@botiverse/raft-daemon 0.72.4 → 0.72.7-play.20260712141058

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,9 +1,13 @@
1
1
  // src/core.ts
2
2
  import path23 from "path";
3
3
  import os8 from "os";
4
+ import { randomUUID as randomUUID9 } from "crypto";
4
5
  import { createRequire as createRequire3 } from "module";
5
- import { accessSync } from "fs";
6
+ import { accessSync, createReadStream as createReadStream4, createWriteStream as createWriteStream2 } from "fs";
7
+ import { mkdtemp, rm as rm4, stat as stat4 } from "fs/promises";
6
8
  import { fileURLToPath } from "url";
9
+ import { Readable as Readable3 } from "stream";
10
+ import { pipeline as pipeline2 } from "stream/promises";
7
11
 
8
12
  // ../shared/src/typeGuards.ts
9
13
  function makeIsMember(members) {
@@ -1362,6 +1366,7 @@ var PROMOTED_IDENTITY_ATTRS = [
1362
1366
  "launch_id",
1363
1367
  "session_id",
1364
1368
  "request_id",
1369
+ "operation_id",
1365
1370
  "route_pattern",
1366
1371
  "caller_kind"
1367
1372
  ];
@@ -1448,6 +1453,7 @@ var TRACE_B0_FIELD_DEFINITIONS = defineTraceFields([
1448
1453
  { key: "advances_observed_clock", fieldClass: "query_axis", placement: "span_or_event", valueKind: "closed_enum", enumBinding: "pending_457" },
1449
1454
  { key: "duration_ms", fieldClass: "query_axis", placement: "span_or_event", valueKind: "numeric" },
1450
1455
  { key: "request_id", fieldClass: "query_axis", placement: "span", valueKind: "identity", highCardinality: true },
1456
+ { key: "operation_id", fieldClass: "query_axis", placement: "span_or_event", valueKind: "identity", highCardinality: true },
1451
1457
  { key: "route_pattern", fieldClass: "query_axis", placement: "span", valueKind: "route" },
1452
1458
  { key: "caller_kind", fieldClass: "query_axis", placement: "span", valueKind: "closed_enum", enumBinding: "stable" },
1453
1459
  { key: "server_id", fieldClass: "query_axis", placement: "span", valueKind: "identity", highCardinality: true },
@@ -1472,10 +1478,14 @@ var TRACE_B0_FIELD_DEFINITIONS = defineTraceFields([
1472
1478
  { key: "phase", fieldClass: "query_axis", placement: "span_or_event", valueKind: "closed_enum", enumBinding: "pending_457" },
1473
1479
  { key: "eligibility_subcheck", fieldClass: "query_axis", placement: "event", valueKind: "closed_enum", enumBinding: "pending_457" },
1474
1480
  { key: "hint_source", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1481
+ { key: "candidate_activity", fieldClass: "family_query_axis", placement: "span_or_event", valueKind: "closed_enum", scope: "family:activity" },
1482
+ { key: "served_activity", fieldClass: "family_query_axis", placement: "span_or_event", valueKind: "closed_enum", scope: "family:activity" },
1483
+ { key: "write_action", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity", enumBinding: "stable", enumValues: ["none"] },
1484
+ { key: "arbitration_reason", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity", enumBinding: "stable", enumValues: ["trusted_snapshot", "owner_mirror_read_through"] },
1475
1485
  { key: "weak_source", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1476
1486
  { key: "competing_fact", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1477
1487
  { key: "resolved_activity", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1478
- { key: "previous_activity", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1488
+ { key: "previous_activity", fieldClass: "family_query_axis", placement: "span_or_event", valueKind: "closed_enum", scope: "family:activity" },
1479
1489
  { key: "next_activity", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1480
1490
  { key: "repair_kind", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
1481
1491
  { key: "activity_write_site", fieldClass: "family_query_axis", placement: "event", valueKind: "closed_enum", scope: "family:activity" },
@@ -1674,7 +1684,7 @@ function isEnvAssignmentToken(token) {
1674
1684
  function isSlockExecutableToken(token) {
1675
1685
  const lastSep = Math.max(token.lastIndexOf("/"), token.lastIndexOf("\\"));
1676
1686
  const base = (lastSep >= 0 ? token.slice(lastSep + 1) : token).toLowerCase();
1677
- return base === "slock" || base === "slock.cmd";
1687
+ return base === "slock" || base === "slock.cmd" || base === "raft" || base === "raft.cmd";
1678
1688
  }
1679
1689
  function isShellExecutableToken(token) {
1680
1690
  const lastSep = Math.max(token.lastIndexOf("/"), token.lastIndexOf("\\"));
@@ -1785,6 +1795,16 @@ function resolveSlockCliInvocation(toolName, input) {
1785
1795
  visibility: rest.includes("--private") ? "private" : rest.includes("--public") ? "public" : void 0
1786
1796
  }
1787
1797
  };
1798
+ case "channel archive":
1799
+ return {
1800
+ toolName: "archive_channel",
1801
+ input: { target: readOptionValue(rest, "--target") }
1802
+ };
1803
+ case "channel unarchive":
1804
+ return {
1805
+ toolName: "unarchive_channel",
1806
+ input: { target: readOptionValue(rest, "--target") }
1807
+ };
1788
1808
  case "channel add-member":
1789
1809
  return {
1790
1810
  toolName: "add_channel_member",
@@ -2008,8 +2028,90 @@ var actionCardActionSchema = z.discriminatedUnion("type", [
2008
2028
  integrationUpdateAppRegistrationOperationSchema
2009
2029
  ]);
2010
2030
 
2011
- // ../shared/src/agentApiContract.ts
2031
+ // ../shared/src/featureFlagRolloutGuardrail.ts
2012
2032
  import { z as z2 } from "zod";
2033
+ var FEATURE_FLAG_ROLLOUT_GUARDRAIL_SCHEMA = "feature_flag_rollout_guardrail.v1";
2034
+ var FEATURE_FLAG_ROLLOUT_GUARDRAIL_ISSUER = "feature-flag-guardrail";
2035
+ var FEATURE_FLAG_ROLLOUT_GUARDRAIL_POLICY_VERSION = "v1";
2036
+ var FEATURE_FLAG_ROLLOUT_GUARDRAIL_MAX_RECEIPT_AGE_MS = 5 * 60 * 1e3;
2037
+ var FLAG_KEY_RE = /^[a-z0-9][a-z0-9_.-]{0,127}$/;
2038
+ var CONTROL_PLANE_ID_RE = /^[a-z0-9][a-z0-9_.:-]{0,127}$/;
2039
+ var UUID_RE = /^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/;
2040
+ var flagKeySchema = z2.string().regex(FLAG_KEY_RE);
2041
+ var controlPlaneIdSchema = z2.string().regex(CONTROL_PLANE_ID_RE);
2042
+ var uuidSchema2 = z2.string().regex(UUID_RE);
2043
+ var configVersionSchema = z2.number().refine(Number.isSafeInteger).refine((value) => value >= 0);
2044
+ var basisPointsSchema = z2.number().int().min(0).max(1e4);
2045
+ var ruleSchema = z2.object({
2046
+ id: uuidSchema2,
2047
+ flagKey: flagKeySchema.optional(),
2048
+ stage: z2.enum(["user", "platform", "server", "plan", "percentage"]),
2049
+ priority: z2.number().int(),
2050
+ decision: z2.enum(["allow", "deny"]),
2051
+ values: z2.array(z2.string().min(1)).refine((values) => new Set(values).size === values.length),
2052
+ percentageBasisPoints: basisPointsSchema.nullable(),
2053
+ variant: z2.string().min(1).nullable()
2054
+ });
2055
+ var baseStateSchema = z2.strictObject({
2056
+ controlPlaneId: controlPlaneIdSchema,
2057
+ flagKey: flagKeySchema,
2058
+ configVersion: configVersionSchema,
2059
+ killSwitch: z2.boolean(),
2060
+ // Rules are parsed only when the requested operation depends on them. This
2061
+ // keeps emergency kill available even if unrelated rule payloads are bad.
2062
+ rules: z2.unknown().optional()
2063
+ });
2064
+ var intentSchema = z2.discriminatedUnion("kind", [
2065
+ z2.strictObject({
2066
+ kind: z2.literal("server_allowlist_set"),
2067
+ flagKey: flagKeySchema,
2068
+ expectedConfigVersion: configVersionSchema.optional(),
2069
+ serverId: uuidSchema2,
2070
+ desired: z2.enum(["present", "absent"])
2071
+ }),
2072
+ z2.strictObject({
2073
+ kind: z2.literal("percentage_set"),
2074
+ flagKey: flagKeySchema,
2075
+ expectedConfigVersion: configVersionSchema.optional(),
2076
+ desiredBasisPoints: basisPointsSchema
2077
+ }),
2078
+ z2.strictObject({
2079
+ kind: z2.literal("kill_switch_set"),
2080
+ flagKey: flagKeySchema,
2081
+ expectedConfigVersion: configVersionSchema.optional(),
2082
+ desired: z2.boolean()
2083
+ })
2084
+ ]);
2085
+ var wideningOperationSchema = z2.discriminatedUnion("kind", [
2086
+ z2.strictObject({
2087
+ kind: z2.literal("server_allowlist_add"),
2088
+ ruleId: uuidSchema2.nullable(),
2089
+ serverId: uuidSchema2
2090
+ }),
2091
+ z2.strictObject({
2092
+ kind: z2.literal("percentage_increase"),
2093
+ ruleId: uuidSchema2.nullable(),
2094
+ fromBasisPoints: basisPointsSchema,
2095
+ toBasisPoints: basisPointsSchema
2096
+ }).refine((operation) => operation.toBasisPoints > operation.fromBasisPoints),
2097
+ z2.strictObject({ kind: z2.literal("kill_switch_disable") })
2098
+ ]);
2099
+ var receiptSchema = z2.strictObject({
2100
+ schema: z2.literal(FEATURE_FLAG_ROLLOUT_GUARDRAIL_SCHEMA),
2101
+ id: uuidSchema2,
2102
+ verdict: z2.enum(["pass", "fail"]),
2103
+ issuer: z2.literal(FEATURE_FLAG_ROLLOUT_GUARDRAIL_ISSUER),
2104
+ controlPlaneId: controlPlaneIdSchema,
2105
+ flagKey: flagKeySchema,
2106
+ configVersion: configVersionSchema,
2107
+ operation: wideningOperationSchema,
2108
+ policyVersion: z2.literal(FEATURE_FLAG_ROLLOUT_GUARDRAIL_POLICY_VERSION),
2109
+ evaluatedAt: z2.string(),
2110
+ expiresAt: z2.string()
2111
+ });
2112
+
2113
+ // ../shared/src/agentApiContract.ts
2114
+ import { z as z3 } from "zod";
2013
2115
 
2014
2116
  // ../shared/src/attentionDependencyOracle.ts
2015
2117
  var ATTENTION_HINT_SCHEMA = "attention-dependency-hint.v1";
@@ -2017,78 +2119,78 @@ var ATTENTION_HINT_DEFAULT_WINDOW_MS = 7 * 24 * 60 * 60 * 1e3;
2017
2119
 
2018
2120
  // ../shared/src/agentApiContract.ts
2019
2121
  var AGENT_API_BASE_PATH = "/internal/agent-api";
2020
- var optionalStringSchema = z2.string().trim().optional();
2021
- var optionalStringArraySchema = z2.array(z2.string().trim().min(1)).optional();
2022
- var optionalBooleanSchema = z2.boolean().optional();
2023
- var optionalNumberSchema = z2.number().finite().optional();
2024
- var nullableStringSchema = z2.string().nullable();
2025
- var nullableNumberSchema = z2.number().finite().nullable();
2026
- var optionalIsoTimestampSchema = z2.string().datetime().optional();
2027
- var agentStatusSchema = z2.enum(["active", "inactive", "stopped"]);
2028
- var reminderStatusSchema = z2.enum(["scheduled", "fired", "canceled"]);
2029
- var reminderEventTypeSchema = z2.enum(["scheduled", "fired", "snoozed", "updated", "canceled"]);
2030
- var reasoningEffortSchema = z2.enum(["low", "medium", "high", "xhigh", "max", "ultra"]);
2031
- var profileVisibilityMembershipStatusSchema = z2.enum(["active", "removed"]);
2032
- var passthroughObject = (shape) => z2.object(shape).passthrough();
2033
- var taskStatusSchema = z2.enum(["todo", "in_progress", "in_review", "done", "closed"]);
2122
+ var optionalStringSchema = z3.string().trim().optional();
2123
+ var optionalStringArraySchema = z3.array(z3.string().trim().min(1)).optional();
2124
+ var optionalBooleanSchema = z3.boolean().optional();
2125
+ var optionalNumberSchema = z3.number().finite().optional();
2126
+ var nullableStringSchema = z3.string().nullable();
2127
+ var nullableNumberSchema = z3.number().finite().nullable();
2128
+ var optionalIsoTimestampSchema = z3.string().datetime().optional();
2129
+ var agentStatusSchema = z3.enum(["active", "inactive", "stopped"]);
2130
+ var reminderStatusSchema = z3.enum(["scheduled", "fired", "canceled"]);
2131
+ var reminderEventTypeSchema = z3.enum(["scheduled", "fired", "snoozed", "updated", "canceled"]);
2132
+ var reasoningEffortSchema = z3.enum(["low", "medium", "high", "xhigh", "max", "ultra"]);
2133
+ var profileVisibilityMembershipStatusSchema = z3.enum(["active", "left", "removed"]);
2134
+ var passthroughObject = (shape) => z3.object(shape).passthrough();
2135
+ var taskStatusSchema = z3.enum(["todo", "in_progress", "in_review", "done", "closed"]);
2034
2136
  var agentApiEventsQuerySchema = passthroughObject({
2035
2137
  since: optionalStringSchema,
2036
2138
  limit: optionalStringSchema
2037
2139
  });
2038
2140
  var agentApiHistoryQuerySchema = passthroughObject({
2039
- channel: z2.string().trim().min(1),
2141
+ channel: z3.string().trim().min(1),
2040
2142
  before: optionalStringSchema,
2041
2143
  after: optionalStringSchema,
2042
2144
  around: optionalStringSchema,
2043
2145
  limit: optionalStringSchema
2044
2146
  });
2045
2147
  var agentApiKnowledgeGetQuerySchema = passthroughObject({
2046
- topic: z2.string().trim().min(1),
2148
+ topic: z3.string().trim().min(1),
2047
2149
  reason: optionalStringSchema,
2048
2150
  turn_id: optionalStringSchema,
2049
2151
  trace_id: optionalStringSchema
2050
2152
  });
2051
2153
  var agentApiKnowledgeGetResponseSchema = passthroughObject({
2052
- ok: z2.literal(true),
2053
- docId: z2.string(),
2054
- topicOrPath: z2.string(),
2055
- docVersion: z2.string(),
2056
- docState: z2.string(),
2057
- contentType: z2.string(),
2058
- content: z2.string()
2154
+ ok: z3.literal(true),
2155
+ docId: z3.string(),
2156
+ topicOrPath: z3.string(),
2157
+ docVersion: z3.string(),
2158
+ docState: z3.string(),
2159
+ contentType: z3.string(),
2160
+ content: z3.string()
2059
2161
  });
2060
2162
  var agentApiKnowledgeSearchQuerySchema = passthroughObject({
2061
- query: z2.string().trim().min(1),
2163
+ query: z3.string().trim().min(1),
2062
2164
  scope: optionalStringSchema,
2063
2165
  reason: optionalStringSchema,
2064
2166
  turn_id: optionalStringSchema,
2065
2167
  trace_id: optionalStringSchema
2066
2168
  });
2067
2169
  var agentApiKnowledgeSearchResultSchema = passthroughObject({
2068
- slug: z2.string(),
2069
- title: z2.string(),
2070
- firstScreen: z2.string()
2170
+ slug: z3.string(),
2171
+ title: z3.string(),
2172
+ firstScreen: z3.string()
2071
2173
  });
2072
2174
  var agentApiKnowledgeSearchResponseSchema = passthroughObject({
2073
- ok: z2.literal(true),
2074
- query: z2.string(),
2075
- scope: z2.string().nullable(),
2076
- results: z2.array(agentApiKnowledgeSearchResultSchema)
2175
+ ok: z3.literal(true),
2176
+ query: z3.string(),
2177
+ scope: z3.string().nullable(),
2178
+ results: z3.array(agentApiKnowledgeSearchResultSchema)
2077
2179
  });
2078
2180
  var agentApiMessageSearchQuerySchema = passthroughObject({
2079
2181
  q: optionalStringSchema,
2080
2182
  channel: optionalStringSchema,
2081
2183
  sender: optionalStringSchema,
2082
2184
  senderId: optionalStringSchema,
2083
- sort: z2.enum(["relevance", "recent"]).optional(),
2185
+ sort: z3.enum(["relevance", "recent"]).optional(),
2084
2186
  before: optionalStringSchema,
2085
2187
  after: optionalStringSchema,
2086
2188
  limit: optionalStringSchema,
2087
2189
  offset: optionalStringSchema
2088
2190
  });
2089
2191
  var agentApiSendBodySchema = passthroughObject({
2090
- target: z2.string().optional(),
2091
- content: z2.string().optional(),
2192
+ target: z3.string().optional(),
2193
+ content: z3.string().optional(),
2092
2194
  attachmentIds: optionalStringArraySchema,
2093
2195
  idempotencyKey: optionalStringSchema,
2094
2196
  continue: optionalBooleanSchema,
@@ -2098,107 +2200,114 @@ var agentApiSendBodySchema = passthroughObject({
2098
2200
  draftReplacedExisting: optionalBooleanSchema,
2099
2201
  seenUpToSeq: optionalNumberSchema
2100
2202
  });
2203
+ var legacyAgentSendBodySchema = agentApiSendBodySchema.extend({
2204
+ channel: z3.string().optional(),
2205
+ dm_to: z3.string().optional()
2206
+ });
2101
2207
  var agentApiMessageResolveParamsSchema = passthroughObject({
2102
- msgId: z2.string().trim().min(1).transform(asMessageId)
2208
+ msgId: z3.string().trim().min(1).transform(asMessageId)
2103
2209
  });
2104
2210
  var agentApiMessageReactionParamsSchema = passthroughObject({
2105
- msgId: z2.string().trim().min(1).transform(asMessageId)
2211
+ msgId: z3.string().trim().min(1).transform(asMessageId)
2106
2212
  });
2107
2213
  var agentApiMessageReactionBodySchema = passthroughObject({
2108
- emoji: z2.string().trim().min(1).max(16).refine((value) => !/\s/.test(value), {
2214
+ emoji: z3.string().trim().min(1).max(16).refine((value) => !/\s/.test(value), {
2109
2215
  message: "A single reaction emoji is required"
2110
2216
  })
2111
2217
  });
2112
2218
  var agentApiChannelMembershipParamsSchema = passthroughObject({
2113
- channelId: z2.string().trim().min(1).transform(asChannelId)
2219
+ channelId: z3.string().trim().min(1).transform(asChannelId)
2220
+ });
2221
+ var agentApiChannelLifecycleBodySchema = passthroughObject({
2222
+ target: z3.string().trim().min(1)
2114
2223
  });
2115
2224
  var agentApiAttachmentDownloadParamsSchema = passthroughObject({
2116
- attachmentId: z2.string().trim().min(1)
2225
+ attachmentId: z3.string().trim().min(1)
2117
2226
  });
2118
2227
  var agentApiAttachmentCommentsParamsSchema = passthroughObject({
2119
- attachmentId: z2.string().trim().min(1)
2228
+ attachmentId: z3.string().trim().min(1)
2120
2229
  });
2121
2230
  var agentApiAttachmentCommentsQuerySchema = passthroughObject({
2122
2231
  limit: optionalStringSchema
2123
2232
  });
2124
2233
  var agentApiAttachmentCommentAnchorSchema = passthroughObject({
2125
- type: z2.string().trim().min(1),
2126
- data: z2.record(z2.string(), z2.unknown())
2234
+ type: z3.string().trim().min(1),
2235
+ data: z3.record(z3.string(), z3.unknown())
2127
2236
  });
2128
2237
  var agentApiAttachmentCommentReactionSchema = passthroughObject({
2129
- emoji: z2.string().trim().min(1),
2130
- reactorType: z2.string().trim().min(1),
2131
- reactorId: z2.string().trim().min(1),
2132
- createdAt: z2.string().datetime()
2238
+ emoji: z3.string().trim().min(1),
2239
+ reactorType: z3.string().trim().min(1),
2240
+ reactorId: z3.string().trim().min(1),
2241
+ createdAt: z3.string().datetime()
2133
2242
  });
2134
2243
  var agentApiAttachmentCommentResolvedBySchema = passthroughObject({
2135
- reactorId: z2.string().trim().min(1),
2136
- reactorType: z2.string().trim().min(1)
2244
+ reactorId: z3.string().trim().min(1),
2245
+ reactorType: z3.string().trim().min(1)
2137
2246
  });
2138
2247
  var agentApiAttachmentCommentSchema = passthroughObject({
2139
- id: z2.string().trim().min(1),
2140
- channelId: z2.string().trim().min(1).optional(),
2141
- senderId: z2.string().trim().min(1),
2142
- senderType: z2.enum(["user", "agent"]),
2143
- senderName: z2.string().trim().min(1),
2248
+ id: z3.string().trim().min(1),
2249
+ channelId: z3.string().trim().min(1).optional(),
2250
+ senderId: z3.string().trim().min(1),
2251
+ senderType: z3.enum(["user", "agent"]),
2252
+ senderName: z3.string().trim().min(1),
2144
2253
  senderAvatarUrl: nullableStringSchema.optional(),
2145
2254
  senderGravatarHash: nullableStringSchema.optional(),
2146
- content: z2.string(),
2147
- createdAt: z2.string().datetime(),
2148
- reactions: z2.array(agentApiAttachmentCommentReactionSchema),
2255
+ content: z3.string(),
2256
+ createdAt: z3.string().datetime(),
2257
+ reactions: z3.array(agentApiAttachmentCommentReactionSchema),
2149
2258
  anchor: agentApiAttachmentCommentAnchorSchema.nullable(),
2150
- resolved: z2.boolean().optional(),
2259
+ resolved: z3.boolean().optional(),
2151
2260
  resolvedBy: agentApiAttachmentCommentResolvedBySchema.nullable().optional(),
2152
- resolvedAt: z2.string().datetime().nullable().optional()
2261
+ resolvedAt: z3.string().datetime().nullable().optional()
2153
2262
  });
2154
2263
  var agentApiAttachmentCommentsResponseSchema = passthroughObject({
2155
- comments: z2.array(agentApiAttachmentCommentSchema),
2264
+ comments: z3.array(agentApiAttachmentCommentSchema),
2156
2265
  threadChannelId: nullableStringSchema.optional(),
2157
2266
  viewer: passthroughObject({
2158
- canComment: z2.boolean(),
2159
- reason: z2.string().optional(),
2160
- canResolve: z2.boolean(),
2267
+ canComment: z3.boolean(),
2268
+ reason: z3.string().optional(),
2269
+ canResolve: z3.boolean(),
2161
2270
  resolveAction: passthroughObject({
2162
- type: z2.string().trim().min(1),
2163
- emoji: z2.string().trim().min(1)
2271
+ type: z3.string().trim().min(1),
2272
+ emoji: z3.string().trim().min(1)
2164
2273
  }).optional()
2165
2274
  }).optional()
2166
2275
  });
2167
2276
  var agentApiChannelMembersQuerySchema = passthroughObject({
2168
- channel: z2.string().trim().min(1)
2277
+ channel: z3.string().trim().min(1)
2169
2278
  });
2170
2279
  var agentApiResolveChannelBodySchema = passthroughObject({
2171
- target: z2.string().trim().min(1)
2280
+ target: z3.string().trim().min(1)
2172
2281
  });
2173
2282
  var agentApiResolveChannelResponseSchema = passthroughObject({
2174
- channelId: z2.string().trim().min(1)
2283
+ channelId: z3.string().trim().min(1)
2175
2284
  });
2176
2285
  var agentApiThreadUnfollowBodySchema = passthroughObject({
2177
- thread: z2.string().trim().min(1),
2178
- reason: z2.string().trim().min(1).max(200).optional()
2286
+ thread: z3.string().trim().min(1),
2287
+ reason: z3.string().trim().min(1).max(200).optional()
2179
2288
  });
2180
2289
  var agentApiTaskClaimBodySchema = passthroughObject({
2181
- channel: z2.string().trim().min(1),
2182
- task_numbers: z2.array(z2.number().int().positive()).optional(),
2290
+ channel: z3.string().trim().min(1),
2291
+ task_numbers: z3.array(z3.number().int().positive()).optional(),
2183
2292
  message_ids: optionalStringArraySchema
2184
2293
  });
2185
2294
  var agentApiTaskListQuerySchema = passthroughObject({
2186
- channel: z2.string().trim().min(1),
2187
- status: z2.union([taskStatusSchema, z2.literal("all")]).optional()
2295
+ channel: z3.string().trim().min(1),
2296
+ status: z3.union([taskStatusSchema, z3.literal("all")]).optional()
2188
2297
  });
2189
2298
  var agentApiTaskCreateBodySchema = passthroughObject({
2190
- channel: z2.string().trim().min(1),
2191
- tasks: z2.array(passthroughObject({
2192
- title: z2.string().trim().min(1)
2299
+ channel: z3.string().trim().min(1),
2300
+ tasks: z3.array(passthroughObject({
2301
+ title: z3.string().trim().min(1)
2193
2302
  })).min(1)
2194
2303
  });
2195
2304
  var agentApiTaskUnclaimBodySchema = passthroughObject({
2196
- channel: z2.string().trim().min(1),
2197
- task_number: z2.number().int().positive()
2305
+ channel: z3.string().trim().min(1),
2306
+ task_number: z3.number().int().positive()
2198
2307
  });
2199
2308
  var agentApiTaskUpdateStatusBodySchema = passthroughObject({
2200
- channel: z2.string().trim().min(1),
2201
- task_number: z2.number().int().positive(),
2309
+ channel: z3.string().trim().min(1),
2310
+ task_number: z3.number().int().positive(),
2202
2311
  status: taskStatusSchema
2203
2312
  });
2204
2313
  var agentApiReminderListQuerySchema = passthroughObject({
@@ -2206,20 +2315,20 @@ var agentApiReminderListQuerySchema = passthroughObject({
2206
2315
  all: optionalStringSchema
2207
2316
  });
2208
2317
  var agentApiReminderParamsSchema = passthroughObject({
2209
- reminderId: z2.string().trim().min(1)
2318
+ reminderId: z3.string().trim().min(1)
2210
2319
  });
2211
2320
  var agentApiReminderScheduleBodySchema = passthroughObject({
2212
- title: z2.string(),
2321
+ title: z3.string(),
2213
2322
  fireAt: optionalStringSchema,
2214
2323
  delaySeconds: optionalNumberSchema,
2215
- msgId: z2.string().nullable().optional(),
2216
- payload: z2.unknown().optional(),
2324
+ msgId: z3.string().nullable().optional(),
2325
+ payload: z3.unknown().optional(),
2217
2326
  repeat: optionalStringSchema,
2218
2327
  tz: optionalStringSchema,
2219
2328
  channel: optionalStringSchema
2220
2329
  });
2221
2330
  var agentApiReminderSnoozeBodySchema = passthroughObject({
2222
- delaySeconds: z2.number().finite()
2331
+ delaySeconds: z3.number().finite()
2223
2332
  });
2224
2333
  var agentApiReminderUpdateBodySchema = passthroughObject({
2225
2334
  fireAt: optionalStringSchema,
@@ -2237,58 +2346,58 @@ var agentApiProfileUpdateBodySchema = passthroughObject({
2237
2346
  description: optionalStringSchema
2238
2347
  });
2239
2348
  var agentApiProfileCreatedAgentSchema = passthroughObject({
2240
- id: z2.string(),
2241
- name: z2.string(),
2349
+ id: z3.string(),
2350
+ name: z3.string(),
2242
2351
  displayName: nullableStringSchema,
2243
2352
  avatarUrl: nullableStringSchema,
2244
- runtime: z2.string(),
2353
+ runtime: z3.string(),
2245
2354
  status: agentStatusSchema
2246
2355
  });
2247
- var agentApiProfileCreatorSchema = z2.union([
2356
+ var agentApiProfileCreatorSchema = z3.union([
2248
2357
  passthroughObject({
2249
- type: z2.literal("human"),
2250
- id: z2.string(),
2251
- name: z2.string(),
2358
+ type: z3.literal("human"),
2359
+ id: z3.string(),
2360
+ name: z3.string(),
2252
2361
  displayName: nullableStringSchema,
2253
2362
  avatarUrl: nullableStringSchema,
2254
- gravatarHash: z2.string()
2363
+ gravatarHash: z3.string()
2255
2364
  }),
2256
2365
  passthroughObject({
2257
- type: z2.literal("agent"),
2258
- id: z2.string(),
2259
- name: z2.string(),
2366
+ type: z3.literal("agent"),
2367
+ id: z3.string(),
2368
+ name: z3.string(),
2260
2369
  displayName: nullableStringSchema,
2261
2370
  avatarUrl: nullableStringSchema,
2262
2371
  deletedAt: nullableStringSchema
2263
2372
  })
2264
2373
  ]);
2265
- var agentApiProfileViewSchema = z2.discriminatedUnion("kind", [
2374
+ var agentApiProfileViewSchema = z3.discriminatedUnion("kind", [
2266
2375
  passthroughObject({
2267
- kind: z2.literal("human"),
2268
- id: z2.string(),
2269
- isSelf: z2.boolean(),
2270
- name: z2.string(),
2376
+ kind: z3.literal("human"),
2377
+ id: z3.string(),
2378
+ isSelf: z3.boolean(),
2379
+ name: z3.string(),
2271
2380
  displayName: nullableStringSchema,
2272
2381
  description: nullableStringSchema,
2273
2382
  avatarUrl: nullableStringSchema,
2274
2383
  email: nullableStringSchema,
2275
- role: z2.enum(["owner", "admin", "member"]).nullable(),
2384
+ role: z3.enum(["owner", "admin", "member"]).nullable(),
2276
2385
  joinedAt: nullableStringSchema,
2277
2386
  membershipStatus: profileVisibilityMembershipStatusSchema,
2278
- createdAgents: z2.array(agentApiProfileCreatedAgentSchema)
2387
+ createdAgents: z3.array(agentApiProfileCreatedAgentSchema)
2279
2388
  }),
2280
2389
  passthroughObject({
2281
- kind: z2.literal("agent"),
2282
- id: z2.string(),
2283
- isSelf: z2.boolean(),
2284
- name: z2.string(),
2390
+ kind: z3.literal("agent"),
2391
+ id: z3.string(),
2392
+ isSelf: z3.boolean(),
2393
+ name: z3.string(),
2285
2394
  displayName: nullableStringSchema,
2286
2395
  description: nullableStringSchema,
2287
2396
  avatarUrl: nullableStringSchema,
2288
2397
  status: agentStatusSchema,
2289
- serverRole: z2.enum(["owner", "admin", "member"]).nullable(),
2290
- runtime: z2.string(),
2291
- model: z2.string(),
2398
+ serverRole: z3.enum(["owner", "admin", "member"]).nullable(),
2399
+ runtime: z3.string(),
2400
+ model: z3.string(),
2292
2401
  reasoningEffort: reasoningEffortSchema.nullable(),
2293
2402
  executionMode: nullableStringSchema,
2294
2403
  computerId: nullableStringSchema,
@@ -2296,20 +2405,20 @@ var agentApiProfileViewSchema = z2.discriminatedUnion("kind", [
2296
2405
  computerHostname: nullableStringSchema,
2297
2406
  daemonVersion: nullableStringSchema,
2298
2407
  creator: agentApiProfileCreatorSchema.nullable(),
2299
- createdAgents: z2.array(agentApiProfileCreatedAgentSchema),
2300
- createdAt: z2.string(),
2408
+ createdAgents: z3.array(agentApiProfileCreatedAgentSchema),
2409
+ createdAt: z3.string(),
2301
2410
  deletedAt: nullableStringSchema
2302
2411
  })
2303
2412
  ]);
2304
2413
  var agentApiIntegrationLoginBodySchema = passthroughObject({
2305
- service: z2.string().trim().min(1),
2414
+ service: z3.string().trim().min(1),
2306
2415
  scopes: optionalStringArraySchema,
2307
2416
  target: optionalStringSchema
2308
2417
  });
2309
2418
  var agentApiIntegrationAppPrepareBodySchema = passthroughObject({
2310
- mode: z2.enum(["register", "update"]),
2311
- target: z2.string().trim().min(1),
2312
- clientKey: z2.string().trim().min(1),
2419
+ mode: z3.enum(["register", "update"]),
2420
+ target: z3.string().trim().min(1),
2421
+ clientKey: z3.string().trim().min(1),
2313
2422
  name: optionalStringSchema,
2314
2423
  description: optionalStringSchema,
2315
2424
  homepageUrl: optionalStringSchema,
@@ -2320,138 +2429,158 @@ var agentApiIntegrationAppPrepareBodySchema = passthroughObject({
2320
2429
  draftHint: optionalStringSchema
2321
2430
  });
2322
2431
  var agentApiIntegrationAppRotateSecretBodySchema = passthroughObject({
2323
- clientKey: z2.string().trim().min(1)
2432
+ clientKey: z3.string().trim().min(1)
2324
2433
  });
2325
2434
  var agentApiActionPrepareBodySchema = passthroughObject({
2326
- target: z2.string().trim().min(1),
2435
+ target: z3.string().trim().min(1),
2327
2436
  action: actionCardActionSchema
2328
2437
  });
2329
2438
  var agentApiServerInfoResponseSchema = passthroughObject({
2330
2439
  runtimeContext: passthroughObject({
2331
- agentId: z2.string(),
2332
- runtime: z2.string().optional(),
2333
- model: z2.string().optional(),
2440
+ agentId: z3.string(),
2441
+ runtime: z3.string().optional(),
2442
+ model: z3.string().optional(),
2334
2443
  reasoningEffort: reasoningEffortSchema.nullable().optional(),
2335
- serverId: z2.string(),
2336
- machineId: z2.string().nullable().optional(),
2337
- machineName: z2.string().nullable().optional(),
2338
- machineDescription: z2.string().nullable().optional(),
2339
- machineHostname: z2.string().nullable().optional(),
2340
- machineOs: z2.string().nullable().optional(),
2341
- daemonVersion: z2.string().nullable().optional(),
2342
- workspacePath: z2.string().nullable().optional()
2444
+ serverId: z3.string(),
2445
+ machineId: z3.string().nullable().optional(),
2446
+ machineName: z3.string().nullable().optional(),
2447
+ machineDescription: z3.string().nullable().optional(),
2448
+ machineHostname: z3.string().nullable().optional(),
2449
+ machineOs: z3.string().nullable().optional(),
2450
+ daemonVersion: z3.string().nullable().optional(),
2451
+ workspacePath: z3.string().nullable().optional()
2343
2452
  }),
2344
- serverRole: z2.string().nullable().optional(),
2453
+ serverRole: z3.string().nullable().optional(),
2345
2454
  serverCapabilities: passthroughObject({}).optional(),
2346
- channels: z2.array(passthroughObject({
2347
- id: z2.string().transform(asChannelId),
2348
- name: z2.string(),
2349
- joined: z2.boolean()
2455
+ channels: z3.array(passthroughObject({
2456
+ id: z3.string().transform(asChannelId),
2457
+ name: z3.string(),
2458
+ joined: z3.boolean()
2350
2459
  })),
2351
- agents: z2.array(passthroughObject({
2352
- name: z2.string(),
2353
- status: z2.string().optional(),
2354
- activity: z2.string().nullable().optional(),
2355
- activityDetail: z2.string().nullable().optional(),
2356
- role: z2.enum(["owner", "admin", "member"]).nullable().optional()
2460
+ agents: z3.array(passthroughObject({
2461
+ name: z3.string(),
2462
+ status: z3.string().optional(),
2463
+ activity: z3.string().nullable().optional(),
2464
+ activityDetail: z3.string().nullable().optional(),
2465
+ role: z3.enum(["owner", "admin", "member"]).nullable().optional()
2357
2466
  })),
2358
- humans: z2.array(passthroughObject({
2359
- name: z2.string(),
2360
- role: z2.enum(["owner", "admin", "member"]).nullable().optional()
2467
+ humans: z3.array(passthroughObject({
2468
+ name: z3.string(),
2469
+ role: z3.enum(["owner", "admin", "member"]).nullable().optional()
2361
2470
  }))
2362
2471
  });
2363
2472
  var agentApiMentionActionsPendingQuerySchema = passthroughObject({
2364
2473
  limit: optionalStringSchema
2365
2474
  });
2366
2475
  var agentApiMentionActionEnvelopeSchema = passthroughObject({
2367
- resolutionId: z2.string()
2476
+ resolutionId: z3.string()
2477
+ });
2478
+ var agentApiMentionActionResultSchema = passthroughObject({
2479
+ resolutionId: z3.string(),
2480
+ status: z3.enum([
2481
+ "queued",
2482
+ "delivered",
2483
+ "dropped",
2484
+ "stale",
2485
+ "expired",
2486
+ "no_permission",
2487
+ "not_found",
2488
+ "ambiguous"
2489
+ ]),
2490
+ action: z3.enum(["notify", "add"]).optional(),
2491
+ reason: optionalStringSchema,
2492
+ messageId: optionalStringSchema,
2493
+ channelId: optionalStringSchema,
2494
+ targetType: z3.enum(["user", "agent"]).optional(),
2495
+ targetId: optionalStringSchema,
2496
+ dedupedResolutionIds: optionalStringArraySchema
2368
2497
  });
2369
2498
  var agentApiMentionActionsPendingResponseSchema = passthroughObject({
2370
- pendingMentionActions: z2.array(agentApiMentionActionEnvelopeSchema),
2371
- has_more: z2.boolean().optional()
2499
+ pendingMentionActions: z3.array(agentApiMentionActionEnvelopeSchema),
2500
+ has_more: z3.boolean().optional()
2372
2501
  });
2373
2502
  var agentApiMentionActionsExecuteBodySchema = passthroughObject({
2374
- action: z2.enum(["notify", "add"]),
2503
+ action: z3.enum(["notify", "add"]),
2375
2504
  resolutionIds: optionalStringArraySchema,
2376
2505
  ids: optionalStringArraySchema
2377
2506
  });
2378
2507
  var agentApiMentionActionsExecuteResponseSchema = passthroughObject({
2379
- ok: z2.literal(true),
2380
- action: z2.enum(["notify", "add"]),
2381
- results: z2.array(agentApiMentionActionEnvelopeSchema)
2508
+ ok: z3.literal(true),
2509
+ action: z3.enum(["notify", "add"]),
2510
+ results: z3.array(agentApiMentionActionResultSchema)
2382
2511
  });
2383
2512
  var agentApiIntegrationServiceSchema = passthroughObject({
2384
- id: z2.string(),
2385
- clientId: z2.string(),
2386
- appType: z2.enum(["server_local", "slock_builtin", "third_party_global"]).optional(),
2387
- name: z2.string(),
2513
+ id: z3.string(),
2514
+ clientId: z3.string(),
2515
+ appType: z3.enum(["server_local", "slock_builtin", "third_party_global"]).optional(),
2516
+ name: z3.string(),
2388
2517
  description: nullableStringSchema,
2389
2518
  homepageUrl: nullableStringSchema,
2390
2519
  returnUrl: nullableStringSchema,
2391
2520
  agentManifestUrl: nullableStringSchema,
2392
- agentManifestUrlSource: z2.enum(["explicit", "well_known"]).nullable().optional(),
2393
- createdAt: z2.string(),
2394
- updatedAt: z2.string()
2521
+ agentManifestUrlSource: z3.enum(["explicit", "well_known"]).nullable().optional(),
2522
+ createdAt: z3.string(),
2523
+ updatedAt: z3.string()
2395
2524
  });
2396
2525
  var agentApiActiveIntegrationLoginSchema = passthroughObject({
2397
- id: z2.string(),
2398
- serviceId: z2.string(),
2399
- clientId: z2.string(),
2400
- appType: z2.enum(["server_local", "slock_builtin", "third_party_global"]).optional(),
2401
- name: z2.string(),
2526
+ id: z3.string(),
2527
+ serviceId: z3.string(),
2528
+ clientId: z3.string(),
2529
+ appType: z3.enum(["server_local", "slock_builtin", "third_party_global"]).optional(),
2530
+ name: z3.string(),
2402
2531
  description: nullableStringSchema,
2403
2532
  homepageUrl: nullableStringSchema,
2404
2533
  returnUrl: nullableStringSchema,
2405
2534
  agentManifestUrl: nullableStringSchema,
2406
- agentManifestUrlSource: z2.enum(["explicit", "well_known"]).nullable().optional(),
2407
- scopes: z2.array(z2.string()),
2408
- createdAt: z2.string()
2535
+ agentManifestUrlSource: z3.enum(["explicit", "well_known"]).nullable().optional(),
2536
+ scopes: z3.array(z3.string()),
2537
+ createdAt: z3.string()
2409
2538
  });
2410
2539
  var agentApiIntegrationListResponseSchema = passthroughObject({
2411
- services: z2.array(agentApiIntegrationServiceSchema),
2412
- activeLogins: z2.array(agentApiActiveIntegrationLoginSchema)
2540
+ services: z3.array(agentApiIntegrationServiceSchema),
2541
+ activeLogins: z3.array(agentApiActiveIntegrationLoginSchema)
2413
2542
  });
2414
2543
  var agentApiIntegrationLoginResponseSchema = passthroughObject({
2415
- status: z2.enum(["logged_in", "already_logged_in", "approval_required"]),
2544
+ status: z3.enum(["logged_in", "already_logged_in", "approval_required"]),
2416
2545
  service: agentApiIntegrationServiceSchema,
2417
- scopes: z2.array(z2.string()),
2418
- requestId: z2.string().optional(),
2546
+ scopes: z3.array(z3.string()),
2547
+ requestId: z3.string().optional(),
2419
2548
  session: passthroughObject({
2420
- status: z2.literal("stored"),
2421
- source: z2.enum(["cache", "fresh"]),
2549
+ status: z3.literal("stored"),
2550
+ source: z3.enum(["cache", "fresh"]),
2422
2551
  path: nullableStringSchema
2423
2552
  }).optional(),
2424
2553
  approval: passthroughObject({
2425
- requestId: z2.string(),
2554
+ requestId: z3.string(),
2426
2555
  target: nullableStringSchema,
2427
2556
  actionCardMessageId: nullableStringSchema
2428
2557
  }).optional()
2429
2558
  });
2430
2559
  var agentApiIntegrationAppPrepareResponseSchema = passthroughObject({
2431
- status: z2.literal("prepared"),
2432
- mode: z2.enum(["register", "update"]),
2433
- target: z2.string(),
2434
- actionCardMessageId: z2.string(),
2435
- action: z2.discriminatedUnion("type", [
2560
+ status: z3.literal("prepared"),
2561
+ mode: z3.enum(["register", "update"]),
2562
+ target: z3.string(),
2563
+ actionCardMessageId: z3.string(),
2564
+ action: z3.discriminatedUnion("type", [
2436
2565
  integrationRegisterAppOperationSchema,
2437
2566
  integrationUpdateAppRegistrationOperationSchema
2438
2567
  ])
2439
2568
  });
2440
2569
  var agentApiIntegrationAppRotateSecretResponseSchema = passthroughObject({
2441
- clientId: z2.string(),
2442
- clientKey: z2.string(),
2443
- clientName: z2.string(),
2444
- clientSecret: z2.string()
2570
+ clientId: z3.string(),
2571
+ clientKey: z3.string(),
2572
+ clientName: z3.string(),
2573
+ clientSecret: z3.string()
2445
2574
  });
2446
2575
  var agentApiAttachmentEnvelopeSchema = passthroughObject({
2447
- id: z2.string(),
2448
- filename: z2.string()
2576
+ id: z3.string(),
2577
+ filename: z3.string()
2449
2578
  });
2450
2579
  var agentApiAttachmentUploadResponseSchema = passthroughObject({
2451
- id: z2.string().trim().min(1),
2452
- filename: z2.string(),
2580
+ id: z3.string().trim().min(1),
2581
+ filename: z3.string(),
2453
2582
  mimeType: nullableStringSchema,
2454
- sizeBytes: z2.number().int().nonnegative(),
2583
+ sizeBytes: z3.number().int().nonnegative(),
2455
2584
  thumbnailUrl: nullableStringSchema
2456
2585
  });
2457
2586
  var agentApiMessageEnvelopeSchema = passthroughObject({
@@ -2464,69 +2593,69 @@ var agentApiMessageEnvelopeSchema = passthroughObject({
2464
2593
  sender_type: optionalStringSchema,
2465
2594
  senderName: optionalStringSchema,
2466
2595
  sender_name: optionalStringSchema,
2467
- senderDescription: z2.string().nullable().optional(),
2468
- sender_description: z2.string().nullable().optional(),
2596
+ senderDescription: z3.string().nullable().optional(),
2597
+ sender_description: z3.string().nullable().optional(),
2469
2598
  channel_type: optionalStringSchema,
2470
2599
  channel_name: optionalStringSchema,
2471
2600
  parent_channel_type: optionalStringSchema,
2472
2601
  parent_channel_name: optionalStringSchema,
2473
2602
  content: optionalStringSchema,
2474
- attachments: z2.array(agentApiAttachmentEnvelopeSchema).optional(),
2475
- taskStatus: z2.string().nullable().optional(),
2476
- task_status: z2.string().nullable().optional(),
2477
- taskNumber: z2.number().int().positive().nullable().optional(),
2478
- task_number: z2.number().int().positive().nullable().optional(),
2479
- taskAssigneeId: z2.string().nullable().optional(),
2480
- task_assignee_id: z2.string().nullable().optional(),
2481
- taskAssigneeType: z2.string().nullable().optional(),
2482
- task_assignee_type: z2.string().nullable().optional(),
2483
- threadId: z2.string().nullable().optional(),
2484
- replyCount: z2.number().int().nonnegative().nullable().optional()
2603
+ attachments: z3.array(agentApiAttachmentEnvelopeSchema).optional(),
2604
+ taskStatus: z3.string().nullable().optional(),
2605
+ task_status: z3.string().nullable().optional(),
2606
+ taskNumber: z3.number().int().positive().nullable().optional(),
2607
+ task_number: z3.number().int().positive().nullable().optional(),
2608
+ taskAssigneeId: z3.string().nullable().optional(),
2609
+ task_assignee_id: z3.string().nullable().optional(),
2610
+ taskAssigneeType: z3.string().nullable().optional(),
2611
+ task_assignee_type: z3.string().nullable().optional(),
2612
+ threadId: z3.string().nullable().optional(),
2613
+ replyCount: z3.number().int().nonnegative().nullable().optional()
2485
2614
  });
2486
2615
  var agentApiEventsResponseSchema = passthroughObject({
2487
- events: z2.array(agentApiMessageEnvelopeSchema),
2616
+ events: z3.array(agentApiMessageEnvelopeSchema),
2488
2617
  last_seen_msgId: nullableStringSchema,
2489
2618
  last_seen_seq: nullableNumberSchema,
2490
2619
  reply_target: nullableStringSchema,
2491
- pending_notice_ids: z2.array(z2.string()),
2492
- wake_reason: z2.string().nullable(),
2493
- has_more: z2.boolean()
2620
+ pending_notice_ids: z3.array(z3.string()),
2621
+ wake_reason: z3.string().nullable(),
2622
+ has_more: z3.boolean()
2494
2623
  });
2495
2624
  var agentApiHistoryResponseSchema = passthroughObject({
2496
- messages: z2.array(agentApiMessageEnvelopeSchema),
2497
- has_more: z2.boolean(),
2498
- has_older: z2.boolean(),
2499
- has_newer: z2.boolean(),
2625
+ messages: z3.array(agentApiMessageEnvelopeSchema),
2626
+ has_more: z3.boolean(),
2627
+ has_older: z3.boolean(),
2628
+ has_newer: z3.boolean(),
2500
2629
  last_read_seq: nullableNumberSchema.optional()
2501
2630
  });
2502
2631
  var agentApiHeldFreshnessResponseSchema = passthroughObject({
2503
- ok: z2.literal(true).optional(),
2504
- state: z2.literal("held"),
2505
- outcome: z2.literal("held").optional(),
2506
- subtype: z2.literal("freshness").optional(),
2507
- reason: z2.string().optional(),
2508
- decision: z2.enum(["local_hold", "syncing_hold"]).optional(),
2632
+ ok: z3.literal(true).optional(),
2633
+ state: z3.literal("held"),
2634
+ outcome: z3.literal("held").optional(),
2635
+ subtype: z3.literal("freshness").optional(),
2636
+ reason: z3.string().optional(),
2637
+ decision: z3.enum(["local_hold", "syncing_hold"]).optional(),
2509
2638
  producerFactId: optionalStringSchema,
2510
- available_actions: z2.array(z2.string()).optional(),
2511
- heldMessages: z2.array(agentApiMessageEnvelopeSchema).optional(),
2512
- recentUnread: z2.array(agentApiMessageEnvelopeSchema).optional(),
2639
+ available_actions: z3.array(z3.string()).optional(),
2640
+ heldMessages: z3.array(agentApiMessageEnvelopeSchema).optional(),
2641
+ recentUnread: z3.array(agentApiMessageEnvelopeSchema).optional(),
2513
2642
  newMessageCount: optionalNumberSchema,
2514
2643
  shownMessageCount: optionalNumberSchema,
2515
2644
  omittedMessageCount: optionalNumberSchema,
2516
2645
  mentionAnnotation: passthroughObject({
2517
- formalMentionCount: z2.number().finite()
2646
+ formalMentionCount: z3.number().finite()
2518
2647
  }).optional(),
2519
2648
  continueAnywaySuggested: optionalBooleanSchema,
2520
2649
  seenUpToSeq: optionalNumberSchema,
2521
2650
  seenUpToMessageId: nullableStringSchema.optional()
2522
2651
  });
2523
2652
  var agentApiSendSentResponseSchema = passthroughObject({
2524
- ok: z2.literal(true),
2525
- state: z2.literal("sent"),
2526
- messageId: z2.string(),
2653
+ ok: z3.literal(true),
2654
+ state: z3.literal("sent"),
2655
+ messageId: z3.string(),
2527
2656
  messageSeq: optionalNumberSchema,
2528
- recentUnread: z2.array(agentApiMessageEnvelopeSchema).optional(),
2529
- pendingMentionActions: z2.array(agentApiMessageEnvelopeSchema).optional(),
2657
+ recentUnread: z3.array(agentApiMessageEnvelopeSchema).optional(),
2658
+ pendingMentionActions: z3.array(agentApiMessageEnvelopeSchema).optional(),
2530
2659
  attention: passthroughObject({
2531
2660
  driveByJoinedToPost: passthroughObject({
2532
2661
  reason: optionalStringSchema,
@@ -2535,7 +2664,7 @@ var agentApiSendSentResponseSchema = passthroughObject({
2535
2664
  }).optional()
2536
2665
  }).optional()
2537
2666
  });
2538
- var agentApiSendResponseSchema = z2.discriminatedUnion("state", [
2667
+ var agentApiSendResponseSchema = z3.discriminatedUnion("state", [
2539
2668
  agentApiSendSentResponseSchema,
2540
2669
  agentApiHeldFreshnessResponseSchema
2541
2670
  ]);
@@ -2551,46 +2680,46 @@ var agentApiChannelAttentionSchema = passthroughObject({
2551
2680
  manageApi: optionalStringSchema
2552
2681
  });
2553
2682
  var agentApiOkResponseSchema = passthroughObject({
2554
- ok: z2.literal(true),
2683
+ ok: z3.literal(true),
2555
2684
  attention: agentApiChannelAttentionSchema.optional()
2556
2685
  });
2557
2686
  var agentApiSearchResultSchema = passthroughObject({
2558
- id: z2.string(),
2559
- seq: z2.number().int().nonnegative(),
2560
- channelId: z2.string(),
2561
- threadId: z2.string().nullable(),
2562
- parentMessageId: z2.string().nullable(),
2563
- parentMessageContent: z2.string().nullable(),
2564
- parentChannelId: z2.string(),
2565
- parentChannelName: z2.string(),
2566
- parentChannelType: z2.string(),
2687
+ id: z3.string(),
2688
+ seq: z3.number().int().nonnegative(),
2689
+ channelId: z3.string(),
2690
+ threadId: z3.string().nullable(),
2691
+ parentMessageId: z3.string().nullable(),
2692
+ parentMessageContent: z3.string().nullable(),
2693
+ parentChannelId: z3.string(),
2694
+ parentChannelName: z3.string(),
2695
+ parentChannelType: z3.string(),
2567
2696
  parentChannelArchivedAt: nullableStringSchema,
2568
- senderId: z2.string(),
2569
- senderType: z2.string(),
2570
- senderName: z2.string(),
2571
- channelName: z2.string(),
2572
- channelType: z2.string(),
2697
+ senderId: z3.string(),
2698
+ senderType: z3.string(),
2699
+ senderName: z3.string(),
2700
+ channelName: z3.string(),
2701
+ channelType: z3.string(),
2573
2702
  channelArchivedAt: nullableStringSchema,
2574
- content: z2.string(),
2575
- snippet: z2.string(),
2576
- createdAt: z2.string().datetime()
2703
+ content: z3.string(),
2704
+ snippet: z3.string(),
2705
+ createdAt: z3.string().datetime()
2577
2706
  });
2578
2707
  var agentApiMessageSearchResponseSchema = passthroughObject({
2579
- results: z2.array(agentApiSearchResultSchema),
2580
- hasMore: z2.boolean()
2708
+ results: z3.array(agentApiSearchResultSchema),
2709
+ hasMore: z3.boolean()
2581
2710
  });
2582
2711
  var agentApiChannelMembersResponseSchema = passthroughObject({
2583
2712
  channel: passthroughObject({
2584
- ref: z2.string(),
2585
- type: z2.string()
2713
+ ref: z3.string(),
2714
+ type: z3.string()
2586
2715
  }),
2587
- agents: z2.array(passthroughObject({
2588
- name: z2.string(),
2716
+ agents: z3.array(passthroughObject({
2717
+ name: z3.string(),
2589
2718
  status: optionalStringSchema
2590
2719
  })),
2591
- humans: z2.array(passthroughObject({
2592
- name: z2.string(),
2593
- description: z2.string().nullable().optional(),
2720
+ humans: z3.array(passthroughObject({
2721
+ name: z3.string(),
2722
+ description: z3.string().nullable().optional(),
2594
2723
  role: optionalStringSchema
2595
2724
  }))
2596
2725
  });
@@ -2609,107 +2738,120 @@ var agentApiChannelMuteResponseSchema = passthroughObject({
2609
2738
  catchUp: optionalStringSchema
2610
2739
  }).optional()
2611
2740
  });
2741
+ var agentApiChannelLifecycleResponseBaseSchema = passthroughObject({
2742
+ id: z3.string().trim().min(1).transform(asChannelId),
2743
+ name: z3.string().trim().min(1),
2744
+ type: z3.enum(["channel", "private"]),
2745
+ archivedByUserId: nullableStringSchema.optional(),
2746
+ archivedByAgentId: nullableStringSchema.optional()
2747
+ });
2748
+ var agentApiChannelArchiveResponseSchema = agentApiChannelLifecycleResponseBaseSchema.extend({
2749
+ archivedAt: z3.string().trim().min(1)
2750
+ });
2751
+ var agentApiChannelUnarchiveResponseSchema = agentApiChannelLifecycleResponseBaseSchema.extend({
2752
+ archivedAt: z3.null()
2753
+ });
2612
2754
  var agentApiChannelMuteBodySchema = passthroughObject({
2613
2755
  attentionHintAccepted: passthroughObject({
2614
- schema: z2.literal(ATTENTION_HINT_SCHEMA),
2615
- trigger: z2.enum(["M2", "M3"]),
2616
- scope: z2.string().trim().min(1),
2756
+ schema: z3.literal(ATTENTION_HINT_SCHEMA),
2757
+ trigger: z3.enum(["M2", "M3"]),
2758
+ scope: z3.string().trim().min(1),
2617
2759
  suggested_command: optionalStringSchema,
2618
- copy_version: z2.string().trim().min(1),
2619
- epoch_ms: z2.number().int().nonnegative()
2760
+ copy_version: z3.string().trim().min(1),
2761
+ epoch_ms: z3.number().int().nonnegative()
2620
2762
  }).optional()
2621
2763
  });
2622
2764
  var agentApiTaskClaimResultSchema = passthroughObject({
2623
- taskNumber: z2.number().int().positive().optional(),
2765
+ taskNumber: z3.number().int().positive().optional(),
2624
2766
  messageId: optionalStringSchema,
2625
- success: z2.boolean(),
2767
+ success: z3.boolean(),
2626
2768
  reason: optionalStringSchema
2627
2769
  });
2628
2770
  var agentApiTaskClaimSuccessResponseSchema = passthroughObject({
2629
- results: z2.array(agentApiTaskClaimResultSchema)
2771
+ results: z3.array(agentApiTaskClaimResultSchema)
2630
2772
  });
2631
- var agentApiTaskClaimResponseSchema = z2.union([
2773
+ var agentApiTaskClaimResponseSchema = z3.union([
2632
2774
  agentApiTaskClaimSuccessResponseSchema,
2633
2775
  agentApiHeldFreshnessResponseSchema
2634
2776
  ]);
2635
2777
  var agentApiTaskEnvelopeSchema = passthroughObject({
2636
- taskNumber: z2.number().int().positive().optional(),
2637
- status: z2.string().optional(),
2778
+ taskNumber: z3.number().int().positive().optional(),
2779
+ status: z3.string().optional(),
2638
2780
  title: optionalStringSchema,
2639
- claimedByName: z2.string().nullable().optional(),
2640
- createdByName: z2.string().nullable().optional(),
2641
- messageId: z2.string().nullable().optional(),
2781
+ claimedByName: z3.string().nullable().optional(),
2782
+ createdByName: z3.string().nullable().optional(),
2783
+ messageId: z3.string().nullable().optional(),
2642
2784
  isLegacy: optionalBooleanSchema
2643
2785
  });
2644
2786
  var agentApiTaskListResponseSchema = passthroughObject({
2645
- tasks: z2.array(agentApiTaskEnvelopeSchema)
2787
+ tasks: z3.array(agentApiTaskEnvelopeSchema)
2646
2788
  });
2647
2789
  var agentApiCreatedTaskEnvelopeSchema = passthroughObject({
2648
- taskNumber: z2.number().int().positive(),
2649
- messageId: z2.string(),
2650
- title: z2.string()
2790
+ taskNumber: z3.number().int().positive(),
2791
+ messageId: z3.string(),
2792
+ title: z3.string()
2651
2793
  });
2652
2794
  var agentApiTaskCreateResponseSchema = passthroughObject({
2653
- tasks: z2.array(agentApiCreatedTaskEnvelopeSchema)
2795
+ tasks: z3.array(agentApiCreatedTaskEnvelopeSchema)
2654
2796
  });
2655
2797
  var agentApiTaskUnclaimResponseSchema = passthroughObject({
2656
- ok: z2.literal(true)
2798
+ ok: z3.literal(true)
2657
2799
  });
2658
2800
  var agentApiTaskUpdateStatusSuccessResponseSchema = passthroughObject({
2659
- ok: z2.literal(true)
2801
+ ok: z3.literal(true)
2660
2802
  });
2661
- var agentApiTaskUpdateStatusResponseSchema = z2.union([
2803
+ var agentApiTaskUpdateStatusResponseSchema = z3.union([
2662
2804
  agentApiTaskUpdateStatusSuccessResponseSchema,
2663
2805
  agentApiHeldFreshnessResponseSchema
2664
2806
  ]);
2665
2807
  var agentApiActionPrepareResponseSchema = passthroughObject({
2666
- messageId: z2.string(),
2808
+ messageId: z3.string(),
2667
2809
  metadata: passthroughObject({
2668
- kind: z2.literal("action-card")
2810
+ kind: z3.literal("action-card")
2669
2811
  })
2670
2812
  });
2671
- var agentApiReminderRecurrenceSchema = z2.object({
2672
- kind: z2.enum(["interval", "daily", "weekly", "unsupported"]),
2673
- description: z2.string()
2813
+ var agentApiReminderRecurrenceSchema = z3.object({
2814
+ kind: z3.enum(["interval", "daily", "weekly", "unsupported"]),
2815
+ description: z3.string()
2674
2816
  });
2675
- var agentApiReminderSummarySchema = z2.object({
2676
- reminderId: z2.string(),
2677
- ownerAgentId: z2.string(),
2678
- title: z2.string(),
2679
- fireAt: z2.string(),
2817
+ var agentApiReminderSummarySchema = z3.object({
2818
+ reminderId: z3.string(),
2819
+ ownerAgentId: z3.string(),
2820
+ title: z3.string(),
2821
+ fireAt: z3.string(),
2680
2822
  firedAt: nullableStringSchema.optional(),
2681
- createdAt: z2.string(),
2823
+ createdAt: z3.string(),
2682
2824
  status: reminderStatusSchema,
2683
2825
  msgRef: nullableStringSchema,
2684
2826
  msgPermalink: nullableStringSchema,
2685
2827
  recurrence: agentApiReminderRecurrenceSchema.nullable()
2686
2828
  });
2687
- var agentApiReminderEventSummarySchema = z2.object({
2688
- eventId: z2.string(),
2689
- reminderId: z2.string(),
2829
+ var agentApiReminderEventSummarySchema = z3.object({
2830
+ eventId: z3.string(),
2831
+ reminderId: z3.string(),
2690
2832
  eventType: reminderEventTypeSchema,
2691
- actorType: z2.enum(["agent", "human", "system"]),
2833
+ actorType: z3.enum(["agent", "human", "system"]),
2692
2834
  actorId: nullableStringSchema,
2693
- occurredAt: z2.string(),
2835
+ occurredAt: z3.string(),
2694
2836
  nextFireAt: nullableStringSchema,
2695
- metadata: z2.record(z2.string(), z2.unknown()).nullable()
2837
+ metadata: z3.record(z3.string(), z3.unknown()).nullable()
2696
2838
  });
2697
2839
  var agentApiReminderListResponseSchema = passthroughObject({
2698
- reminders: z2.array(agentApiReminderSummarySchema)
2840
+ reminders: z3.array(agentApiReminderSummarySchema)
2699
2841
  });
2700
2842
  var agentApiReminderResponseSchema = passthroughObject({
2701
2843
  reminder: agentApiReminderSummarySchema,
2702
2844
  warning: optionalStringSchema
2703
2845
  });
2704
2846
  var agentApiReminderLogResponseSchema = passthroughObject({
2705
- events: z2.array(agentApiReminderEventSummarySchema)
2847
+ events: z3.array(agentApiReminderEventSummarySchema)
2706
2848
  });
2707
- var agentApiMigrationStateSchema = z2.enum(["provisioning", "prep", "ready", "in_transit", "arriving", "completed", "aborted", "failed"]);
2849
+ var agentApiMigrationStateSchema = z3.enum(["provisioning", "prep", "ready", "in_transit", "arriving", "completed", "aborted", "failed"]);
2708
2850
  var agentApiMigrationSummarySchema = passthroughObject({
2709
- id: z2.string(),
2710
- agentId: z2.string(),
2711
- sourceMachineId: z2.string(),
2712
- targetMachineId: z2.string(),
2851
+ id: z3.string(),
2852
+ agentId: z3.string(),
2853
+ sourceMachineId: z3.string(),
2854
+ targetMachineId: z3.string(),
2713
2855
  state: agentApiMigrationStateSchema,
2714
2856
  manifestPath: nullableStringSchema,
2715
2857
  manifestSha256: nullableStringSchema,
@@ -2717,26 +2859,26 @@ var agentApiMigrationSummarySchema = passthroughObject({
2717
2859
  arrivalReportSha256: nullableStringSchema,
2718
2860
  abortReason: nullableStringSchema,
2719
2861
  failureReason: nullableStringSchema,
2720
- prepDeadlineAt: z2.string().datetime(),
2721
- transferDeadlineAt: z2.string().datetime(),
2722
- arrivalDeadlineAt: z2.string().datetime(),
2862
+ prepDeadlineAt: z3.string().datetime(),
2863
+ transferDeadlineAt: z3.string().datetime(),
2864
+ arrivalDeadlineAt: z3.string().datetime(),
2723
2865
  readyAt: nullableStringSchema,
2724
2866
  flippedAt: nullableStringSchema,
2725
2867
  arrivedAt: nullableStringSchema,
2726
2868
  completedAt: nullableStringSchema,
2727
2869
  abortedAt: nullableStringSchema,
2728
- revision: z2.number().int().positive(),
2729
- createdAt: z2.string().datetime(),
2730
- updatedAt: z2.string().datetime()
2870
+ revision: z3.number().int().positive(),
2871
+ createdAt: z3.string().datetime(),
2872
+ updatedAt: z3.string().datetime()
2731
2873
  });
2732
2874
  var agentApiMigrationBeginBodySchema = passthroughObject({
2733
- targetMachineId: z2.string().trim().min(1),
2734
- prepDeadlineMs: z2.number().int().positive().optional(),
2735
- transferDeadlineMs: z2.number().int().positive().optional(),
2736
- arrivalDeadlineMs: z2.number().int().positive().optional()
2875
+ targetMachineId: z3.string().trim().min(1),
2876
+ prepDeadlineMs: z3.number().int().positive().optional(),
2877
+ transferDeadlineMs: z3.number().int().positive().optional(),
2878
+ arrivalDeadlineMs: z3.number().int().positive().optional()
2737
2879
  });
2738
2880
  var agentApiMigrationReadyBodySchema = passthroughObject({
2739
- manifestPath: z2.string().trim().min(1),
2881
+ manifestPath: z3.string().trim().min(1),
2740
2882
  manifestSha256: optionalStringSchema
2741
2883
  });
2742
2884
  var agentApiMigrationArrivedBodySchema = passthroughObject({
@@ -2886,6 +3028,26 @@ var agentApiContract = {
2886
3028
  request: { params: agentApiChannelMembershipParamsSchema },
2887
3029
  response: { body: agentApiChannelMuteResponseSchema }
2888
3030
  }),
3031
+ channelArchive: route({
3032
+ key: "channelArchive",
3033
+ method: "POST",
3034
+ path: "/channels/archive",
3035
+ client: { resource: "channels", method: "archive" },
3036
+ capability: "channels",
3037
+ description: "Archive a regular channel when the bound agent has server channel-management authority.",
3038
+ request: { body: agentApiChannelLifecycleBodySchema },
3039
+ response: { body: agentApiChannelArchiveResponseSchema }
3040
+ }),
3041
+ channelUnarchive: route({
3042
+ key: "channelUnarchive",
3043
+ method: "POST",
3044
+ path: "/channels/unarchive",
3045
+ client: { resource: "channels", method: "unarchive" },
3046
+ capability: "channels",
3047
+ description: "Unarchive a regular channel when the bound agent has server channel-management authority.",
3048
+ request: { body: agentApiChannelLifecycleBodySchema },
3049
+ response: { body: agentApiChannelUnarchiveResponseSchema }
3050
+ }),
2889
3051
  channelMembers: route({
2890
3052
  key: "channelMembers",
2891
3053
  method: "GET",
@@ -3215,47 +3377,47 @@ var agentApiContract = {
3215
3377
  };
3216
3378
 
3217
3379
  // ../shared/src/daemonApiContract.ts
3218
- import { z as z3 } from "zod";
3380
+ import { z as z4 } from "zod";
3219
3381
  var DAEMON_API_BASE_PATH = "/internal/agent-api";
3220
- var optionalStringSchema2 = z3.string().trim().optional();
3221
- var optionalNonNegativeIntSchema = z3.number().int().nonnegative().optional();
3222
- var optionalQueryIntSchema = z3.union([z3.number().int().nonnegative(), z3.string().trim().min(1)]).optional();
3223
- var nullableNumberSchema2 = z3.number().finite().nullable();
3224
- var passthroughObject2 = (shape) => z3.object(shape).passthrough();
3225
- var daemonApiInboxFlagSchema = z3.enum(["mention", "thread", "dm", "task"]);
3382
+ var optionalStringSchema2 = z4.string().trim().optional();
3383
+ var optionalNonNegativeIntSchema = z4.number().int().nonnegative().optional();
3384
+ var optionalQueryIntSchema = z4.union([z4.number().int().nonnegative(), z4.string().trim().min(1)]).optional();
3385
+ var nullableNumberSchema2 = z4.number().finite().nullable();
3386
+ var passthroughObject2 = (shape) => z4.object(shape).passthrough();
3387
+ var daemonApiInboxFlagSchema = z4.enum(["mention", "thread", "dm", "task"]);
3226
3388
  var daemonApiAttentionHintSchema = passthroughObject2({
3227
- schema: z3.literal(ATTENTION_HINT_SCHEMA),
3228
- trigger: z3.enum(["M2", "M3"]),
3229
- scope: z3.string().trim().min(1),
3230
- suggested_command: z3.string().trim().min(1),
3231
- copy: z3.string().trim().min(1),
3232
- copy_version: z3.literal("attention-hint-copy-v1"),
3233
- epoch_ms: z3.number().int().nonnegative(),
3389
+ schema: z4.literal(ATTENTION_HINT_SCHEMA),
3390
+ trigger: z4.enum(["M2", "M3"]),
3391
+ scope: z4.string().trim().min(1),
3392
+ suggested_command: z4.string().trim().min(1),
3393
+ copy: z4.string().trim().min(1),
3394
+ copy_version: z4.literal("attention-hint-copy-v1"),
3395
+ epoch_ms: z4.number().int().nonnegative(),
3234
3396
  thresholds: passthroughObject2({
3235
3397
  K: optionalNonNegativeIntSchema,
3236
3398
  k: optionalNonNegativeIntSchema,
3237
- window_ms: z3.number().int().positive()
3399
+ window_ms: z4.number().int().positive()
3238
3400
  })
3239
3401
  });
3240
3402
  var daemonApiInboxTargetRowSchema = passthroughObject2({
3241
- target: z3.string().trim().min(1),
3403
+ target: z4.string().trim().min(1),
3242
3404
  channelId: optionalStringSchema2,
3243
3405
  channelType: optionalStringSchema2,
3244
- pendingCount: z3.number().int().nonnegative(),
3406
+ pendingCount: z4.number().int().nonnegative(),
3245
3407
  firstPendingMsgId: optionalStringSchema2,
3246
3408
  firstPendingSeq: optionalNonNegativeIntSchema,
3247
3409
  latestMsgId: optionalStringSchema2,
3248
3410
  latestSeq: optionalNonNegativeIntSchema,
3249
3411
  latestSenderName: optionalStringSchema2,
3250
- latestSenderType: z3.enum(["human", "agent", "system", "third_party_app"]).optional(),
3251
- flags: z3.array(daemonApiInboxFlagSchema),
3412
+ latestSenderType: z4.enum(["human", "agent", "system", "third_party_app"]).optional(),
3413
+ flags: z4.array(daemonApiInboxFlagSchema),
3252
3414
  attentionHint: daemonApiAttentionHintSchema.optional()
3253
3415
  });
3254
3416
  var daemonApiInboxCheckResponseSchema = passthroughObject2({
3255
- rows: z3.array(daemonApiInboxTargetRowSchema).optional()
3417
+ rows: z4.array(daemonApiInboxTargetRowSchema).optional()
3256
3418
  });
3257
3419
  var daemonApiWakeHintsQuerySchema = passthroughObject2({
3258
- since: z3.union([z3.literal("latest"), z3.number().int().nonnegative(), z3.string().trim().min(1)]).optional(),
3420
+ since: z4.union([z4.literal("latest"), z4.number().int().nonnegative(), z4.string().trim().min(1)]).optional(),
3259
3421
  limit: optionalQueryIntSchema
3260
3422
  });
3261
3423
  var daemonApiWakeHintSchema = passthroughObject2({
@@ -3263,8 +3425,8 @@ var daemonApiWakeHintSchema = passthroughObject2({
3263
3425
  hint_id: optionalStringSchema2,
3264
3426
  eventId: optionalStringSchema2,
3265
3427
  event_id: optionalStringSchema2,
3266
- messageId: z3.string().nullable().optional(),
3267
- message_id: z3.string().nullable().optional(),
3428
+ messageId: z4.string().nullable().optional(),
3429
+ message_id: z4.string().nullable().optional(),
3268
3430
  seq: optionalNonNegativeIntSchema,
3269
3431
  id: optionalStringSchema2,
3270
3432
  target: optionalStringSchema2,
@@ -3277,27 +3439,27 @@ var daemonApiWakeHintSchema = passthroughObject2({
3277
3439
  created_at: optionalStringSchema2
3278
3440
  });
3279
3441
  var daemonApiWakeHintsFetchResponseSchema = passthroughObject2({
3280
- hints: z3.array(daemonApiWakeHintSchema).optional(),
3281
- wake_hints: z3.array(daemonApiWakeHintSchema).optional(),
3442
+ hints: z4.array(daemonApiWakeHintSchema).optional(),
3443
+ wake_hints: z4.array(daemonApiWakeHintSchema).optional(),
3282
3444
  last_seen_hint_seq: nullableNumberSchema2.optional(),
3283
3445
  last_hint_seq: nullableNumberSchema2.optional(),
3284
- has_more: z3.boolean().optional()
3446
+ has_more: z4.boolean().optional()
3285
3447
  });
3286
3448
  var daemonApiActivityEventSchema = passthroughObject2({
3287
3449
  schema: optionalStringSchema2
3288
3450
  });
3289
3451
  var daemonApiActivityForwardBodySchema = passthroughObject2({
3290
- schema: z3.literal("raft-agent-activity-ingest.v1"),
3452
+ schema: z4.literal("raft-agent-activity-ingest.v1"),
3291
3453
  coreSessionId: optionalStringSchema2,
3292
3454
  adapterInstance: optionalStringSchema2,
3293
- events: z3.array(daemonApiActivityEventSchema),
3455
+ events: z4.array(daemonApiActivityEventSchema),
3294
3456
  dropped: optionalNonNegativeIntSchema
3295
3457
  });
3296
3458
  var daemonApiActivityForwardResponseSchema = passthroughObject2({
3297
- ok: z3.literal(true).optional(),
3298
- acceptedCount: z3.number().int().nonnegative().optional(),
3299
- rejectedCount: z3.number().int().nonnegative().optional(),
3300
- droppedCount: z3.number().int().nonnegative().optional()
3459
+ ok: z4.literal(true).optional(),
3460
+ acceptedCount: z4.number().int().nonnegative().optional(),
3461
+ rejectedCount: z4.number().int().nonnegative().optional(),
3462
+ droppedCount: z4.number().int().nonnegative().optional()
3301
3463
  });
3302
3464
  function route2(input) {
3303
3465
  return {
@@ -3391,7 +3553,7 @@ function formatAttentionHintField(hint) {
3391
3553
  }
3392
3554
 
3393
3555
  // ../shared/src/externalAgentIntegration.ts
3394
- import { z as z4 } from "zod";
3556
+ import { z as z5 } from "zod";
3395
3557
  var EXTERNAL_AGENT_COMMS_PROTOCOL_VERSION = "agent-comms-core.v1";
3396
3558
  var EXTERNAL_AGENT_PROOF_SCHEMA_VERSION = "agent-proof.v1";
3397
3559
  var EXTERNAL_RUNTIME_INTEGRATION_MANIFEST_SCHEMA = "slock-external-runtime-integration.v1";
@@ -3435,35 +3597,35 @@ var externalAgentAdapterFailureValues = [
3435
3597
  "auth_revoked"
3436
3598
  ];
3437
3599
  var externalAgentServerApiModeValues = ["interim-agent-api-events", "agent-inbox-protocol"];
3438
- var nonEmptyStringSchema = z4.string().min(1);
3439
- var isoTimestampSchema = z4.string().refine((value) => !Number.isNaN(Date.parse(value)), {
3600
+ var nonEmptyStringSchema = z5.string().min(1);
3601
+ var isoTimestampSchema = z5.string().refine((value) => !Number.isNaN(Date.parse(value)), {
3440
3602
  message: "must be a parseable timestamp"
3441
3603
  });
3442
- var externalRuntimeIntegrationManifestSchema = z4.object({
3443
- schema: z4.literal(EXTERNAL_RUNTIME_INTEGRATION_MANIFEST_SCHEMA),
3604
+ var externalRuntimeIntegrationManifestSchema = z5.object({
3605
+ schema: z5.literal(EXTERNAL_RUNTIME_INTEGRATION_MANIFEST_SCHEMA),
3444
3606
  runtimeId: nonEmptyStringSchema,
3445
- integrationPattern: z4.enum(externalAgentIntegrationPatternValues),
3446
- commsMode: z4.enum(externalAgentCommsModeValues),
3447
- commsProtocolVersion: z4.literal(EXTERNAL_AGENT_COMMS_PROTOCOL_VERSION),
3448
- proofSchemaVersion: z4.literal(EXTERNAL_AGENT_PROOF_SCHEMA_VERSION),
3607
+ integrationPattern: z5.enum(externalAgentIntegrationPatternValues),
3608
+ commsMode: z5.enum(externalAgentCommsModeValues),
3609
+ commsProtocolVersion: z5.literal(EXTERNAL_AGENT_COMMS_PROTOCOL_VERSION),
3610
+ proofSchemaVersion: z5.literal(EXTERNAL_AGENT_PROOF_SCHEMA_VERSION),
3449
3611
  minSlockCliVersion: nonEmptyStringSchema,
3450
- multiplex: z4.boolean(),
3451
- agentIsolation: z4.enum(externalAgentIsolationValues),
3452
- bridgeLifecycle: z4.object({
3453
- explicitStartOnly: z4.literal(true),
3454
- oneShotCommandsBridgeIndependent: z4.literal(true),
3455
- requiresBridgeFailureCodes: z4.array(z4.enum(["BRIDGE_NOT_RUNNING", "NO_CORE_SESSION"])).min(1),
3456
- autoStartDefault: z4.literal(false)
3612
+ multiplex: z5.boolean(),
3613
+ agentIsolation: z5.enum(externalAgentIsolationValues),
3614
+ bridgeLifecycle: z5.object({
3615
+ explicitStartOnly: z5.literal(true),
3616
+ oneShotCommandsBridgeIndependent: z5.literal(true),
3617
+ requiresBridgeFailureCodes: z5.array(z5.enum(["BRIDGE_NOT_RUNNING", "NO_CORE_SESSION"])).min(1),
3618
+ autoStartDefault: z5.literal(false)
3457
3619
  }).strict(),
3458
- serverApi: z4.object({
3459
- mode: z4.enum(externalAgentServerApiModeValues),
3460
- deliveryOnly: z4.boolean(),
3461
- cursorAuthority: z4.literal("model_seen_only")
3620
+ serverApi: z5.object({
3621
+ mode: z5.enum(externalAgentServerApiModeValues),
3622
+ deliveryOnly: z5.boolean(),
3623
+ cursorAuthority: z5.literal("model_seen_only")
3462
3624
  }).strict(),
3463
- wakeAdapter: z4.object({
3464
- kind: z4.enum(externalAgentWakeAdapterKindValues),
3625
+ wakeAdapter: z5.object({
3626
+ kind: z5.enum(externalAgentWakeAdapterKindValues),
3465
3627
  protocol: nonEmptyStringSchema,
3466
- requiresInteractiveSession: z4.boolean().optional()
3628
+ requiresInteractiveSession: z5.boolean().optional()
3467
3629
  }).strict()
3468
3630
  }).strict().superRefine((value, ctx) => {
3469
3631
  if (!value.bridgeLifecycle.requiresBridgeFailureCodes.includes("BRIDGE_NOT_RUNNING")) {
@@ -3488,8 +3650,8 @@ var externalRuntimeIntegrationManifestSchema = z4.object({
3488
3650
  });
3489
3651
  }
3490
3652
  });
3491
- var externalAgentWakeEventBaseSchema = z4.object({
3492
- schema: z4.literal(EXTERNAL_AGENT_WAKE_EVENT_SCHEMA),
3653
+ var externalAgentWakeEventBaseSchema = z5.object({
3654
+ schema: z5.literal(EXTERNAL_AGENT_WAKE_EVENT_SCHEMA),
3493
3655
  eventId: nonEmptyStringSchema,
3494
3656
  attemptId: nonEmptyStringSchema,
3495
3657
  messageId: nonEmptyStringSchema,
@@ -3499,30 +3661,30 @@ var externalAgentWakeEventBaseSchema = z4.object({
3499
3661
  adapterInstance: nonEmptyStringSchema,
3500
3662
  runtimeSession: nonEmptyStringSchema.nullable(),
3501
3663
  occurredAt: isoTimestampSchema,
3502
- lifecycleState: z4.enum(externalAgentCommsLifecycleStateValues),
3503
- authority: z4.object({
3504
- source: z4.enum(externalAgentLifecycleSourceValues),
3505
- provenance: z4.enum(externalAgentLifecycleProvenanceValues)
3664
+ lifecycleState: z5.enum(externalAgentCommsLifecycleStateValues),
3665
+ authority: z5.object({
3666
+ source: z5.enum(externalAgentLifecycleSourceValues),
3667
+ provenance: z5.enum(externalAgentLifecycleProvenanceValues)
3506
3668
  }).strict()
3507
3669
  }).strict();
3508
3670
  var externalAgentProofEventEnvelopeSchema = externalAgentWakeEventBaseSchema.extend({
3509
- kind: z4.literal("proof"),
3510
- proofLevel: z4.enum(externalAgentWakeProofLevelValues),
3511
- outcome: z4.literal("ok"),
3512
- failureMeta: z4.undefined().optional(),
3513
- reason: z4.string().optional()
3671
+ kind: z5.literal("proof"),
3672
+ proofLevel: z5.enum(externalAgentWakeProofLevelValues),
3673
+ outcome: z5.literal("ok"),
3674
+ failureMeta: z5.undefined().optional(),
3675
+ reason: z5.string().optional()
3514
3676
  });
3515
3677
  var externalAgentFailedWakeEventEnvelopeSchema = externalAgentWakeEventBaseSchema.extend({
3516
- kind: z4.literal("wake_attempt"),
3517
- proofLevel: z4.undefined().optional(),
3518
- outcome: z4.literal("failed"),
3519
- failureMeta: z4.object({
3520
- failureClass: z4.enum(externalAgentAdapterFailureValues),
3521
- retryAfterMs: z4.number().int().positive().optional()
3678
+ kind: z5.literal("wake_attempt"),
3679
+ proofLevel: z5.undefined().optional(),
3680
+ outcome: z5.literal("failed"),
3681
+ failureMeta: z5.object({
3682
+ failureClass: z5.enum(externalAgentAdapterFailureValues),
3683
+ retryAfterMs: z5.number().int().positive().optional()
3522
3684
  }).strict(),
3523
3685
  reason: nonEmptyStringSchema
3524
3686
  });
3525
- var externalAgentWakeEventEnvelopeSchema = z4.discriminatedUnion("kind", [
3687
+ var externalAgentWakeEventEnvelopeSchema = z5.discriminatedUnion("kind", [
3526
3688
  externalAgentProofEventEnvelopeSchema,
3527
3689
  externalAgentFailedWakeEventEnvelopeSchema
3528
3690
  ]);
@@ -3658,7 +3820,137 @@ var SERVER_CAPABILITY_MATRIX = {
3658
3820
  })
3659
3821
  };
3660
3822
 
3823
+ // ../shared/src/canonicalMessageManifest.ts
3824
+ var CANONICAL_MESSAGE_MANIFEST_VERSION = 4;
3825
+ var present = { messageNew: "present", enrichedUpdated: "present", taskStatusUpdated: "present" };
3826
+ var enrichedOnly = { messageNew: "present", enrichedUpdated: "present", taskStatusUpdated: "absent" };
3827
+ var newOnly = { messageNew: "present", enrichedUpdated: "absent", taskStatusUpdated: "absent" };
3828
+ var CANONICAL_MESSAGE_FIELD_DESCRIPTORS = Object.freeze([
3829
+ // —— canonicalRequired (fail-closed; resolved rows use non-null types for
3830
+ // id/channelId/senderType/senderId/content/createdAt) ——
3831
+ { name: "channelId", class: "canonicalRequired", wireType: "string", nullable: false, mergePolicy: "overwrite", presence: present },
3832
+ { name: "content", class: "canonicalRequired", wireType: "string", nullable: false, mergePolicy: "overwrite", presence: present },
3833
+ { name: "createdAt", class: "canonicalRequired", wireType: "string", nullable: false, mergePolicy: "overwrite", presence: present },
3834
+ { name: "id", class: "canonicalRequired", wireType: "string", nullable: false, mergePolicy: "overwrite", presence: present },
3835
+ { name: "messageType", class: "canonicalRequired", wireType: "string-union-raw", nullable: false, mergePolicy: "overwrite", presence: present },
3836
+ { name: "randomId", class: "canonicalRequired", wireType: "string", nullable: true, mergePolicy: "overwrite", presence: present },
3837
+ { name: "senderId", class: "canonicalRequired", wireType: "string", nullable: false, mergePolicy: "overwrite", presence: present },
3838
+ { name: "senderType", class: "canonicalRequired", wireType: "string-union-raw", nullable: false, mergePolicy: "overwrite", presence: present },
3839
+ { name: "seq", class: "canonicalRequired", wireType: "number", nullable: false, mergePolicy: "overwrite", presence: present },
3840
+ { name: "threadId", class: "canonicalRequired", wireType: "string", nullable: true, mergePolicy: "overwrite", presence: present },
3841
+ // —— optionalAggregate (explicit presence; absent=preserve, present=overwrite) ——
3842
+ { name: "actionMetadata", class: "optionalAggregate", wireType: "structured-json", nullable: true, mergePolicy: "present-overwrite", presence: present },
3843
+ { name: "attachments", class: "optionalAggregate", wireType: "array<attachment>", nullable: false, mergePolicy: "present-overwrite", presence: enrichedOnly },
3844
+ { name: "commentRef", class: "optionalAggregate", wireType: "object<commentRef>", nullable: true, mergePolicy: "shared-null-preserve", presence: enrichedOnly },
3845
+ { name: "conversationContext", class: "optionalAggregate", wireType: "object<conversationContext>", nullable: false, mergePolicy: "present-overwrite", presence: newOnly },
3846
+ { name: "mentions", class: "optionalAggregate", wireType: "array<mention>", nullable: false, mergePolicy: "present-overwrite", presence: enrichedOnly },
3847
+ { name: "reactions", class: "optionalAggregate", wireType: "array<reaction>", nullable: false, mergePolicy: "present-overwrite", presence: enrichedOnly },
3848
+ { name: "senderDescription", class: "optionalAggregate", wireType: "string", nullable: true, mergePolicy: "present-overwrite", presence: enrichedOnly },
3849
+ { name: "senderMembershipStatus", class: "optionalAggregate", wireType: "string-union-raw", nullable: true, mergePolicy: "present-overwrite", presence: enrichedOnly },
3850
+ { name: "senderName", class: "optionalAggregate", wireType: "string", nullable: false, mergePolicy: "present-overwrite", presence: present }
3851
+ ]);
3852
+ function nestedShape(fields) {
3853
+ return Object.freeze(fields);
3854
+ }
3855
+ var CANONICAL_NESTED_WIRE_SHAPES = Object.freeze({
3856
+ attachment: nestedShape([
3857
+ // commentCount is viewer-scoped (shared strip forces 0) — excluded from the
3858
+ // canonical shared attachment fact; see viewerScopedFields.
3859
+ { name: "filename", wireType: "string", nullable: false },
3860
+ { name: "height", wireType: "number", nullable: true },
3861
+ { name: "id", wireType: "string", nullable: false },
3862
+ { name: "mimeType", wireType: "string", nullable: false },
3863
+ { name: "sizeBytes", wireType: "number", nullable: false },
3864
+ { name: "thumbnailUrl", wireType: "string", nullable: true },
3865
+ { name: "width", wireType: "number", nullable: true }
3866
+ ]),
3867
+ reaction: nestedShape([
3868
+ { name: "count", wireType: "number", nullable: false },
3869
+ { name: "emoji", wireType: "string", nullable: false },
3870
+ { name: "reactorIds", wireType: "array<string>", nullable: false },
3871
+ { name: "reactorNames", wireType: "array<string>", nullable: false }
3872
+ ]),
3873
+ mention: nestedShape([
3874
+ { name: "id", wireType: "string", nullable: false },
3875
+ { name: "name", wireType: "string", nullable: false },
3876
+ { name: "type", wireType: "string-union-raw", nullable: false }
3877
+ ]),
3878
+ commentRef: nestedShape([
3879
+ { name: "anchorLabel", wireType: "string", nullable: true },
3880
+ { name: "anchorQuote", wireType: "string", nullable: true },
3881
+ { name: "attachmentId", wireType: "string", nullable: false },
3882
+ { name: "filename", wireType: "string", nullable: false },
3883
+ { name: "hostMessageId", wireType: "string", nullable: true },
3884
+ { name: "hostSource", wireType: "object<hostSource>", nullable: true }
3885
+ ]),
3886
+ commentRefHostSource: nestedShape([
3887
+ { name: "channelId", wireType: "string", nullable: false },
3888
+ { name: "parentMessageId", wireType: "string", nullable: false, optionalKey: true },
3889
+ { name: "rootThreadChannelId", wireType: "string", nullable: false, optionalKey: true },
3890
+ { name: "routeKind", wireType: "string-union-raw", nullable: false },
3891
+ { name: "threadChannelId", wireType: "string", nullable: false, optionalKey: true },
3892
+ { name: "type", wireType: "string-union-raw", nullable: false }
3893
+ ]),
3894
+ conversationContext: nestedShape([
3895
+ { name: "channelType", wireType: "string-union-raw", nullable: false },
3896
+ { name: "parentChannelId", wireType: "string", nullable: false, optionalKey: true },
3897
+ { name: "parentChannelType", wireType: "string-union-raw", nullable: false, optionalKey: true },
3898
+ { name: "parentMessageId", wireType: "string", nullable: false, optionalKey: true }
3899
+ ])
3900
+ });
3901
+ var CANONICAL_REQUIRED_MESSAGE_FIELDS = Object.freeze(
3902
+ CANONICAL_MESSAGE_FIELD_DESCRIPTORS.filter((d) => d.class === "canonicalRequired").map((d) => d.name)
3903
+ );
3904
+ var OPTIONAL_AGGREGATE_MESSAGE_FIELDS = Object.freeze(
3905
+ CANONICAL_MESSAGE_FIELD_DESCRIPTORS.filter((d) => d.class === "optionalAggregate").map((d) => d.name)
3906
+ );
3907
+ var TASK_STATUS_FAMILY_PRESENT_AGGREGATES = Object.freeze(
3908
+ CANONICAL_MESSAGE_FIELD_DESCRIPTORS.filter((d) => d.class === "optionalAggregate" && d.presence.taskStatusUpdated === "present").map((d) => d.name)
3909
+ );
3910
+ var EXCLUDED_CLIENT_ONLY_MESSAGE_FIELDS = Object.freeze(["optimisticDisplaySeq"]);
3911
+ var CANONICAL_MESSAGE_EXCLUSIONS = Object.freeze({
3912
+ /** task-domain projection riding the message carrier: authority=task,
3913
+ * applyTarget=task-domain, messageFold=excluded. Fan out to the task
3914
+ * consumer at ingress; message fold never applies these. */
3915
+ taskDomainProjection: Object.freeze({
3916
+ fields: ["taskAssigneeId", "taskAssigneeType", "taskClaimedAt", "taskCompletedAt", "taskNumber", "taskStatus"],
3917
+ migrationStatus: "active-consumers (web taskStore / KMP task projection); dual-dispatch at ingress"
3918
+ }),
3919
+ /** Emitted but consumed by no canonical client surface. */
3920
+ emittedUnconsumed: Object.freeze({
3921
+ fields: ["updatedAt"],
3922
+ migrationStatus: "web canonical zero-consumption; mobile legacy consumption to retire in round-2 (label/event-key/SQL cache -> (epoch,seq,id/revision) adjudication)"
3923
+ }),
3924
+ /** Viewer-scoped nested metadata: shared broadcasts strip these; truth comes
3925
+ * only from actor-scoped HTTP / receiver-private surfaces. */
3926
+ viewerScopedFields: Object.freeze({
3927
+ fields: ["attachment.commentCount"],
3928
+ migrationStatus: "overlay-domain data; never apply shared-stripped values to canonical or overlay state"
3929
+ }),
3930
+ /** Client-local optimistic coordinates, never server facts. */
3931
+ clientOnly: Object.freeze({
3932
+ fields: ["optimisticDisplaySeq"],
3933
+ migrationStatus: "n/a (never on wire)"
3934
+ }),
3935
+ /** Storage/idempotency/search-only DB columns. Sealed at the socket boundary
3936
+ * by projectRichMessageSocketPayload (slock#4593, merged b0fcdfd9). Never on
3937
+ * any post-projection wire frame. */
3938
+ storageOnlySealed: Object.freeze({
3939
+ fields: ["agentSendKey", "searchText", "searchVector"],
3940
+ migrationStatus: "sealed server-side; G6 registry gate enforces post-projection shape"
3941
+ })
3942
+ });
3943
+ var CANONICAL_MESSAGE_MANIFEST = Object.freeze({
3944
+ version: CANONICAL_MESSAGE_MANIFEST_VERSION,
3945
+ producerRegistryAnchor: "slock#4593@b0fcdfd9fae9f0af9b32a87a1d5c3e196d3fdaa1",
3946
+ fields: CANONICAL_MESSAGE_FIELD_DESCRIPTORS,
3947
+ nestedWireShapes: CANONICAL_NESTED_WIRE_SHAPES,
3948
+ exclusions: CANONICAL_MESSAGE_EXCLUSIONS,
3949
+ excludedClientOnly: EXCLUDED_CLIENT_ONLY_MESSAGE_FIELDS
3950
+ });
3951
+
3661
3952
  // ../shared/src/index.ts
3953
+ var COMPUTER_CAPABILITY_SUPERVISOR_MUTATIONS = "computer:supervisor-mutations-v1";
3662
3954
  var RUNTIME_CONFIG_VERSION = 1;
3663
3955
  var BUILTIN_RUNTIME_PROVIDER_ENV_KEYS = PI_BUILTIN_PROVIDER_API_KEY_ENV_KEYS_GENERATED;
3664
3956
  var BUILTIN_RUNTIME_PROVIDERS = Object.entries(BUILTIN_RUNTIME_PROVIDER_ENV_KEYS).map(([id, envKey]) => ({ id, envKey }));
@@ -3710,6 +4002,10 @@ var AGENT_ACTIVITY_DETAIL_KINDS = [
3710
4002
  "ready",
3711
4003
  "runtime_interrupted",
3712
4004
  "machine_disconnected",
4005
+ "computer_started",
4006
+ "computer_restarted",
4007
+ "computer_upgraded",
4008
+ "computer_operation_failed",
3713
4009
  "daemon_activity",
3714
4010
  "external_activity",
3715
4011
  "synthetic_repair",
@@ -4600,7 +4896,7 @@ Use the \`raft\` CLI for chat / task / attachment operations (\`slock\` remains
4600
4896
  1. **Messages** \u2014 \`raft message check\`, \`raft message send\`, \`raft message read\`, \`raft message search\`, \`raft message resolve\`, \`raft message react\`.
4601
4897
  2. **Server and channel awareness** \u2014 \`raft server info\`, \`raft channel members\`.
4602
4898
  3. **Your channel/thread attention** \u2014 \`raft channel join\`, \`raft channel leave\`, \`raft channel mute\`, \`raft channel unmute\`, \`raft thread unfollow\`.
4603
- 4. **Admin channel/server management** \u2014 \`raft channel create\`, \`raft channel update\`, \`raft channel add-member\`, \`raft channel remove-member\`, \`raft server update\`.
4899
+ 4. **Admin channel/server management** \u2014 \`raft channel create\`, \`raft channel update\`, \`raft channel archive\`, \`raft channel unarchive\`, \`raft channel add-member\`, \`raft channel remove-member\`, \`raft server update\`.
4604
4900
  5. **Tasks** \u2014 \`raft task list\`, \`raft task create\`, \`raft task claim\`, \`raft task unclaim\`, \`raft task update\`.
4605
4901
  6. **Attachments** \u2014 \`raft attachment upload\`, \`raft attachment view\`.
4606
4902
  7. **Profiles** \u2014 \`raft profile show\`, \`raft profile update\`.
@@ -5143,6 +5439,15 @@ function listLegacySlockStatePaths(slockHome = resolveSlockHome(), homeDir = os.
5143
5439
  return candidates.filter((candidate) => existsSync(candidate.path));
5144
5440
  }
5145
5441
 
5442
+ // src/authEnv.ts
5443
+ var DAEMON_API_KEY_ENV = "SLOCK_MACHINE_API_KEY";
5444
+ var SLOCK_AGENT_TOKEN_ENV = "SLOCK_AGENT_TOKEN";
5445
+ function scrubDaemonChildEnv(env) {
5446
+ delete env[DAEMON_API_KEY_ENV];
5447
+ delete env[SLOCK_AGENT_TOKEN_ENV];
5448
+ return env;
5449
+ }
5450
+
5146
5451
  // src/agentCredentialProxy.ts
5147
5452
  import { randomBytes } from "crypto";
5148
5453
  import http from "http";
@@ -6211,6 +6516,7 @@ async function handleProxyRequest(req, res) {
6211
6516
  return;
6212
6517
  }
6213
6518
  const method = req.method ?? "GET";
6519
+ const correlationId = randomBytes(8).toString("hex");
6214
6520
  let target;
6215
6521
  try {
6216
6522
  target = new URL2(req.url ?? "/", registration.serverUrl);
@@ -6279,9 +6585,11 @@ async function handleProxyRequest(req, res) {
6279
6585
  body
6280
6586
  });
6281
6587
  if (upstream.status >= 500) {
6282
- registration.inboxCoordinator?.recordTransportNormalizedError?.(
6283
- transportNormalizedErrorForHttpStatus(target, upstream.status, registration.launchId)
6588
+ const transportError = transportNormalizedErrorForHttpStatus(target, upstream.status, registration.launchId);
6589
+ logger.warn(
6590
+ `[Agent Credential Proxy] upstream returned HTTP ${upstream.status} (agent=${registration.agentId}, launch=${registration.launchId ?? "none"}, correlation=${correlationId}, method=${method}, path=${target.pathname}, route_family=${transportError.routeFamily}, target_host_class=${transportError.targetHostClass})`
6284
6591
  );
6592
+ registration.inboxCoordinator?.recordTransportNormalizedError?.(transportError);
6285
6593
  }
6286
6594
  if (shouldBufferJsonResponse(upstream, target.pathname, registration)) {
6287
6595
  const responseText = await upstream.text();
@@ -6303,14 +6611,16 @@ async function handleProxyRequest(req, res) {
6303
6611
  res.end();
6304
6612
  }
6305
6613
  } catch (err) {
6306
- const failure = proxyFailureForError(method, target, err);
6614
+ const transportError = transportNormalizedErrorForError(target, err, registration.launchId);
6615
+ const failure = proxyFailureForError(method, target, err, {
6616
+ correlationId,
6617
+ transportError
6618
+ });
6307
6619
  logger.warn(
6308
- `[Agent Credential Proxy] request failed (agent=${registration.agentId}, launch=${registration.launchId ?? "none"}, method=${failure.method}, path=${failure.pathname}, query_keys=${failure.queryKeys.join(",") || "none"}): ${failure.errorName}: ${failure.errorMessage}${failure.errorCause ? ` (cause=${failure.errorCause})` : ""}`
6620
+ `[Agent Credential Proxy] request failed (agent=${registration.agentId}, launch=${registration.launchId ?? "none"}, correlation=${failure.correlationId ?? "none"}, method=${failure.method}, path=${failure.pathname}, route_family=${failure.routeFamily ?? "unknown"}, upstream_layer=${failure.upstreamLayer ?? "unknown"}, response_started=${failure.responseStarted ?? false}, query_keys=${failure.queryKeys.join(",") || "none"}): ${failure.errorName}: ${failure.errorMessage}${failure.errorCause ? ` (cause=${failure.errorCause})` : ""}`
6309
6621
  );
6310
6622
  registration.inboxCoordinator?.recordProxyFailure?.(failure);
6311
- registration.inboxCoordinator?.recordTransportNormalizedError?.(
6312
- transportNormalizedErrorForError(target, err, registration.launchId)
6313
- );
6623
+ registration.inboxCoordinator?.recordTransportNormalizedError?.(transportError);
6314
6624
  writeProxyFailureResponse(res, failure);
6315
6625
  }
6316
6626
  }
@@ -6325,16 +6635,37 @@ function writeProxyFailureResponse(res, failure) {
6325
6635
  code: failure.responseCode ?? "agent_proxy_failed",
6326
6636
  detail: failure.errorMessage
6327
6637
  };
6638
+ const proxyDiagnostics = proxyDiagnosticsForFailure(failure);
6639
+ if (proxyDiagnostics) body.proxy = proxyDiagnostics;
6328
6640
  if (failure.lifecycleInvalidAgentId) body.agent_id = failure.lifecycleInvalidAgentId;
6329
6641
  if (failure.lifecycleInvalidContext) body.invariant_context = failure.lifecycleInvalidContext;
6330
- res.writeHead(failure.responseStatusCode ?? 502, { "content-type": "application/json" });
6642
+ const headers = { "content-type": "application/json" };
6643
+ if (failure.correlationId) headers["x-raft-correlation-id"] = failure.correlationId;
6644
+ res.writeHead(failure.responseStatusCode ?? 502, headers);
6331
6645
  res.end(JSON.stringify(body));
6332
6646
  }
6333
- function proxyFailureForError(method, target, err) {
6647
+ function proxyDiagnosticsForFailure(failure) {
6648
+ if (!failure.correlationId && !failure.routeFamily && !failure.upstreamLayer) return void 0;
6649
+ const body = {
6650
+ layer: failure.upstream === "local_daemon" ? "local_daemon" : "local_daemon_proxy"
6651
+ };
6652
+ if (failure.correlationId) body.correlation_id = failure.correlationId;
6653
+ if (failure.routeFamily) body.route_family = failure.routeFamily;
6654
+ if (failure.responseStarted !== void 0) body.response_started = failure.responseStarted;
6655
+ if (failure.upstreamLayer) body.upstream_layer = failure.upstreamLayer;
6656
+ if (failure.upstreamStatus !== void 0) body.upstream_status = failure.upstreamStatus;
6657
+ if (failure.targetHostClass) body.target_host_class = failure.targetHostClass;
6658
+ if (failure.launchId !== void 0 && failure.launchId !== null) body.launch_id = failure.launchId;
6659
+ if (failure.downstreamCaller) body.downstream_caller = failure.downstreamCaller;
6660
+ if (failure.upstream) body.upstream = failure.upstream;
6661
+ return body;
6662
+ }
6663
+ function proxyFailureForError(method, target, err, context = {}) {
6334
6664
  const queryKeys = target ? [.../* @__PURE__ */ new Set([...target.searchParams.keys()])].sort() : [];
6335
6665
  const cause = err instanceof Error ? err.cause : void 0;
6336
6666
  const errorMessage = truncateProxyErrorMessage(err instanceof Error ? err.message : String(err));
6337
6667
  const lifecycleInvalid = parseAgentNoProcessResidencyInvariant(errorMessage);
6668
+ const transportError = context.transportError;
6338
6669
  const failure = {
6339
6670
  method,
6340
6671
  pathname: target?.pathname ?? "unknown",
@@ -6342,6 +6673,17 @@ function proxyFailureForError(method, target, err) {
6342
6673
  errorName: err instanceof Error ? err.name : typeof err,
6343
6674
  errorMessage
6344
6675
  };
6676
+ if (context.correlationId) failure.correlationId = context.correlationId;
6677
+ if (transportError) {
6678
+ failure.routeFamily = transportError.routeFamily;
6679
+ failure.responseStarted = transportError.responseStarted;
6680
+ failure.upstreamLayer = transportError.upstreamLayer;
6681
+ if (transportError.upstreamStatus !== void 0) failure.upstreamStatus = transportError.upstreamStatus;
6682
+ failure.launchId = transportError.launchId;
6683
+ failure.targetHostClass = transportError.targetHostClass;
6684
+ failure.downstreamCaller = transportError.downstreamCaller;
6685
+ failure.upstream = transportError.upstream;
6686
+ }
6345
6687
  if (lifecycleInvalid) {
6346
6688
  failure.responseStatusCode = 409;
6347
6689
  failure.responseCode = "agent_lifecycle_state_invalid";
@@ -6724,7 +7066,9 @@ var LOOPBACK_NO_PROXY = "127.0.0.1,localhost";
6724
7066
  var CLI_TRANSPORT_TRACE_DIR_ENV = "SLOCK_CLI_TRANSPORT_TRACE_DIR";
6725
7067
  var safePathPart = (value) => value.replace(/[^a-zA-Z0-9_.-]/g, "_");
6726
7068
  var RAW_CREDENTIAL_ENV_DENYLIST = [
6727
- "SLOCK_AGENT_CREDENTIAL_KEY"
7069
+ "SLOCK_AGENT_TOKEN",
7070
+ "SLOCK_AGENT_CREDENTIAL_KEY",
7071
+ "SLOCK_AGENT_CREDENTIAL_KEY_FILE"
6728
7072
  ];
6729
7073
  var WORKSPACE_CLI_TRANSPORT_FILENAMES = [
6730
7074
  "agent-token",
@@ -7079,7 +7423,7 @@ set "SLOCK_AGENT_ACTIVE_CAPABILITIES=${DEFAULT_ACTIVE_CAPABILITIES}"\r
7079
7423
  SLOCK_SERVER_URL: ctx.config.serverUrl,
7080
7424
  PATH: `${slockDir}${path2.delimiter}${process.env.PATH ?? ""}`
7081
7425
  };
7082
- delete spawnEnv.SLOCK_AGENT_TOKEN;
7426
+ scrubDaemonChildEnv(spawnEnv);
7083
7427
  for (const key of RAW_CREDENTIAL_ENV_DENYLIST) {
7084
7428
  delete spawnEnv[key];
7085
7429
  }
@@ -7392,6 +7736,46 @@ var ClaudeEventNormalizer = class {
7392
7736
  }
7393
7737
  };
7394
7738
 
7739
+ // src/drivers/claudeInputBudget.ts
7740
+ var CLAUDE_DEFAULT_CONTEXT_TOKENS = 2e5;
7741
+ var CLAUDE_FABLE_CONTEXT_TOKENS = 1e6;
7742
+ var CLAUDE_INPUT_TOKEN_RESERVE = 32e3;
7743
+ var ClaudeStartupPayloadTooLargeError = class extends Error {
7744
+ constructor(details) {
7745
+ super(
7746
+ `INPUT_TOO_LARGE: Claude daemon-owned startup payload is too large before command launch (estimated ${details.estimatedTokens} tokens, budget ${details.budgetTokens}, context limit ${details.contextLimitTokens}, model ${details.model}). Reduce the current prompt or daemon-injected startup context before retrying.`
7747
+ );
7748
+ this.details = details;
7749
+ this.name = "ClaudeStartupPayloadTooLargeError";
7750
+ }
7751
+ };
7752
+ function assertClaudeStartupPayloadWithinBudget(config, input) {
7753
+ const model = claudeModelName(config);
7754
+ const contextLimitTokens = claudeContextLimitTokens(model);
7755
+ const budgetTokens = Math.max(1, contextLimitTokens - CLAUDE_INPUT_TOKEN_RESERVE);
7756
+ const estimatedTokens = estimateClaudeInputTokens(input);
7757
+ if (estimatedTokens <= budgetTokens) return;
7758
+ throw new ClaudeStartupPayloadTooLargeError({
7759
+ estimatedTokens,
7760
+ budgetTokens,
7761
+ contextLimitTokens,
7762
+ model
7763
+ });
7764
+ }
7765
+ function estimateClaudeInputTokens(input) {
7766
+ return Math.ceil(Buffer.byteLength(input, "utf8") / 3);
7767
+ }
7768
+ function claudeModelName(config) {
7769
+ const runtimeConfig = config.runtimeConfig;
7770
+ if (runtimeConfig?.runtime === "claude") {
7771
+ return runtimeConfigModelValue(runtimeConfig);
7772
+ }
7773
+ return config.model || "unknown";
7774
+ }
7775
+ function claudeContextLimitTokens(model) {
7776
+ return /\bfable\b/i.test(model) ? CLAUDE_FABLE_CONTEXT_TOKENS : CLAUDE_DEFAULT_CONTEXT_TOKENS;
7777
+ }
7778
+
7395
7779
  // src/drivers/claudeLaunch.ts
7396
7780
  import { writeFileSync as writeFileSync2 } from "fs";
7397
7781
  import path5 from "path";
@@ -7647,7 +8031,7 @@ function requiresWindowsShell(command, platform = process.platform) {
7647
8031
  }
7648
8032
  function resolveCommandOnPath(command, deps = {}) {
7649
8033
  const platform = deps.platform ?? process.platform;
7650
- const env = withWindowsUserEnvironment(deps.env ?? process.env, deps);
8034
+ const env = scrubDaemonChildEnv({ ...withWindowsUserEnvironment(deps.env ?? process.env, deps) });
7651
8035
  const execFileSyncFn = deps.execFileSyncFn ?? execFileSync;
7652
8036
  const existsSyncFn = deps.existsSyncFn ?? existsSync3;
7653
8037
  if (platform === "win32") {
@@ -7673,7 +8057,7 @@ function firstExistingPath(candidates, deps = {}) {
7673
8057
  return null;
7674
8058
  }
7675
8059
  function readCommandVersion(command, args = [], deps = {}) {
7676
- const env = withWindowsUserEnvironment(deps.env ?? process.env, deps);
8060
+ const env = scrubDaemonChildEnv({ ...withWindowsUserEnvironment(deps.env ?? process.env, deps) });
7677
8061
  const execFileSyncFn = deps.execFileSyncFn ?? execFileSync;
7678
8062
  try {
7679
8063
  const output = normalizeExecOutput(execFileSyncFn(command, [...args, "--version"], {
@@ -7811,6 +8195,8 @@ var ClaudeDriver = class {
7811
8195
  return buildClaudeArgs(config, opts);
7812
8196
  }
7813
8197
  async spawn(ctx) {
8198
+ assertClaudeStartupPayloadWithinBudget(ctx.config, `${ctx.standingPrompt}
8199
+ ${ctx.prompt}`);
7814
8200
  const { slockDir, tokenFile, spawnEnv } = await prepareCliTransport(
7815
8201
  ctx,
7816
8202
  buildClaudeProviderIsolationEnv(ctx)
@@ -7924,6 +8310,12 @@ function codexSessionRootCandidates(homeDirOrCodexRoot) {
7924
8310
  var RuntimeTurnState = class {
7925
8311
  currentTurnId = null;
7926
8312
  pendingTurnId = null;
8313
+ turnInProgress = false;
8314
+ currentTurnHadRuntimeActivity = false;
8315
+ currentTurnHadTokenUsage = false;
8316
+ currentTurnHadNonEmptyInput = false;
8317
+ pendingNonEmptyInputTurnIds = /* @__PURE__ */ new Set();
8318
+ completedTurnIds = /* @__PURE__ */ new Set();
7927
8319
  /**
7928
8320
  * Post-tool window where the app-server may not yet accept stdin steering.
7929
8321
  * Gate busy-mode delivery until turn/completed or next progress.
@@ -7932,6 +8324,12 @@ var RuntimeTurnState = class {
7932
8324
  reset() {
7933
8325
  this.currentTurnId = null;
7934
8326
  this.pendingTurnId = null;
8327
+ this.turnInProgress = false;
8328
+ this.currentTurnHadRuntimeActivity = false;
8329
+ this.currentTurnHadTokenUsage = false;
8330
+ this.currentTurnHadNonEmptyInput = false;
8331
+ this.pendingNonEmptyInputTurnIds.clear();
8332
+ this.completedTurnIds.clear();
7935
8333
  this.steeringGateActive = false;
7936
8334
  }
7937
8335
  get activeTurnId() {
@@ -7946,20 +8344,54 @@ var RuntimeTurnState = class {
7946
8344
  this.currentTurnId = startedTurnId;
7947
8345
  }
7948
8346
  this.pendingTurnId = null;
8347
+ this.turnInProgress = true;
8348
+ this.currentTurnHadRuntimeActivity = false;
8349
+ this.currentTurnHadTokenUsage = false;
8350
+ this.currentTurnHadNonEmptyInput = startedTurnId ? this.pendingNonEmptyInputTurnIds.delete(startedTurnId) : false;
7949
8351
  this.steeringGateActive = false;
7950
8352
  }
7951
8353
  noteTurnAccepted(turnId) {
7952
8354
  this.pendingTurnId = turnId;
7953
8355
  }
7954
8356
  markProgress() {
8357
+ this.currentTurnHadRuntimeActivity = true;
7955
8358
  this.steeringGateActive = false;
7956
8359
  }
7957
8360
  markToolBoundary() {
8361
+ this.currentTurnHadRuntimeActivity = true;
7958
8362
  this.steeringGateActive = true;
7959
8363
  }
8364
+ markTokenUsage() {
8365
+ this.currentTurnHadTokenUsage = true;
8366
+ }
8367
+ markNonEmptyInputForTurn(turnId) {
8368
+ if (!turnId || this.completedTurnIds.has(turnId)) return;
8369
+ if (this.turnInProgress && this.currentTurnId === turnId) {
8370
+ this.currentTurnHadNonEmptyInput = true;
8371
+ } else {
8372
+ this.pendingNonEmptyInputTurnIds.add(turnId);
8373
+ }
8374
+ }
8375
+ hasNonEmptyInputEvidence() {
8376
+ return this.currentTurnHadNonEmptyInput;
8377
+ }
8378
+ completedWithoutRuntimeActivity() {
8379
+ return this.turnInProgress && !this.currentTurnHadRuntimeActivity && !this.currentTurnHadTokenUsage;
8380
+ }
7960
8381
  markTurnCompleted() {
8382
+ if (this.currentTurnId) {
8383
+ this.completedTurnIds.add(this.currentTurnId);
8384
+ if (this.completedTurnIds.size > 16) {
8385
+ const oldest = this.completedTurnIds.values().next().value;
8386
+ if (oldest) this.completedTurnIds.delete(oldest);
8387
+ }
8388
+ }
7961
8389
  this.currentTurnId = null;
7962
8390
  this.pendingTurnId = null;
8391
+ this.turnInProgress = false;
8392
+ this.currentTurnHadRuntimeActivity = false;
8393
+ this.currentTurnHadTokenUsage = false;
8394
+ this.currentTurnHadNonEmptyInput = false;
7963
8395
  this.steeringGateActive = false;
7964
8396
  }
7965
8397
  };
@@ -8113,7 +8545,7 @@ function codexNotificationDiagnosticEvent(message) {
8113
8545
  ...sessionId ? { sessionId } : {}
8114
8546
  };
8115
8547
  }
8116
- function codexThreadStatusChangedEvent(message) {
8548
+ function codexThreadStatusChangedEvents(message) {
8117
8549
  if (message.method !== "thread/status/changed") return null;
8118
8550
  const params = message.params ?? {};
8119
8551
  const status = params.status ?? params.thread?.status;
@@ -8121,18 +8553,33 @@ function codexThreadStatusChangedEvent(message) {
8121
8553
  const statusType = nonEmptyString2(status.type);
8122
8554
  const sessionId = codexMessageThreadId(message);
8123
8555
  if (statusType === "systemError") {
8124
- const statusMessage = boundedString(status.message) ?? boundedString(status.error?.message) ?? getCodexNotificationErrorMessage(params) ?? "Codex thread entered system error state";
8125
- return {
8556
+ const explicitReason = boundedString(status.message) ?? boundedString(status.error?.message) ?? getCodexNotificationErrorMessage(params);
8557
+ const statusMessage = explicitReason ?? "Codex thread entered system error state";
8558
+ const errorEvent = {
8126
8559
  kind: "error",
8127
8560
  message: statusMessage
8128
8561
  };
8562
+ if (explicitReason) return [errorEvent];
8563
+ return [
8564
+ {
8565
+ kind: "runtime_diagnostic",
8566
+ severity: "warning",
8567
+ source: "codex_app_server_notification",
8568
+ itemType: "codex_thread_system_error_without_reason",
8569
+ message: "Codex thread entered system error state without a reason",
8570
+ payloadBytes: payloadBytes(params),
8571
+ reasonPresent: false,
8572
+ ...sessionId ? { sessionId } : {}
8573
+ },
8574
+ errorEvent
8575
+ ];
8129
8576
  }
8130
8577
  if (statusType !== "active" || !Array.isArray(status.activeFlags)) return null;
8131
8578
  const activeFlags = status.activeFlags.filter((flag) => typeof flag === "string");
8132
8579
  const waitFlags = activeFlags.filter((flag) => flag === "waitingOnApproval" || flag === "waitingOnUserInput");
8133
8580
  if (waitFlags.length === 0) return null;
8134
8581
  const waitLabel = waitFlags.includes("waitingOnApproval") && waitFlags.includes("waitingOnUserInput") ? "approval and user input" : waitFlags.includes("waitingOnApproval") ? "approval" : "user input";
8135
- return {
8582
+ return [{
8136
8583
  kind: "runtime_diagnostic",
8137
8584
  severity: "warning",
8138
8585
  source: "codex_app_server_notification",
@@ -8141,7 +8588,7 @@ function codexThreadStatusChangedEvent(message) {
8141
8588
  details: `Active flags: ${waitFlags.join(", ")}`,
8142
8589
  payloadBytes: payloadBytes(params),
8143
8590
  ...sessionId ? { sessionId } : {}
8144
- };
8591
+ }];
8145
8592
  }
8146
8593
  function joinReasoningSummaryText(item) {
8147
8594
  const summary = Array.isArray(item.summary) ? item.summary.filter((entry) => typeof entry === "string") : [];
@@ -8212,6 +8659,9 @@ var CodexEventNormalizer = class {
8212
8659
  get canSteerBusy() {
8213
8660
  return this.turnState.canSteerBusy;
8214
8661
  }
8662
+ markNonEmptyTurnInput(turnId) {
8663
+ this.turnState.markNonEmptyInputForTurn(turnId);
8664
+ }
8215
8665
  adoptThreadId(threadId) {
8216
8666
  this.currentThreadId = threadId;
8217
8667
  }
@@ -8241,6 +8691,9 @@ var CodexEventNormalizer = class {
8241
8691
  }
8242
8692
  const telemetry = parseCodexTelemetryEvent(message);
8243
8693
  if (telemetry) {
8694
+ if (telemetry.kind === "telemetry" && telemetry.name === "token_usage") {
8695
+ this.turnState.markTokenUsage();
8696
+ }
8244
8697
  const telemetrySessionId = codexMessageThreadId(message);
8245
8698
  const telemetryTurnId = nonEmptyString2(message.params?.turnId) ?? nonEmptyString2(message.params?.turn?.id);
8246
8699
  if (telemetrySessionId) {
@@ -8257,6 +8710,7 @@ var CodexEventNormalizer = class {
8257
8710
  }
8258
8711
  const rawProgress = rawResponseItemProgressEvent(message);
8259
8712
  if (rawProgress) {
8713
+ this.turnState.markProgress();
8260
8714
  events.push(rawProgress);
8261
8715
  return { events };
8262
8716
  }
@@ -8339,9 +8793,9 @@ var CodexEventNormalizer = class {
8339
8793
  break;
8340
8794
  }
8341
8795
  case "thread/status/changed": {
8342
- const event = codexThreadStatusChangedEvent(message);
8343
- if (event) {
8344
- events.push(event);
8796
+ const statusEvents = codexThreadStatusChangedEvents(message);
8797
+ if (statusEvents) {
8798
+ events.push(...statusEvents);
8345
8799
  }
8346
8800
  break;
8347
8801
  }
@@ -8385,6 +8839,7 @@ var CodexEventNormalizer = class {
8385
8839
  break;
8386
8840
  case "commandExecution":
8387
8841
  if (isStarted && typeof item.command === "string") {
8842
+ this.turnState.markProgress();
8388
8843
  events.push({ kind: "tool_call", name: "shell", input: { command: item.command } });
8389
8844
  }
8390
8845
  if (isCompleted) {
@@ -8394,19 +8849,23 @@ var CodexEventNormalizer = class {
8394
8849
  break;
8395
8850
  case "contextCompaction":
8396
8851
  if (isStarted) {
8852
+ this.turnState.markProgress();
8397
8853
  events.push({ kind: "compaction_started" });
8398
8854
  }
8399
8855
  if (isCompleted) {
8856
+ this.turnState.markProgress();
8400
8857
  events.push({ kind: "compaction_finished" });
8401
8858
  }
8402
8859
  break;
8403
8860
  case "enteredReviewMode":
8404
8861
  if (isStarted) {
8862
+ this.turnState.markProgress();
8405
8863
  events.push({ kind: "review_started" });
8406
8864
  }
8407
8865
  break;
8408
8866
  case "exitedReviewMode":
8409
8867
  if (isCompleted) {
8868
+ this.turnState.markProgress();
8410
8869
  events.push({ kind: "review_finished" });
8411
8870
  }
8412
8871
  break;
@@ -8414,6 +8873,7 @@ var CodexEventNormalizer = class {
8414
8873
  if (isStarted && Array.isArray(item.changes)) {
8415
8874
  let outputCount = 0;
8416
8875
  for (const change of item.changes) {
8876
+ this.turnState.markProgress();
8417
8877
  events.push({
8418
8878
  kind: "tool_call",
8419
8879
  name: "file_change",
@@ -8445,6 +8905,7 @@ var CodexEventNormalizer = class {
8445
8905
  case "mcpToolCall":
8446
8906
  if (isStarted) {
8447
8907
  const toolName = codexMcpToolName(item);
8908
+ this.turnState.markProgress();
8448
8909
  events.push({ kind: "tool_call", name: toolName, input: item.arguments });
8449
8910
  }
8450
8911
  if (isCompleted) {
@@ -8455,6 +8916,7 @@ var CodexEventNormalizer = class {
8455
8916
  break;
8456
8917
  case "collabAgentToolCall":
8457
8918
  if (isStarted) {
8919
+ this.turnState.markProgress();
8458
8920
  events.push({ kind: "tool_call", name: "collab_tool_call", input: { tool: item.tool, prompt: item.prompt } });
8459
8921
  }
8460
8922
  if (isCompleted) {
@@ -8464,6 +8926,7 @@ var CodexEventNormalizer = class {
8464
8926
  break;
8465
8927
  case "webSearch":
8466
8928
  if (isStarted) {
8929
+ this.turnState.markProgress();
8467
8930
  events.push({ kind: "tool_call", name: "web_search", input: { query: item.query } });
8468
8931
  }
8469
8932
  if (isCompleted) {
@@ -8483,6 +8946,26 @@ var CodexEventNormalizer = class {
8483
8946
  const detail = typeof turn?.error?.message === "string" && turn.error.message.length > 0 ? `: ${turn.error.message}` : "";
8484
8947
  events.push({ kind: "error", message: `Codex turn interrupted${detail}` });
8485
8948
  }
8949
+ if (turn?.status === "completed" && this.turnState.completedWithoutRuntimeActivity()) {
8950
+ const inputEvidence = this.turnState.hasNonEmptyInputEvidence() ? "nonempty" : "unknown";
8951
+ const diagnosticMessage = "Codex runtime completed an empty turn with no output, progress, or token usage";
8952
+ const userMessage = inputEvidence === "nonempty" ? "Codex runtime returned an empty response. Please retry." : "Codex runtime completed without a response. Please retry.";
8953
+ events.push({
8954
+ kind: "runtime_diagnostic",
8955
+ severity: "warning",
8956
+ source: "codex_app_server_notification",
8957
+ itemType: "codex_zero_evidence_turn_completed",
8958
+ message: diagnosticMessage,
8959
+ details: "Codex runtime reported turn/completed status=completed after turn/started with no assistant text, reasoning text, tool activity, internal progress, raw response-item progress, or valid thread/tokenUsage/updated payload.",
8960
+ payloadBytes: payloadBytes(message.params),
8961
+ inputEvidence,
8962
+ ...this.currentThreadId ? { sessionId: this.currentThreadId } : {}
8963
+ });
8964
+ events.push({
8965
+ kind: "error",
8966
+ message: `${userMessage} (codex_zero_evidence_turn_completed)`
8967
+ });
8968
+ }
8486
8969
  this.turnState.markTurnCompleted();
8487
8970
  this.streamedAgentMessageIds.clear();
8488
8971
  this.streamedReasoningIds.clear();
@@ -8520,6 +9003,15 @@ var CodexEventNormalizer = class {
8520
9003
  // src/drivers/codex.ts
8521
9004
  var CODEX_DESKTOP_BUNDLE_PATH = "/Applications/Codex.app/Contents/Resources/codex";
8522
9005
  var CODEX_APP_SERVER_PROBE_ARGS = ["app-server", "--help"];
9006
+ function hasNonEmptyCodexTextInput(input) {
9007
+ return Array.isArray(input) && input.some(
9008
+ (item) => item && typeof item === "object" && item.type === "text" && typeof item.text === "string" && item.text.length > 0
9009
+ );
9010
+ }
9011
+ function resultTurnId(message) {
9012
+ const turn = message.result?.turn;
9013
+ return turn && typeof turn.id === "string" ? turn.id : null;
9014
+ }
8523
9015
  function isWindowsSandboxRunner(commandPath) {
8524
9016
  return path7.basename(commandPath).toLowerCase().startsWith("codex-command-runner");
8525
9017
  }
@@ -8849,6 +9341,7 @@ var CodexDriver = class {
8849
9341
  pendingResumeFallbackParams = null;
8850
9342
  pendingResumeThreadId = null;
8851
9343
  pendingInitialTurnRequestId = null;
9344
+ pendingInitialTurnInput = null;
8852
9345
  pendingDeliveryRequests = /* @__PURE__ */ new Map();
8853
9346
  initialTurnStarted = false;
8854
9347
  normalizer = new CodexEventNormalizer();
@@ -8869,6 +9362,7 @@ var CodexDriver = class {
8869
9362
  this.pendingResumeFallbackParams = null;
8870
9363
  this.pendingResumeThreadId = null;
8871
9364
  this.pendingInitialTurnRequestId = null;
9365
+ this.pendingInitialTurnInput = null;
8872
9366
  this.pendingDeliveryRequests.clear();
8873
9367
  this.initialTurnStarted = false;
8874
9368
  this.normalizer.reset();
@@ -8991,28 +9485,33 @@ var CodexDriver = class {
8991
9485
  startupRequestMethod: "turn/start"
8992
9486
  });
8993
9487
  } else {
9488
+ if (hasNonEmptyCodexTextInput(this.pendingInitialTurnInput)) {
9489
+ this.normalizer.markNonEmptyTurnInput(resultTurnId(message));
9490
+ }
8994
9491
  this.pendingInitialPrompt = null;
8995
9492
  }
9493
+ this.pendingInitialTurnInput = null;
8996
9494
  return events;
8997
9495
  }
8998
9496
  if (isResponse && message.id !== void 0 && this.pendingDeliveryRequests.has(message.id)) {
8999
- const requestMethod = this.pendingDeliveryRequests.get(message.id);
9497
+ const deliveryRequest = this.pendingDeliveryRequests.get(message.id);
9000
9498
  this.pendingDeliveryRequests.delete(message.id);
9001
9499
  if (hasJsonRpcField(message, "error")) {
9002
9500
  const params = message.error ?? {};
9003
9501
  events.push({
9004
9502
  kind: "delivery_error",
9005
9503
  message: message.error?.message || "Codex app-server request failed",
9006
- requestMethod,
9504
+ requestMethod: deliveryRequest.method,
9007
9505
  source: "codex_app_server_response",
9008
9506
  payloadBytes: payloadBytes2(params)
9009
9507
  });
9508
+ } else if (hasNonEmptyCodexTextInput(deliveryRequest.input)) {
9509
+ this.normalizer.markNonEmptyTurnInput(deliveryRequest.turnId ?? resultTurnId(message));
9010
9510
  }
9011
9511
  return events;
9012
9512
  }
9013
9513
  const result = this.normalizer.normalizeMessage(message);
9014
9514
  if (result.turnStarted) {
9015
- this.pendingInitialTurnRequestId = null;
9016
9515
  this.pendingInitialPrompt = null;
9017
9516
  }
9018
9517
  if (result.threadReady) {
@@ -9029,7 +9528,9 @@ var CodexDriver = class {
9029
9528
  if (mode === "busy") {
9030
9529
  if (!this.normalizer.canSteerBusy) return null;
9031
9530
  const id2 = this.nextRequestId();
9032
- this.pendingDeliveryRequests.set(id2, "turn/steer");
9531
+ const input2 = [{ type: "text", text }];
9532
+ const turnId = this.normalizer.activeTurnId;
9533
+ this.pendingDeliveryRequests.set(id2, { method: "turn/steer", input: input2, turnId });
9033
9534
  return JSON.stringify({
9034
9535
  jsonrpc: "2.0",
9035
9536
  id: id2,
@@ -9037,19 +9538,20 @@ var CodexDriver = class {
9037
9538
  params: {
9038
9539
  threadId: this.normalizer.threadId,
9039
9540
  expectedTurnId: this.normalizer.activeTurnId,
9040
- input: [{ type: "text", text }]
9541
+ input: input2
9041
9542
  }
9042
9543
  });
9043
9544
  }
9044
9545
  const id = this.nextRequestId();
9045
- this.pendingDeliveryRequests.set(id, "turn/start");
9546
+ const input = [{ type: "text", text }];
9547
+ this.pendingDeliveryRequests.set(id, { method: "turn/start", input, turnId: null });
9046
9548
  return JSON.stringify({
9047
9549
  jsonrpc: "2.0",
9048
9550
  id,
9049
9551
  method: "turn/start",
9050
9552
  params: {
9051
9553
  threadId: this.normalizer.threadId,
9052
- input: [{ type: "text", text }]
9554
+ input
9053
9555
  }
9054
9556
  });
9055
9557
  }
@@ -9071,9 +9573,11 @@ var CodexDriver = class {
9071
9573
  if (this.initialTurnStarted || this.pendingInitialTurnRequestId !== null || !this.pendingInitialPrompt || !this.normalizer.threadId) return;
9072
9574
  this.initialTurnStarted = true;
9073
9575
  const prompt = this.pendingInitialPrompt;
9576
+ const input = [{ type: "text", text: prompt }];
9577
+ this.pendingInitialTurnInput = input;
9074
9578
  this.pendingInitialTurnRequestId = this.sendRequest("turn/start", {
9075
9579
  threadId: this.normalizer.threadId,
9076
- input: [{ type: "text", text: prompt }]
9580
+ input
9077
9581
  });
9078
9582
  }
9079
9583
  sendRequest(method, params) {
@@ -9757,11 +10261,11 @@ function detectCursorModels(runCommand = runCursorModelsCommand) {
9757
10261
  return parseCursorModelsOutput(String(result.stdout || ""));
9758
10262
  }
9759
10263
  function buildCursorModelProbeEnv(deps = {}) {
9760
- return withWindowsUserEnvironment({
10264
+ return scrubDaemonChildEnv(withWindowsUserEnvironment({
9761
10265
  ...deps.env ?? process.env,
9762
10266
  FORCE_COLOR: "0",
9763
10267
  NO_COLOR: "1"
9764
- }, deps);
10268
+ }, deps));
9765
10269
  }
9766
10270
  function runCursorModelsCommand() {
9767
10271
  return spawnSync("cursor-agent", ["models"], {
@@ -9817,7 +10321,7 @@ function resolveGeminiSpawn(commandArgs, deps = {}) {
9817
10321
  }
9818
10322
  const execFileSyncFn = deps.execFileSyncFn ?? execFileSync3;
9819
10323
  const existsSyncFn = deps.existsSyncFn ?? existsSync5;
9820
- const env = deps.env ?? process.env;
10324
+ const env = scrubDaemonChildEnv({ ...deps.env ?? process.env });
9821
10325
  const winPath = path8.win32;
9822
10326
  let geminiEntry = null;
9823
10327
  try {
@@ -9954,12 +10458,15 @@ var GeminiDriver = class {
9954
10458
  // src/drivers/kimi.ts
9955
10459
  import { randomUUID as randomUUID2 } from "crypto";
9956
10460
  import { spawn as spawn7 } from "child_process";
9957
- import { existsSync as existsSync6, readFileSync as readFileSync3, writeFileSync as writeFileSync3 } from "fs";
10461
+ import { chmodSync, existsSync as existsSync6, readFileSync as readFileSync3, writeFileSync as writeFileSync3 } from "fs";
9958
10462
  import os4 from "os";
9959
10463
  import path9 from "path";
9960
10464
  var KIMI_WIRE_PROTOCOL_VERSION = "1.3";
9961
10465
  var KIMI_SYSTEM_PROMPT_FILE = ".slock-kimi-system.md";
9962
10466
  var KIMI_AGENT_FILE = ".slock-kimi-agent.yaml";
10467
+ var KIMI_GENERATED_CONFIG_FILE = ".slock-kimi-config.toml";
10468
+ var SLOCK_KIMI_CONFIG_CONTENT_ENV = "SLOCK_KIMI_CONFIG_CONTENT";
10469
+ var SLOCK_KIMI_CONFIG_FILE_ENV = "SLOCK_KIMI_CONFIG_FILE";
9963
10470
  function parseToolArguments(raw) {
9964
10471
  if (typeof raw !== "string") return raw;
9965
10472
  try {
@@ -9968,6 +10475,73 @@ function parseToolArguments(raw) {
9968
10475
  return raw;
9969
10476
  }
9970
10477
  }
10478
+ function readKimiConfigSource(home = os4.homedir(), env = process.env) {
10479
+ const inlineConfig = env[SLOCK_KIMI_CONFIG_CONTENT_ENV];
10480
+ if (inlineConfig && inlineConfig.trim()) {
10481
+ return {
10482
+ raw: inlineConfig,
10483
+ explicitPath: null,
10484
+ sourcePath: SLOCK_KIMI_CONFIG_CONTENT_ENV
10485
+ };
10486
+ }
10487
+ const explicitPath = env[SLOCK_KIMI_CONFIG_FILE_ENV];
10488
+ const configPath = explicitPath && explicitPath.trim() ? explicitPath : path9.join(home, ".kimi", "config.toml");
10489
+ try {
10490
+ return {
10491
+ raw: readFileSync3(configPath, "utf8"),
10492
+ explicitPath: explicitPath && explicitPath.trim() ? explicitPath : null,
10493
+ sourcePath: configPath
10494
+ };
10495
+ } catch {
10496
+ return {
10497
+ raw: null,
10498
+ explicitPath: explicitPath && explicitPath.trim() ? explicitPath : null,
10499
+ sourcePath: configPath
10500
+ };
10501
+ }
10502
+ }
10503
+ function buildKimiSpawnEnv(env = process.env) {
10504
+ const spawnEnv = { ...env, FORCE_COLOR: "0", NO_COLOR: "1" };
10505
+ delete spawnEnv[SLOCK_KIMI_CONFIG_CONTENT_ENV];
10506
+ delete spawnEnv[SLOCK_KIMI_CONFIG_FILE_ENV];
10507
+ return scrubDaemonChildEnv(spawnEnv);
10508
+ }
10509
+ function buildKimiEffectiveEnv(ctx, overrideEnv) {
10510
+ return {
10511
+ ...process.env,
10512
+ ...ctx.config.envVars || {},
10513
+ ...overrideEnv || {}
10514
+ };
10515
+ }
10516
+ function buildKimiLaunchOptions(ctx, opts = {}) {
10517
+ const env = buildKimiEffectiveEnv(ctx, opts.env);
10518
+ const source = readKimiConfigSource(opts.home ?? os4.homedir(), env);
10519
+ const args = [];
10520
+ let configFilePath = null;
10521
+ let configContent = null;
10522
+ if (source.explicitPath) {
10523
+ configFilePath = source.explicitPath;
10524
+ } else if (source.raw !== null && source.sourcePath === SLOCK_KIMI_CONFIG_CONTENT_ENV) {
10525
+ configFilePath = path9.join(ctx.workingDirectory, KIMI_GENERATED_CONFIG_FILE);
10526
+ configContent = source.raw;
10527
+ if (opts.writeGeneratedConfig !== false) {
10528
+ writeFileSync3(configFilePath, source.raw, { encoding: "utf8", mode: 384 });
10529
+ chmodSync(configFilePath, 384);
10530
+ }
10531
+ }
10532
+ if (configFilePath) {
10533
+ args.push("--config-file", configFilePath);
10534
+ }
10535
+ if (ctx.config.model && ctx.config.model !== "default") {
10536
+ args.push("--model", ctx.config.model);
10537
+ }
10538
+ return {
10539
+ args,
10540
+ env: buildKimiSpawnEnv(env),
10541
+ configFilePath,
10542
+ configContent
10543
+ };
10544
+ }
9971
10545
  function resolveKimiSpawn(commandArgs, deps = {}) {
9972
10546
  return {
9973
10547
  command: resolveCommandOnPath("kimi", deps) ?? "kimi",
@@ -9991,7 +10565,25 @@ var KimiDriver = class {
9991
10565
  };
9992
10566
  model = {
9993
10567
  detectedModelsVerifiedAs: "launchable",
9994
- toLaunchSpec: (modelId) => ({ args: ["--model", modelId] })
10568
+ toLaunchSpec: (modelId, ctx, opts) => {
10569
+ if (!ctx) return { args: ["--model", modelId] };
10570
+ const launchCtx = {
10571
+ ...ctx,
10572
+ config: {
10573
+ ...ctx.config,
10574
+ model: modelId
10575
+ }
10576
+ };
10577
+ const launch = buildKimiLaunchOptions(launchCtx, {
10578
+ home: opts?.home,
10579
+ writeGeneratedConfig: false
10580
+ });
10581
+ return {
10582
+ args: launch.args,
10583
+ env: launch.env,
10584
+ configFiles: launch.configFilePath ? [launch.configFilePath] : void 0
10585
+ };
10586
+ }
9995
10587
  };
9996
10588
  supportsStdinNotification = true;
9997
10589
  busyDeliveryMode = "direct";
@@ -10015,21 +10607,23 @@ var KimiDriver = class {
10015
10607
  ` system_prompt_path: ./${KIMI_SYSTEM_PROMPT_FILE}`,
10016
10608
  ""
10017
10609
  ].join("\n"), "utf8");
10610
+ const launch = buildKimiLaunchOptions(ctx);
10018
10611
  const args = [
10019
10612
  "--wire",
10020
10613
  "--yolo",
10021
10614
  "--agent-file",
10022
10615
  agentFilePath,
10023
10616
  "--session",
10024
- this.sessionId
10617
+ this.sessionId,
10618
+ ...launch.args
10025
10619
  ];
10026
10620
  const launchRuntimeFields = runtimeConfigToLaunchFields(hydrateRuntimeConfig(ctx.config));
10027
10621
  if (launchRuntimeFields.model && launchRuntimeFields.model !== "default") {
10028
10622
  args.push("--model", launchRuntimeFields.model);
10029
10623
  }
10030
10624
  const spawnEnv = (await prepareCliTransport(ctx, { NO_COLOR: "1" })).spawnEnv;
10031
- const launch = resolveKimiSpawn(args);
10032
- const proc = spawn7(launch.command, launch.args, {
10625
+ const spawnTarget = resolveKimiSpawn(args);
10626
+ const proc = spawn7(spawnTarget.command, spawnTarget.args, {
10033
10627
  cwd: ctx.workingDirectory,
10034
10628
  stdio: ["pipe", "pipe", "pipe"],
10035
10629
  env: spawnEnv,
@@ -10037,7 +10631,7 @@ var KimiDriver = class {
10037
10631
  // and has an 8191-character command-line limit. Kimi's official
10038
10632
  // installer/uv entrypoint is an executable, so launch it directly and
10039
10633
  // keep prompts on stdin / files instead of routing through cmd.exe.
10040
- shell: launch.shell
10634
+ shell: spawnTarget.shell
10041
10635
  });
10042
10636
  proc.stdin?.write(JSON.stringify({
10043
10637
  jsonrpc: "2.0",
@@ -10150,14 +10744,9 @@ var KimiDriver = class {
10150
10744
  return detectKimiModels();
10151
10745
  }
10152
10746
  };
10153
- function detectKimiModels(home = os4.homedir()) {
10154
- const configPath = path9.join(home, ".kimi", "config.toml");
10155
- let raw;
10156
- try {
10157
- raw = readFileSync3(configPath, "utf8");
10158
- } catch {
10159
- return null;
10160
- }
10747
+ function detectKimiModels(home = os4.homedir(), opts = {}) {
10748
+ const raw = readKimiConfigSource(home, opts.env).raw;
10749
+ if (raw === null) return null;
10161
10750
  const models = [];
10162
10751
  const sectionRe = /^\s*\[models(?:\.([^\]]+)|"\.[^"]+"|\."[^"]+")\s*\]\s*$/gm;
10163
10752
  const lineRe = /^\s*\[models\.(.+?)\s*\]\s*$/gm;
@@ -10417,6 +11006,12 @@ var KimiSdkRuntimeSession = class {
10417
11006
  get closed() {
10418
11007
  return this.didClose;
10419
11008
  }
11009
+ // In-process SDK session: there is no OS pid to probe with signal-0, so
11010
+ // liveness is unknowable via the pid-probe boundary. Return undefined, which
11011
+ // callers treat the same as the historic "no pid" probe result (RS-011).
11012
+ isAlive() {
11013
+ return void 0;
11014
+ }
10420
11015
  on(event, cb) {
10421
11016
  this.events.on(event, cb);
10422
11017
  }
@@ -10836,7 +11431,7 @@ function runOpenCodeModelsCommand(home, deps = {}) {
10836
11431
  const platform = deps.platform ?? process.platform;
10837
11432
  const spawnSyncFn = deps.spawnSyncFn ?? spawnSync2;
10838
11433
  const result = spawnSyncFn("opencode", ["models"], {
10839
- env: { ...process.env, HOME: home, FORCE_COLOR: "0", NO_COLOR: "1" },
11434
+ env: scrubDaemonChildEnv({ ...process.env, HOME: home, FORCE_COLOR: "0", NO_COLOR: "1" }),
10840
11435
  encoding: "utf8",
10841
11436
  timeout: 5e3,
10842
11437
  shell: platform === "win32"
@@ -11684,6 +12279,12 @@ var PiSdkRuntimeSession = class {
11684
12279
  get closed() {
11685
12280
  return this.didClose;
11686
12281
  }
12282
+ // In-process SDK session: there is no OS pid to probe with signal-0, so
12283
+ // liveness is unknowable via the pid-probe boundary. Return undefined, which
12284
+ // callers treat the same as the historic "no pid" probe result (RS-011).
12285
+ isAlive() {
12286
+ return void 0;
12287
+ }
11687
12288
  on(event, cb) {
11688
12289
  this.events.on(event, cb);
11689
12290
  }
@@ -12002,6 +12603,25 @@ var ChildProcessRuntimeSession = class {
12002
12603
  get closed() {
12003
12604
  return this.process ? this.process.exitCode != null || this.process.signalCode != null : false;
12004
12605
  }
12606
+ /**
12607
+ * Read-only OS liveness introspection (signal-0), NOT control IO — exposed so
12608
+ * managers query liveness through the session boundary (RS-011) instead of
12609
+ * poking the raw pid. Preserves the historic `probeRuntimeProcessLiveness`
12610
+ * semantics exactly: undefined when there is no pid, true on success or EPERM,
12611
+ * false otherwise. Deliberately does NOT short-circuit on `this.closed` — the
12612
+ * original probe checked only pid + signal-0.
12613
+ */
12614
+ isAlive() {
12615
+ const pid = this.process?.pid;
12616
+ if (typeof pid !== "number") return void 0;
12617
+ try {
12618
+ process.kill(pid, 0);
12619
+ return true;
12620
+ } catch (err) {
12621
+ const code = typeof err === "object" && err !== null && "code" in err ? err.code : void 0;
12622
+ return code === "EPERM" ? true : false;
12623
+ }
12624
+ }
12005
12625
  on(event, cb) {
12006
12626
  this.events.on(event, cb);
12007
12627
  }
@@ -12115,6 +12735,61 @@ function getDriver(runtimeId) {
12115
12735
  return driver;
12116
12736
  }
12117
12737
 
12738
+ // src/daemonOrphanReaper.ts
12739
+ async function reapOrphanProcesses(pids, logger2, recordTrace) {
12740
+ const survivors = pids.filter((pid) => {
12741
+ try {
12742
+ process.kill(pid, 0);
12743
+ return true;
12744
+ } catch {
12745
+ return false;
12746
+ }
12747
+ });
12748
+ if (survivors.length === 0) return false;
12749
+ for (const pid of survivors) {
12750
+ logger2.warn(`[Daemon] Agent subprocess ${pid} survived stopAll; sending SIGKILL`);
12751
+ try {
12752
+ process.kill(pid, "SIGKILL");
12753
+ } catch {
12754
+ }
12755
+ }
12756
+ recordTrace("daemon.agent.stop_all.survivor_reaped", {
12757
+ survivor_count: survivors.length,
12758
+ survivor_pids: survivors.join(","),
12759
+ reason: "shutdown_survivor",
12760
+ signal: "SIGKILL"
12761
+ });
12762
+ const deadline = Date.now() + 2e3;
12763
+ while (Date.now() < deadline) {
12764
+ const alive = survivors.filter((pid) => {
12765
+ try {
12766
+ process.kill(pid, 0);
12767
+ return true;
12768
+ } catch {
12769
+ return false;
12770
+ }
12771
+ });
12772
+ if (alive.length === 0) break;
12773
+ await new Promise((r) => setTimeout(r, 50));
12774
+ }
12775
+ const stillAlive = survivors.filter((pid) => {
12776
+ try {
12777
+ process.kill(pid, 0);
12778
+ return true;
12779
+ } catch {
12780
+ return false;
12781
+ }
12782
+ });
12783
+ const outcome = stillAlive.length > 0 ? "survivors_still_alive" : "survivors_killed";
12784
+ recordTrace("daemon.agent.stop_all.completed", {
12785
+ survivor_count: survivors.length,
12786
+ reaped_count: survivors.length - stillAlive.length,
12787
+ still_alive_count: stillAlive.length,
12788
+ outcome
12789
+ }, stillAlive.length > 0 ? "error" : "ok");
12790
+ return true;
12791
+ }
12792
+
12118
12793
  // src/workspaces.ts
12119
12794
  import { readdir, rm, stat } from "fs/promises";
12120
12795
  import path13 from "path";
@@ -13205,6 +13880,7 @@ function buildRuntimeErrorDiagnosticEnvelope(message) {
13205
13880
  const runtimeErrorReason = classifyRuntimeErrorReason(runtimeErrorClass);
13206
13881
  const runtimeErrorAction = classifyRuntimeErrorAction(runtimeErrorClass);
13207
13882
  const fingerprint = fingerprintRuntimeError(scrubbed);
13883
+ const inputTooLargeAttrs = runtimeErrorClass === "InputTooLargeError" ? extractInputTooLargeAttrs(rawMessage) : {};
13208
13884
  const spanAttrs = {
13209
13885
  turn_outcome: "failed",
13210
13886
  turn_subtype: "runtime_error",
@@ -13215,7 +13891,8 @@ function buildRuntimeErrorDiagnosticEnvelope(message) {
13215
13891
  runtime_error_fingerprint: fingerprint,
13216
13892
  runtime_error_message_present: rawMessage.length > 0,
13217
13893
  runtime_error_message_length_bucket: bucketLength(rawMessage.length),
13218
- runtime_error_message_truncated: truncated
13894
+ runtime_error_message_truncated: truncated,
13895
+ ...inputTooLargeAttrs
13219
13896
  };
13220
13897
  if (httpStatus !== null) {
13221
13898
  spanAttrs.runtime_error_http_status = httpStatus;
@@ -13239,6 +13916,10 @@ function formatRuntimeStartTimeoutMessage(runtimeId) {
13239
13916
  const runtimeLabel = runtimeDisplayName(runtimeId);
13240
13917
  return `${runtimeLabel} did not finish starting on this machine. Check that ${runtimeLabel} is installed, logged in, and can run non-interactively, then retry starting this agent.`;
13241
13918
  }
13919
+ function formatRuntimeInputTooLargeMessage(runtimeId) {
13920
+ const runtimeLabel = runtimeDisplayName(runtimeId);
13921
+ return `${runtimeLabel} reported input that is too large for the selected model. Reduce the current prompt or injected startup context. For a resumed session, compact it or start a new session before retrying.`;
13922
+ }
13242
13923
  function scrubRuntimeErrorDiagnosticText(value) {
13243
13924
  return value.replace(/\bBearer\s+[A-Za-z0-9._~+/=-]{8,}/gi, "Bearer [REDACTED_TOKEN]").replace(/\b(?:sk|sk-ant|sk-proj|xox[baprs]?)-[A-Za-z0-9_-]{8,}\b/g, "[REDACTED_TOKEN]").replace(/\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}\b/g, "[REDACTED_EMAIL]").replace(/https?:\/\/[^\s"'<>]+/gi, (url) => redactUrlQuery(url)).replace(/\/Users\/[^\s"'<>:]+(?:\/[^\s"'<>:]+)*/g, "[REDACTED_PATH]").replace(/\/home\/[^\s"'<>:]+(?:\/[^\s"'<>:]+)*/g, "[REDACTED_PATH]").replace(/[A-Za-z]:\\Users\\[^\s"'<>:]+(?:\\[^\s"'<>:]+)*/g, "[REDACTED_PATH]");
13244
13925
  }
@@ -13254,6 +13935,10 @@ function extractHttpStatus(message) {
13254
13935
  }
13255
13936
  function classifyRuntimeError(message, httpStatus) {
13256
13937
  const explicit = /\b([A-Z][A-Za-z0-9_]*(?:Error|Exception))\b/.exec(message);
13938
+ if (explicit && /InputTooLargeError/i.test(explicit[1])) return "InputTooLargeError";
13939
+ if (/\bINPUT_TOO_LARGE\b/i.test(message) || /\binput too large\b/i.test(message) || /\bexceeds the maximum allowed\b/i.test(message)) {
13940
+ return "InputTooLargeError";
13941
+ }
13257
13942
  if (explicit) return explicit[1];
13258
13943
  if (httpStatus !== null) {
13259
13944
  if (httpStatus === 429) return "RateLimitError";
@@ -13300,6 +13985,8 @@ function classifyRuntimeErrorReason(runtimeErrorClass) {
13300
13985
  return "not_found";
13301
13986
  case "ModelConfigError":
13302
13987
  return "model_config_error";
13988
+ case "InputTooLargeError":
13989
+ return "input_too_large";
13303
13990
  case "ProviderServerError":
13304
13991
  return "provider_server_error";
13305
13992
  case "ProviderApiError":
@@ -13308,6 +13995,34 @@ function classifyRuntimeErrorReason(runtimeErrorClass) {
13308
13995
  return "unclassified_runtime_error";
13309
13996
  }
13310
13997
  }
13998
+ function extractInputTooLargeAttrs(message) {
13999
+ const attrs = {};
14000
+ const estimatedTokens = firstIntegerMatch(message, [
14001
+ /\bestimated\s+([\d,]+)\s+tokens?\b/i
14002
+ ]);
14003
+ if (estimatedTokens !== null) attrs.runtime_input_estimated_tokens = estimatedTokens;
14004
+ const budgetTokens = firstIntegerMatch(message, [
14005
+ /\bbudget\s+([\d,]+)\b/i
14006
+ ]);
14007
+ if (budgetTokens !== null) attrs.runtime_input_budget_tokens = budgetTokens;
14008
+ const contextLimitTokens = firstIntegerMatch(message, [
14009
+ /\bcontext limit\s+([\d,]+)\b/i,
14010
+ /\bmaximum allowed[^()]*\(([\d,]+)\)/i
14011
+ ]);
14012
+ if (contextLimitTokens !== null) attrs.runtime_input_context_limit_tokens = contextLimitTokens;
14013
+ const model = /\bmodel\s+([A-Za-z0-9._:/+-]+)\b/i.exec(message);
14014
+ if (model) attrs.runtime_input_model = model[1];
14015
+ return attrs;
14016
+ }
14017
+ function firstIntegerMatch(message, patterns) {
14018
+ for (const pattern of patterns) {
14019
+ const match = pattern.exec(message);
14020
+ if (!match) continue;
14021
+ const parsed = Number.parseInt(match[1].replace(/,/g, ""), 10);
14022
+ if (Number.isSafeInteger(parsed)) return parsed;
14023
+ }
14024
+ return null;
14025
+ }
13311
14026
  function runtimeDisplayName(runtimeId) {
13312
14027
  switch (runtimeId) {
13313
14028
  case "antigravity":
@@ -13541,6 +14256,88 @@ var RuntimeNotificationState = class {
13541
14256
  }
13542
14257
  };
13543
14258
 
14259
+ // src/proxyFailureTrace.ts
14260
+ function failureReason(input) {
14261
+ if (input.lifecycleInvalidContext) return "local_daemon_state_invalid";
14262
+ const text = `${input.errorCause ?? ""} ${input.errorMessage}`.toLowerCase();
14263
+ if (/enotfound|eai_again|\bdns\b/.test(text)) return "dns";
14264
+ if (/econnrefused|econnreset|epipe|und_err_socket|\bsocket\b|other side closed|terminated/.test(text)) return "tcp";
14265
+ if (/certificate|\btls\b/.test(text)) return "tls";
14266
+ if (/und_err_headers_timeout|und_err_body_timeout|\btimeout\b/.test(text)) return "read_timeout";
14267
+ if (/\bproxy\b/.test(text)) return "proxy_connect";
14268
+ if (/\bfly\b/.test(text)) return "fly_edge";
14269
+ return "unknown";
14270
+ }
14271
+ function boundedErrorClass(value) {
14272
+ if (value === "TypeError") return "TypeError";
14273
+ if (value === "AbortError") return "AbortError";
14274
+ if (value === "Error") return "Error";
14275
+ return "OtherError";
14276
+ }
14277
+ function boundedMethod(value) {
14278
+ const method = value.toUpperCase();
14279
+ return ["GET", "POST", "PUT", "PATCH", "DELETE", "HEAD", "OPTIONS"].includes(method) ? method : "OTHER";
14280
+ }
14281
+ function cannedExcerpt(reason) {
14282
+ switch (reason) {
14283
+ case "local_daemon_state_invalid":
14284
+ return "Local daemon lifecycle state rejected the proxy request";
14285
+ case "dns":
14286
+ return "Upstream DNS resolution failed";
14287
+ case "tcp":
14288
+ return "Upstream TCP connection failed";
14289
+ case "tls":
14290
+ return "Upstream TLS negotiation failed";
14291
+ case "read_timeout":
14292
+ return "Upstream response timed out";
14293
+ case "proxy_connect":
14294
+ return "Upstream proxy connection failed";
14295
+ case "fly_edge":
14296
+ return "Upstream edge transport failed";
14297
+ case "unknown":
14298
+ return "Proxy request failed with an unclassified cause";
14299
+ }
14300
+ }
14301
+ function daemonProxyFailureTraceAttrs(input) {
14302
+ const reason = failureReason(input);
14303
+ return {
14304
+ route_family: routeFamilyForPath(input.pathname),
14305
+ method: boundedMethod(input.method),
14306
+ outcome: "error",
14307
+ reason,
14308
+ error_class: boundedErrorClass(input.errorName),
14309
+ error_excerpt: cannedExcerpt(reason),
14310
+ ...typeof input.responseStatusCode === "number" ? { response_status_code: input.responseStatusCode } : {},
14311
+ response_code_present: Boolean(input.responseCode)
14312
+ };
14313
+ }
14314
+ function daemonTransportErrorExcerpt(input) {
14315
+ if (input.normalizedCode === "local_daemon_state_invalid") {
14316
+ return "Local daemon lifecycle state rejected the proxy request";
14317
+ }
14318
+ if (input.normalizedCode === "server_5xx") return "Upstream server returned a 5xx response";
14319
+ switch (input.upstreamLayer) {
14320
+ case "dns":
14321
+ return "Upstream DNS resolution failed";
14322
+ case "tcp":
14323
+ return "Upstream TCP connection failed";
14324
+ case "tls":
14325
+ return "Upstream TLS negotiation failed";
14326
+ case "read_timeout":
14327
+ return "Upstream response timed out";
14328
+ case "proxy_connect":
14329
+ return "Upstream proxy connection failed";
14330
+ case "fly_edge":
14331
+ return "Upstream edge transport failed";
14332
+ case "body_decode_failure":
14333
+ return "Upstream response body could not be decoded";
14334
+ case "http_status":
14335
+ return "Upstream HTTP request failed";
14336
+ case "unknown":
14337
+ return "Proxy transport failed with an unclassified cause";
14338
+ }
14339
+ }
14340
+
13544
14341
  // src/agentProcessManager.ts
13545
14342
  var DEFAULT_MAX_CONCURRENT_AGENT_STARTS = 5;
13546
14343
  var DEFAULT_AGENT_START_INTERVAL_MS = 500;
@@ -14398,7 +15195,7 @@ Do not copy these answers verbatim.
14398
15195
  ## FAQ 15: How do I create agents or channels?
14399
15196
  ### Answer idea
14400
15197
  - If you have \`channel:create\` scope and your server role has channel-management authority, create channels directly with \`raft channel create --name <name>\` (add \`--private\` for private channels). This creates the channel under your agent identity and joins you to it.
14401
- - If you also have the matching channel-management scopes and authority, edit regular channels with \`raft channel update --target "#channel-name" --name "#new-name"\`, add humans or agents with \`raft channel add-member --target "#channel-name" --user @alice\` or \`--agent @scout\`, and remove them with \`raft channel remove-member --target "#channel-name" --user @alice\` or \`--agent @scout\`. Adding members is the direct follow-up for private channels you create under your agent identity.
15198
+ - If you also have the matching channel-management scopes and authority, edit regular channels with \`raft channel update --target "#channel-name" --name "#new-name"\`, freeze/restore writes with \`raft channel archive --target "#channel-name"\` and \`raft channel unarchive --target "#channel-name"\`, add humans or agents with \`raft channel add-member --target "#channel-name" --user @alice\` or \`--agent @scout\`, and remove them with \`raft channel remove-member --target "#channel-name" --user @alice\` or \`--agent @scout\`. Adding members is the direct follow-up for private channels you create under your agent identity.
14402
15199
  - When a human should review/commit the action, or when creating a new agent, **post an action card** with \`raft action prepare\`. The card lives inline in chat; the owner clicks the action button, the matching create dialog opens prefilled with your values (editable), and the resource is created under their identity when they submit.
14403
15200
  - v1 supports three action types via \`raft action prepare --target '<channel>' <<'RAFTACTION' { ... } RAFTACTION\`:
14404
15201
  - \`{type: "channel:create", name, visibility: "public" | "private", description?, initialHumans?: ["@alice"], initialAgents?: ["@scout"], draftHint?}\`
@@ -14412,7 +15209,7 @@ Do not copy these answers verbatim.
14412
15209
  - For direct channel creation, name the channel, create it, add needed members if requested/appropriate, then post the first useful update there. For human-committed actions, prefill the values you have, post the action card with a short \`draftHint\` explaining why these values, and tell the owner: "click the button on the card to review and commit." Then propose the first task to send once the card flips to Done.
14413
15210
 
14414
15211
  ### Guardrail
14415
- - Do not imply you created or edited a channel unless the corresponding \`raft channel create\` / \`raft channel update\` command succeeded. Do not imply you added or removed a channel member unless the corresponding member command succeeded. Do not imply you created an agent or a human-committed channel unless the card state is \`executed\`.
15212
+ - Do not imply you created, edited, archived, or unarchived a channel unless the corresponding \`raft channel create\` / \`update\` / \`archive\` / \`unarchive\` command succeeded. Do not imply you added or removed a channel member unless the corresponding member command succeeded. Do not imply you created an agent or a human-committed channel unless the card state is \`executed\`.
14416
15213
  - Do not prefill runtime / model / reasoning effort on \`agent:create\`. Computer placement is only allowed as the structured \`suggestedComputer\` / \`requiredComputer\` field when the owner's request includes that placement; never rely on \`draftHint\` for a computer constraint.
14417
15214
  - If the action type or direct CLI command the user wants is not yet supported, say so plainly and offer the manual UI path; do not invent action types the schema does not accept.
14418
15215
  `;
@@ -14846,7 +15643,9 @@ function runtimeDiagnosticTraceAttrs(event) {
14846
15643
  details_present: Boolean(event.details),
14847
15644
  path_present: Boolean(event.path),
14848
15645
  range_present: event.range !== void 0,
14849
- session_id_present: Boolean(event.sessionId)
15646
+ session_id_present: Boolean(event.sessionId),
15647
+ input_evidence: event.inputEvidence,
15648
+ reason_present: event.reasonPresent
14850
15649
  };
14851
15650
  }
14852
15651
  function runtimeRecoveryTrajectoryEntry(event) {
@@ -14915,10 +15714,11 @@ function classifyTerminalFailure(ap) {
14915
15714
  for (const text of candidates) {
14916
15715
  const diagnostics = buildRuntimeErrorDiagnosticEnvelope(text);
14917
15716
  const lower = text.toLowerCase();
14918
- if (lower.includes("usage limit") || lower.includes("quota exceeded") || lower.includes("quota limit") || lower.includes("budget limit exceeded") || lower.includes("usage not included in your plan") || lower.includes("modelnotfounderror") || lower.includes("requested entity was not found") || lower.includes("model deprecated") || lower.includes("model not found") || lower.includes("model is not supported") || lower.includes("unsupported model") || /\bmodel\b.*\bnot supported\b/i.test(text) || diagnostics.spanAttrs.runtime_error_action_required === true || isProviderStreamFailureText(text) || isRuntimeStartTimeoutText(text)) {
15717
+ if (lower.includes("usage limit") || lower.includes("quota exceeded") || lower.includes("quota limit") || lower.includes("budget limit exceeded") || lower.includes("usage not included in your plan") || lower.includes("modelnotfounderror") || lower.includes("requested entity was not found") || lower.includes("model deprecated") || lower.includes("model not found") || lower.includes("model is not supported") || lower.includes("unsupported model") || lower.includes("codex_zero_evidence_turn_completed") || /\bmodel\b.*\bnot supported\b/i.test(text) || diagnostics.spanAttrs.runtime_error_action_required === true || diagnostics.spanAttrs.runtime_error_class === "InputTooLargeError" || isProviderStreamFailureText(text) || isRuntimeStartTimeoutText(text)) {
14919
15718
  const actionRequired = diagnostics.spanAttrs.runtime_error_action_required === true;
15719
+ const inputTooLarge = diagnostics.spanAttrs.runtime_error_class === "InputTooLargeError";
14920
15720
  return {
14921
- detail: actionRequired ? formatRuntimeActionRequiredMessage(ap) : text,
15721
+ detail: actionRequired ? formatRuntimeActionRequiredMessage(ap) : inputTooLarge ? formatRuntimeInputTooLargeMessage(ap.driver.id) : text,
14922
15722
  actionRequired,
14923
15723
  ...actionRequired ? { entries: buildRuntimeActionRequiredEntries(ap, text, diagnostics) } : {}
14924
15724
  };
@@ -14930,6 +15730,7 @@ function classifyStickyTerminalFailure(ap) {
14930
15730
  const terminalFailure = classifyTerminalFailure(ap);
14931
15731
  if (!terminalFailure) return null;
14932
15732
  if (terminalFailure.actionRequired) return terminalFailure;
15733
+ if (/\bcodex_zero_evidence_turn_completed\b/i.test(terminalFailure.detail)) return terminalFailure;
14933
15734
  if (/\bmodel\b.*\bnot supported\b/i.test(terminalFailure.detail)) return terminalFailure;
14934
15735
  if (/\bunsupported\b.*\bmodel\b/i.test(terminalFailure.detail)) return terminalFailure;
14935
15736
  if (isProviderStreamFailureText(terminalFailure.detail)) return null;
@@ -15281,6 +16082,7 @@ var AgentProcessManager = class _AgentProcessManager {
15281
16082
  * of reconstructing it from unrelated fields.
15282
16083
  */
15283
16084
  daemonVersion;
16085
+ daemonInstanceId;
15284
16086
  computerVersion;
15285
16087
  workerUrl;
15286
16088
  fetchImpl;
@@ -15297,6 +16099,7 @@ var AgentProcessManager = class _AgentProcessManager {
15297
16099
  this.defaultAgentEnvVarsProvider = opts.defaultAgentEnvVarsProvider || null;
15298
16100
  this.tracer = opts.tracer ?? noopTracer;
15299
16101
  this.daemonVersion = opts.daemonVersion?.trim() || null;
16102
+ this.daemonInstanceId = opts.daemonInstanceId?.trim() || null;
15300
16103
  this.computerVersion = opts.computerVersion?.trim() || null;
15301
16104
  this.workerUrl = opts.workerUrl?.trim() || null;
15302
16105
  this.fetchImpl = opts.fetchImpl ?? daemonFetch;
@@ -16006,17 +16809,9 @@ var AgentProcessManager = class _AgentProcessManager {
16006
16809
  };
16007
16810
  }
16008
16811
  recordAgentProxyFailure(agentId, input) {
16009
- this.recordDaemonTrace("daemon.agent.proxy.failure", {
16812
+ this.recordDaemonTrace("daemon.proxy.failed", {
16010
16813
  agentId,
16011
- method: input.method,
16012
- path: input.pathname,
16013
- query_keys: input.queryKeys,
16014
- error_name: input.errorName,
16015
- error_message: input.errorMessage,
16016
- response_status_code: input.responseStatusCode,
16017
- response_code: input.responseCode,
16018
- lifecycle_invalid_agent_id: input.lifecycleInvalidAgentId,
16019
- lifecycle_invalid_context: input.lifecycleInvalidContext
16814
+ ...daemonProxyFailureTraceAttrs(input)
16020
16815
  }, "error");
16021
16816
  }
16022
16817
  recordAgentProxyTransportNormalizedError(agentId, input) {
@@ -16028,7 +16823,7 @@ var AgentProcessManager = class _AgentProcessManager {
16028
16823
  response_started: input.responseStarted,
16029
16824
  upstream_layer: input.upstreamLayer,
16030
16825
  ...typeof input.upstreamStatus === "number" ? { upstream_status: input.upstreamStatus } : {},
16031
- ...input.originalMessage ? { original_message: input.originalMessage } : {},
16826
+ error_excerpt: daemonTransportErrorExcerpt(input),
16032
16827
  launchId: input.launchId,
16033
16828
  target_host_class: input.targetHostClass,
16034
16829
  downstream_caller: input.downstreamCaller,
@@ -16055,6 +16850,7 @@ var AgentProcessManager = class _AgentProcessManager {
16055
16850
  detailKind: activity.statusEntry.detailKind ?? "daemon_activity",
16056
16851
  entries: activity.entries,
16057
16852
  launchId: ap?.launchId || void 0,
16853
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
16058
16854
  clientSeq: ap ? this.nextActivityClientSeq(agentId) : void 0,
16059
16855
  isHeartbeat: false
16060
16856
  });
@@ -16069,6 +16865,7 @@ var AgentProcessManager = class _AgentProcessManager {
16069
16865
  detailKind: ap.lastActivityDetailKind || "none",
16070
16866
  entries: [runtimeDiagnosticTrajectoryEntry(event)],
16071
16867
  launchId: ap.launchId || void 0,
16868
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
16072
16869
  clientSeq: this.nextActivityClientSeq(agentId),
16073
16870
  isHeartbeat: false
16074
16871
  });
@@ -16121,6 +16918,7 @@ var AgentProcessManager = class _AgentProcessManager {
16121
16918
  detailKind: ap.lastActivityDetailKind || "none",
16122
16919
  entries: [runtimeRecoveryTrajectoryEntry(event)],
16123
16920
  launchId: ap.launchId || void 0,
16921
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
16124
16922
  clientSeq: this.nextActivityClientSeq(agentId),
16125
16923
  isHeartbeat: false
16126
16924
  });
@@ -17219,8 +18017,14 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
17219
18017
  this.broadcastActivity(agentId, "error", visibleErrorMessage, [
17220
18018
  ...terminalFailure?.entries ?? [{ kind: "text", text: `Error: ${visibleErrorMessage}` }]
17221
18019
  ], agentProcess.launchId, "runtime_error");
18020
+ } else if (diagnostics?.spanAttrs.runtime_error_class === "InputTooLargeError") {
18021
+ const visibleErrorMessage = formatRuntimeInputTooLargeMessage(agentProcess.driver.id);
18022
+ this.broadcastActivity(agentId, "error", visibleErrorMessage, [
18023
+ { kind: "text", text: `Error: ${visibleErrorMessage}` }
18024
+ ], agentProcess.launchId, "runtime_error");
17222
18025
  }
17223
- throw new Error(`Runtime session failed to start: ${startResult.reason}${startResult.error ? ` (${startResult.error})` : ""}`);
18026
+ const visibleStartError = diagnostics?.spanAttrs.runtime_error_class === "InputTooLargeError" ? formatRuntimeInputTooLargeMessage(agentProcess.driver.id) : startResult.error;
18027
+ throw new Error(`Runtime session failed to start: ${startResult.reason}${visibleStartError ? ` (${visibleStartError})` : ""}`);
17224
18028
  }
17225
18029
  this.closeNoProcessResidency(agentId, "advanced");
17226
18030
  if (this.lifecycleRecords.deleteTerminalFailure(agentId)) {
@@ -18188,57 +18992,12 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
18188
18992
  pids: pids.join(",")
18189
18993
  });
18190
18994
  await Promise.all(ids.map((id) => this.stopAgent(id, { wait: true, silent: true })));
18191
- const survivors = pids.filter((pid) => {
18192
- try {
18193
- process.kill(pid, 0);
18194
- return true;
18195
- } catch {
18196
- return false;
18197
- }
18198
- });
18199
- if (survivors.length > 0) {
18200
- for (const pid of survivors) {
18201
- logger.warn(`[Daemon] Agent subprocess ${pid} survived stopAll; sending SIGKILL`);
18202
- try {
18203
- process.kill(pid, "SIGKILL");
18204
- } catch {
18205
- }
18206
- }
18207
- this.recordDaemonTrace("daemon.agent.stop_all.survivor_reaped", {
18208
- survivor_count: survivors.length,
18209
- survivor_pids: survivors.join(","),
18210
- reason: "shutdown_survivor",
18211
- signal: "SIGKILL"
18212
- });
18213
- const deadline = Date.now() + 2e3;
18214
- while (Date.now() < deadline) {
18215
- const alive = survivors.filter((pid) => {
18216
- try {
18217
- process.kill(pid, 0);
18218
- return true;
18219
- } catch {
18220
- return false;
18221
- }
18222
- });
18223
- if (alive.length === 0) break;
18224
- await new Promise((r) => setTimeout(r, 50));
18225
- }
18226
- const stillAlive = survivors.filter((pid) => {
18227
- try {
18228
- process.kill(pid, 0);
18229
- return true;
18230
- } catch {
18231
- return false;
18232
- }
18233
- });
18234
- const outcome = stillAlive.length > 0 ? "survivors_still_alive" : "survivors_killed";
18235
- this.recordDaemonTrace("daemon.agent.stop_all.completed", {
18236
- survivor_count: survivors.length,
18237
- reaped_count: survivors.length - stillAlive.length,
18238
- still_alive_count: stillAlive.length,
18239
- outcome
18240
- }, stillAlive.length > 0 ? "error" : "ok");
18241
- } else {
18995
+ const reapedSurvivors = await reapOrphanProcesses(
18996
+ pids,
18997
+ logger,
18998
+ (name, attrs, status) => this.recordDaemonTrace(name, attrs, status)
18999
+ );
19000
+ if (!reapedSurvivors) {
18242
19001
  this.recordDaemonTrace("daemon.agent.stop_all.completed", {
18243
19002
  agent_count: ids.length,
18244
19003
  survivor_count: 0,
@@ -18980,7 +19739,8 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
18980
19739
  const ap = this.agents.get(agentId);
18981
19740
  const entries = [...extraTrajectory];
18982
19741
  const hasToolStart = entries.some((e) => e.kind === "tool_start");
18983
- if (!hasToolStart) {
19742
+ const isThinkingProgressFrame = activityKind === "thinking" && detail === "" && detailKind === "none" && entries.every((e) => e.kind === "thinking" || e.kind === "text");
19743
+ if (!hasToolStart && !isThinkingProgressFrame) {
18984
19744
  entries.push({
18985
19745
  kind: "status",
18986
19746
  activity: activityKind,
@@ -19003,6 +19763,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
19003
19763
  detailKind,
19004
19764
  entries,
19005
19765
  launchId,
19766
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
19006
19767
  clientSeq,
19007
19768
  producerFactId,
19008
19769
  observedAtMs,
@@ -19034,6 +19795,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
19034
19795
  detail: ap.lastActivityDetail,
19035
19796
  detailKind: ap.lastActivityDetailKind,
19036
19797
  launchId: heartbeatLaunchId,
19798
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
19037
19799
  clientSeq: heartbeatClientSeq,
19038
19800
  producerFactId: heartbeatProducerFactId,
19039
19801
  observedAtMs: heartbeatObservedAtMs,
@@ -19083,7 +19845,8 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
19083
19845
  });
19084
19846
  }
19085
19847
  buildActivityProducerFactId(agentId, launchId, clientSeq) {
19086
- return `daemon_activity:${agentId}:${launchId ?? "legacy"}:${clientSeq}`;
19848
+ const daemonGeneration = this.daemonInstanceId ? `:${this.daemonInstanceId}` : "";
19849
+ return `daemon_activity:${agentId}:${launchId ?? "legacy"}${daemonGeneration}:${clientSeq}`;
19087
19850
  }
19088
19851
  /**
19089
19852
  * Respond to a server-issued `agent:activity_probe`. Echoes the
@@ -19123,6 +19886,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
19123
19886
  detail,
19124
19887
  detailKind,
19125
19888
  launchId,
19889
+ ...this.daemonInstanceId ? { daemonInstanceId: this.daemonInstanceId } : {},
19126
19890
  probeId,
19127
19891
  clientSeq,
19128
19892
  producerFactId,
@@ -19992,15 +20756,7 @@ Use \`raft message read\` to catch up on the channels listed above, then stop. R
19992
20756
  return true;
19993
20757
  }
19994
20758
  probeRuntimeProcessLiveness(ap) {
19995
- const pid = ap.runtime.pid;
19996
- if (typeof pid !== "number") return void 0;
19997
- try {
19998
- process.kill(pid, 0);
19999
- return true;
20000
- } catch (err) {
20001
- const code = typeof err === "object" && err !== null && "code" in err ? err.code : void 0;
20002
- return code === "EPERM" ? true : false;
20003
- }
20759
+ return ap.runtime.isAlive();
20004
20760
  }
20005
20761
  recoverStaleProcessForQueuedMessageIfNeeded(agentId, ap) {
20006
20762
  const staleForMs = ap.runtimeProgress.ageMs();
@@ -21384,6 +22140,9 @@ var DaemonConnection = class {
21384
22140
  launchId: msg.launchId,
21385
22141
  launch_id: msg.launchId,
21386
22142
  launch_id_present: Boolean(msg.launchId),
22143
+ daemonInstanceId: msg.daemonInstanceId,
22144
+ daemon_instance_id: msg.daemonInstanceId,
22145
+ daemon_instance_id_present: Boolean(msg.daemonInstanceId),
21387
22146
  clientSeq: msg.clientSeq,
21388
22147
  client_seq: msg.clientSeq,
21389
22148
  client_seq_present: typeof msg.clientSeq === "number",
@@ -21621,7 +22380,8 @@ var DIAGNOSTIC_ID_ATTRS = /* @__PURE__ */ new Set([
21621
22380
  "process_instance_id",
21622
22381
  "launch_id",
21623
22382
  "correlation_id",
21624
- "migration_attempt_id"
22383
+ "migration_attempt_id",
22384
+ "operation_id"
21625
22385
  ]);
21626
22386
  var DIAGNOSTIC_ERROR_ATTRS = /* @__PURE__ */ new Set([
21627
22387
  "runtime_error_class",
@@ -22073,23 +22833,190 @@ function readPositiveIntegerEnv2(name, fallback) {
22073
22833
  }
22074
22834
 
22075
22835
  // src/computerMigrationGuard.ts
22076
- import { existsSync as existsSync9, readdirSync as readdirSync6, readFileSync as readFileSync8 } from "fs";
22836
+ import { existsSync as existsSync9, readdirSync as readdirSync6, readFileSync as readFileSync9 } from "fs";
22077
22837
  import path18 from "path";
22838
+
22839
+ // src/legacySupervisor.ts
22840
+ import { execFileSync as execFileSync4 } from "child_process";
22841
+ import { readFileSync as readFileSync8 } from "fs";
22842
+ function execFileText(file, args) {
22843
+ try {
22844
+ return execFileSync4(file, args, {
22845
+ encoding: "utf8",
22846
+ timeout: 1e3,
22847
+ maxBuffer: 256 * 1024,
22848
+ stdio: ["ignore", "pipe", "ignore"]
22849
+ });
22850
+ } catch {
22851
+ return void 0;
22852
+ }
22853
+ }
22854
+ function readFileText(file) {
22855
+ try {
22856
+ return readFileSync8(file, "utf8");
22857
+ } catch {
22858
+ return void 0;
22859
+ }
22860
+ }
22861
+ function defaultProbe(pid) {
22862
+ return {
22863
+ pid,
22864
+ platform: process.platform,
22865
+ env: process.env,
22866
+ execFile: execFileText,
22867
+ readFile: readFileText
22868
+ };
22869
+ }
22870
+ function shellQuote(value) {
22871
+ return `'${value.replace(/'/g, `'\\''`)}'`;
22872
+ }
22873
+ function parentPid(probe, pid) {
22874
+ const stdout = probe.execFile("ps", ["-o", "ppid=", "-p", String(pid)]);
22875
+ const parsed = Number.parseInt(stdout?.trim() ?? "", 10);
22876
+ return Number.isInteger(parsed) && parsed > 0 ? parsed : void 0;
22877
+ }
22878
+ function processCommand(probe, pid) {
22879
+ return probe.execFile("ps", ["-o", "command=", "-p", String(pid)])?.trim().toLowerCase() ?? "";
22880
+ }
22881
+ function relatedProcessIds(probe) {
22882
+ const ids = [probe.pid];
22883
+ let current = probe.pid;
22884
+ for (let depth = 0; depth < 12; depth += 1) {
22885
+ const parent = parentPid(probe, current);
22886
+ if (!parent || ids.includes(parent)) break;
22887
+ ids.push(parent);
22888
+ if (parent === 1) break;
22889
+ current = parent;
22890
+ }
22891
+ return ids;
22892
+ }
22893
+ function detectPm2(probe, relatedPids) {
22894
+ const hasPm2Ancestor = relatedPids.slice(1).some((pid) => processCommand(probe, pid).includes("pm2"));
22895
+ const hasPm2Environment = Boolean(probe.env.PM2_HOME || probe.env.pm_id);
22896
+ if (!hasPm2Ancestor && !hasPm2Environment) return void 0;
22897
+ const pm2Json = probe.execFile("pm2", ["jlist"]);
22898
+ if (pm2Json) {
22899
+ try {
22900
+ const entries = JSON.parse(pm2Json);
22901
+ const entry = entries.find(
22902
+ (candidate) => typeof candidate.pid === "number" && relatedPids.includes(candidate.pid)
22903
+ );
22904
+ if (entry) {
22905
+ const name = typeof entry.name === "string" && entry.name.length > 0 ? entry.name : String(entry.pid);
22906
+ return {
22907
+ kind: "pm2",
22908
+ detail: `PM2 app ${JSON.stringify(name)} is supervising this legacy daemon.`,
22909
+ cleanupCommands: [`pm2 delete ${shellQuote(name)}`, "pm2 save"]
22910
+ };
22911
+ }
22912
+ } catch {
22913
+ }
22914
+ }
22915
+ return {
22916
+ kind: "pm2",
22917
+ detail: "PM2 is supervising this legacy daemon, but its app name could not be resolved.",
22918
+ cleanupCommands: ["pm2 delete <legacy-daemon-app-name>", "pm2 save"]
22919
+ };
22920
+ }
22921
+ function systemdUnitFromCgroup(cgroup) {
22922
+ if (!cgroup) return void 0;
22923
+ for (const line of cgroup.split("\n")) {
22924
+ const pathPart = line.slice(line.lastIndexOf(":") + 1);
22925
+ let unit;
22926
+ for (const segment of pathPart.split("/")) {
22927
+ if (segment.endsWith(".service") && segment.length > ".service".length && !/^user@\d+\.service$/.test(segment)) {
22928
+ unit = segment;
22929
+ }
22930
+ }
22931
+ if (unit) return { unit, user: pathPart.includes("/user.slice/") };
22932
+ }
22933
+ return void 0;
22934
+ }
22935
+ function detectSystemd(probe) {
22936
+ if (probe.platform !== "linux") return void 0;
22937
+ const cgroupUnit = systemdUnitFromCgroup(
22938
+ probe.readFile(`/proc/${probe.pid}/cgroup`)
22939
+ );
22940
+ const hasSystemdEvidence = cgroupUnit !== void 0 || probe.env.INVOCATION_ID !== void 0;
22941
+ if (!hasSystemdEvidence) return void 0;
22942
+ if (cgroupUnit) {
22943
+ const prefix = cgroupUnit.user ? "systemctl --user" : "sudo systemctl";
22944
+ return {
22945
+ kind: "systemd",
22946
+ detail: `systemd unit ${JSON.stringify(cgroupUnit.unit)} is supervising this legacy daemon.`,
22947
+ cleanupCommands: [
22948
+ `${prefix} disable --now ${shellQuote(cgroupUnit.unit)}`
22949
+ ]
22950
+ };
22951
+ }
22952
+ return {
22953
+ kind: "systemd",
22954
+ detail: "systemd is supervising this legacy daemon, but its unit name could not be resolved.",
22955
+ cleanupCommands: [
22956
+ "systemctl --user disable --now <legacy-daemon-unit>.service"
22957
+ ]
22958
+ };
22959
+ }
22960
+ function detectLaunchd(probe) {
22961
+ if (probe.platform !== "darwin") return void 0;
22962
+ const label = probe.env.LAUNCH_JOBKEY_LABEL || probe.env.XPC_SERVICE_NAME;
22963
+ if (!label || label === "0") return void 0;
22964
+ return {
22965
+ kind: "launchd",
22966
+ detail: `launchd job ${JSON.stringify(label)} is supervising this legacy daemon.`,
22967
+ cleanupCommands: [
22968
+ `launchctl bootout gui/$(id -u)/${shellQuote(label)}`,
22969
+ `rm -f ~/Library/LaunchAgents/${shellQuote(`${label}.plist`)}`
22970
+ ]
22971
+ };
22972
+ }
22973
+ function detectLegacyDaemonSupervisor(pid = process.pid) {
22974
+ return detectLegacyDaemonSupervisorWithProbe(defaultProbe(pid));
22975
+ }
22976
+ function detectLegacyDaemonSupervisorWithProbe(probe) {
22977
+ const relatedPids = relatedProcessIds(probe);
22978
+ return detectPm2(probe, relatedPids) ?? detectSystemd(probe) ?? detectLaunchd(probe);
22979
+ }
22980
+ var legacyDaemonSupervisorFallbackCommands = [
22981
+ "PM2: pm2 delete <legacy-daemon-app-name> && pm2 save",
22982
+ "systemd: systemctl --user disable --now <legacy-daemon-unit>.service",
22983
+ "launchd: launchctl bootout gui/$(id -u) ~/Library/LaunchAgents/<legacy-daemon-label>.plist && rm -f ~/Library/LaunchAgents/<legacy-daemon-label>.plist"
22984
+ ];
22985
+
22986
+ // src/computerMigrationGuard.ts
22078
22987
  var LegacyDaemonKeyAdoptedByComputerError = class extends Error {
22079
22988
  code = "LEGACY_DAEMON_KEY_ADOPTED_BY_COMPUTER";
22080
22989
  attachmentPath;
22081
22990
  serverId;
22082
- constructor(match) {
22991
+ constructor(match, supervisor = detectLegacyDaemonSupervisor() ?? null) {
22083
22992
  const serverDisplay = match.serverSlug ? `/${match.serverSlug}` : match.serverId;
22084
22993
  const startCommand = match.serverSlug ? `raft-computer start /${match.serverSlug}` : "raft-computer start";
22994
+ const statusCommand = match.serverSlug ? `raft-computer status /${match.serverSlug}` : "raft-computer status";
22995
+ const supervisorGuidance = formatSupervisorGuidance(
22996
+ supervisor ?? void 0
22997
+ );
22085
22998
  super(
22086
- `This legacy daemon key was already adopted by Raft Computer for ${serverDisplay}. Start the Computer supervisor instead: ${startCommand}. Legacy daemon startup is blocked to avoid relaunching a migrated machine key.`
22999
+ `Legacy Raft daemon startup refused: this machine key was already migrated to Raft Computer for ${serverDisplay}.
23000
+ Raft Computer now owns this connection; do not restart raft-daemon with the migrated key.
23001
+ ${supervisorGuidance}
23002
+ Then start and verify Raft Computer:
23003
+ ${startCommand}
23004
+ ${statusCommand}`
22087
23005
  );
22088
23006
  this.name = "LegacyDaemonKeyAdoptedByComputerError";
22089
23007
  this.attachmentPath = match.attachmentPath;
22090
23008
  this.serverId = match.serverId;
22091
23009
  }
22092
23010
  };
23011
+ function formatSupervisorGuidance(supervisor) {
23012
+ if (supervisor) {
23013
+ return `${supervisor.detail}
23014
+ Remove the old supervisor entry so it cannot auto-restart:
23015
+ ` + supervisor.cleanupCommands.map((command) => ` ${command}`).join("\n");
23016
+ }
23017
+ return `If a process manager keeps restarting the old daemon, remove the entry you configured:
23018
+ ` + legacyDaemonSupervisorFallbackCommands.map((command) => ` ${command}`).join("\n");
23019
+ }
22093
23020
  function daemonApiKeyFingerprint(apiKey) {
22094
23021
  return getDaemonMachineLockId(apiKey).slice("machine-".length);
22095
23022
  }
@@ -22106,7 +23033,7 @@ function findAdoptedComputerForLegacyFingerprint(slockHome, legacyApiKeyFingerpr
22106
23033
  const attachmentPath = path18.join(serversDir, serverId, "runner.state.json");
22107
23034
  let raw;
22108
23035
  try {
22109
- raw = readFileSync8(attachmentPath, "utf8");
23036
+ raw = readFileSync9(attachmentPath, "utf8");
22110
23037
  } catch {
22111
23038
  continue;
22112
23039
  }
@@ -22128,7 +23055,10 @@ function findAdoptedComputerForLegacyFingerprint(slockHome, legacyApiKeyFingerpr
22128
23055
  }
22129
23056
  function assertLegacyDaemonKeyNotAdoptedByComputer(options) {
22130
23057
  const legacyApiKeyFingerprint = daemonApiKeyFingerprint(options.apiKey);
22131
- const match = findAdoptedComputerForLegacyFingerprint(options.slockHome, legacyApiKeyFingerprint);
23058
+ const match = findAdoptedComputerForLegacyFingerprint(
23059
+ options.slockHome,
23060
+ legacyApiKeyFingerprint
23061
+ );
22132
23062
  if (match) throw new LegacyDaemonKeyAdoptedByComputerError(match);
22133
23063
  }
22134
23064
 
@@ -22649,8 +23579,13 @@ function onceDrain(res) {
22649
23579
 
22650
23580
  // src/agentMigrationObjectStoreBundle.ts
22651
23581
  import { createHash as createHash9 } from "crypto";
22652
- import { lstat as lstat3, mkdir as mkdir3, readFile as readFile4, readlink as readlink2, rm as rm3, symlink, writeFile as writeFile3 } from "fs/promises";
23582
+ import { createReadStream as createReadStream2, createWriteStream } from "fs";
23583
+ import { lstat as lstat3, mkdir as mkdir3, readlink as readlink2, rm as rm3, symlink } from "fs/promises";
22653
23584
  import path20 from "path";
23585
+ import { Transform } from "stream";
23586
+ import { pipeline } from "stream/promises";
23587
+ import { createGunzip, createGzip } from "zlib";
23588
+ import { extract, pack } from "tar-stream";
22654
23589
 
22655
23590
  // src/agentMigrationExport.ts
22656
23591
  import { createHash as createHash8 } from "crypto";
@@ -22659,11 +23594,15 @@ import { lstat as lstat2, readdir as readdir4, readFile as readFile3, readlink }
22659
23594
  import path19 from "path";
22660
23595
  var AGENT_MIGRATION_BUNDLE_SCHEMA_VERSION = "agent-bundle/v1";
22661
23596
  var REGENERABLE_DIRECTORY_NAMES = [
23597
+ ".cache",
23598
+ ".gradle",
23599
+ ".pnpm-store",
22662
23600
  ".venv",
22663
23601
  "__pycache__",
22664
23602
  "dist",
22665
23603
  "node_modules",
22666
- "target"
23604
+ "target",
23605
+ "vendor"
22667
23606
  ];
22668
23607
  var SECRET_FILE_NAMES = /* @__PURE__ */ new Set([
22669
23608
  ".env",
@@ -22780,9 +23719,9 @@ async function includeWorkspacePath(workspaceRelativePath, state, opts) {
22780
23719
  const normalizedRelativePath = normalizeRelativePath(workspaceRelativePath);
22781
23720
  if (state.seenWorkspacePaths.has(normalizedRelativePath)) return;
22782
23721
  const sourcePath = path19.join(state.workspace, normalizedRelativePath);
22783
- let stat4;
23722
+ let stat5;
22784
23723
  try {
22785
- stat4 = await lstat2(sourcePath);
23724
+ stat5 = await lstat2(sourcePath);
22786
23725
  } catch {
22787
23726
  state.unreachable.push({
22788
23727
  path: normalizedRelativePath,
@@ -22791,7 +23730,7 @@ async function includeWorkspacePath(workspaceRelativePath, state, opts) {
22791
23730
  });
22792
23731
  return;
22793
23732
  }
22794
- if (stat4.isDirectory()) {
23733
+ if (stat5.isDirectory()) {
22795
23734
  if (!opts.forceIncludeRegenerable && isRegenerablePath(normalizedRelativePath)) {
22796
23735
  state.excludedRegenerable.push({
22797
23736
  path: normalizedRelativePath,
@@ -22809,10 +23748,10 @@ async function includeWorkspacePath(workspaceRelativePath, state, opts) {
22809
23748
  sourcePath,
22810
23749
  workspaceRelativePath: normalizedRelativePath,
22811
23750
  bundlePath: `workspace/${normalizedRelativePath}`,
22812
- mode: stat4.mode,
22813
- mtimeMs: stat4.mtimeMs
23751
+ mode: stat5.mode,
23752
+ mtimeMs: stat5.mtimeMs
22814
23753
  };
22815
- if (stat4.isSymbolicLink()) {
23754
+ if (stat5.isSymbolicLink()) {
22816
23755
  state.files.push({
22817
23756
  ...baseEntry,
22818
23757
  kind: "symlink",
@@ -22820,7 +23759,7 @@ async function includeWorkspacePath(workspaceRelativePath, state, opts) {
22820
23759
  });
22821
23760
  return;
22822
23761
  }
22823
- if (!stat4.isFile()) {
23762
+ if (!stat5.isFile()) {
22824
23763
  state.unreachable.push({
22825
23764
  path: normalizedRelativePath,
22826
23765
  sourcePath,
@@ -22835,7 +23774,7 @@ async function includeWorkspacePath(workspaceRelativePath, state, opts) {
22835
23774
  state.files.push({
22836
23775
  ...baseEntry,
22837
23776
  kind: "file",
22838
- sizeBytes: stat4.size,
23777
+ sizeBytes: stat5.size,
22839
23778
  sha256: await sha256File(sourcePath),
22840
23779
  secretShapes: secretShapes.length > 0 ? secretShapes : void 0
22841
23780
  });
@@ -22854,9 +23793,9 @@ async function buildCrossTreeRefs(refs) {
22854
23793
  reason: ref.reason
22855
23794
  };
22856
23795
  try {
22857
- const stat4 = await lstat2(sourcePath);
22858
- if (stat4.isFile()) {
22859
- entry.sizeBytes = stat4.size;
23796
+ const stat5 = await lstat2(sourcePath);
23797
+ if (stat5.isFile()) {
23798
+ entry.sizeBytes = stat5.size;
22860
23799
  entry.sha256 = await sha256File(sourcePath);
22861
23800
  }
22862
23801
  } catch {
@@ -22974,9 +23913,22 @@ function sortByPath(entries) {
22974
23913
  }
22975
23914
 
22976
23915
  // src/agentMigrationObjectStoreBundle.ts
22977
- var AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION = "agent-object-store-bundle/v1";
22978
- var AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE = "application/vnd.slock.agent-migration-bundle";
23916
+ var AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION = "agent-object-store-tar/v2";
23917
+ var AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE = "application/vnd.raft.agent-migration-bundle+tar+gzip";
23918
+ var ARCHIVE_MANIFEST_PATH = "manifest.json";
23919
+ var ARCHIVE_WORKSPACE_PREFIX = "workspace/";
23920
+ var MAX_ARCHIVE_MANIFEST_BYTES = 64 * 1024 * 1024;
23921
+ var AgentMigrationObjectStoreBundleTooLargeError = class extends Error {
23922
+ constructor(actualBytes, maxBytes) {
23923
+ super(`MIGRATION_OBJECT_STORE_BUNDLE_TOO_LARGE:actualBytes=${actualBytes}:maxBytes=${maxBytes}`);
23924
+ this.actualBytes = actualBytes;
23925
+ this.maxBytes = maxBytes;
23926
+ this.name = "AgentMigrationObjectStoreBundleTooLargeError";
23927
+ }
23928
+ code = "MIGRATION_OBJECT_STORE_BUNDLE_TOO_LARGE";
23929
+ };
22979
23930
  async function buildAgentMigrationObjectStoreBundle(input) {
23931
+ assertPositiveMaxBytes(input.maxBytes);
22980
23932
  const workspacePath = path20.resolve(input.workspacePath);
22981
23933
  const manifest = await buildAgentMigrationExportManifest({
22982
23934
  agentId: input.agentId,
@@ -22984,45 +23936,32 @@ async function buildAgentMigrationObjectStoreBundle(input) {
22984
23936
  workspacePath,
22985
23937
  mode: "forensic"
22986
23938
  });
22987
- const files = [];
22988
- for (const entry of manifest.files) {
22989
- if (entry.source !== "workspace" || !entry.workspaceRelativePath) {
22990
- throw new Error("MIGRATION_OBJECT_STORE_UNSUPPORTED_ENTRY");
22991
- }
22992
- const sourcePath = path20.resolve(entry.sourcePath);
22993
- if (entry.kind === "symlink") {
22994
- files.push({
22995
- kind: "symlink",
22996
- workspaceRelativePath: normalizeWorkspaceRelativePath(entry.workspaceRelativePath),
22997
- linkTarget: entry.linkTarget ?? await readlink2(sourcePath)
22998
- });
22999
- continue;
23000
- }
23001
- const stat4 = await lstat3(sourcePath);
23002
- if (!stat4.isFile()) throw new Error("MIGRATION_OBJECT_STORE_FILE_KIND_MISMATCH");
23003
- files.push({
23004
- kind: "file",
23005
- workspaceRelativePath: normalizeWorkspaceRelativePath(entry.workspaceRelativePath),
23006
- contentBase64: (await readFile4(sourcePath)).toString("base64")
23007
- });
23008
- }
23009
- const payload = {
23939
+ const contentBytes = assertAgentMigrationObjectStoreBundleSize(manifest, input.maxBytes);
23940
+ const archiveManifest = {
23010
23941
  schemaVersion: AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION,
23011
- manifest,
23012
- files
23942
+ manifest
23013
23943
  };
23014
- const bundle = Buffer.from(`${JSON.stringify(sortJsonValue2(payload))}
23944
+ const manifestBuffer = Buffer.from(`${canonicalJson2(archiveManifest)}
23015
23945
  `, "utf8");
23016
- if (!Number.isSafeInteger(input.maxBytes) || input.maxBytes <= 0 || bundle.byteLength > input.maxBytes) {
23017
- throw new Error("MIGRATION_OBJECT_STORE_BUNDLE_TOO_LARGE");
23018
- }
23946
+ if (manifestBuffer.byteLength > MAX_ARCHIVE_MANIFEST_BYTES) {
23947
+ throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_TOO_LARGE");
23948
+ }
23949
+ const tarPack = pack();
23950
+ const gzip = createGzip();
23951
+ const bundle = tarPack.pipe(gzip);
23952
+ tarPack.on("error", (error) => gzip.destroy(error));
23953
+ void writeArchive(tarPack, manifestBuffer, manifest, workspacePath).catch((error) => {
23954
+ tarPack.destroy(error instanceof Error ? error : new Error(String(error)));
23955
+ });
23019
23956
  return {
23020
23957
  bundle,
23021
- manifestSha256: sha256Buffer2(Buffer.from(canonicalJson2(manifest), "utf8"))
23958
+ manifest,
23959
+ manifestSha256: sha256Buffer2(Buffer.from(canonicalJson2(manifest), "utf8")),
23960
+ contentBytes
23022
23961
  };
23023
23962
  }
23024
23963
  async function stageAgentMigrationObjectStoreBundle(input) {
23025
- const parsed = parseObjectStoreBundle(input.bundle);
23964
+ assertPositiveMaxBytes(input.maxBytes);
23026
23965
  const stagingWorkspacePath = path20.join(
23027
23966
  path20.resolve(input.slockHome),
23028
23967
  "migrations",
@@ -23031,45 +23970,198 @@ async function stageAgentMigrationObjectStoreBundle(input) {
23031
23970
  );
23032
23971
  await rm3(stagingWorkspacePath, { recursive: true, force: true });
23033
23972
  await mkdir3(stagingWorkspacePath, { recursive: true });
23034
- for (const file of parsed.files) {
23035
- const relativePath = normalizeWorkspaceRelativePath(file.workspaceRelativePath);
23036
- const targetPath = path20.join(stagingWorkspacePath, relativePath);
23037
- await mkdir3(path20.dirname(targetPath), { recursive: true });
23038
- if (file.kind === "symlink") {
23039
- if (!file.linkTarget) throw new Error("MIGRATION_OBJECT_STORE_LINK_TARGET_MISSING");
23040
- await symlink(file.linkTarget, targetPath);
23973
+ let archiveManifest = null;
23974
+ let expectedEntries = /* @__PURE__ */ new Map();
23975
+ const extractedEntries = /* @__PURE__ */ new Set();
23976
+ let contentBytes = 0;
23977
+ const tarExtract = extract();
23978
+ tarExtract.on("entry", (header, stream, next) => {
23979
+ void handleArchiveEntry({
23980
+ header,
23981
+ stream,
23982
+ stagingWorkspacePath,
23983
+ maxBytes: input.maxBytes,
23984
+ getArchiveManifest: () => archiveManifest,
23985
+ setArchiveManifest: (value) => {
23986
+ archiveManifest = value;
23987
+ expectedEntries = expectedWorkspaceEntries(value.manifest);
23988
+ },
23989
+ getExpectedEntries: () => expectedEntries,
23990
+ extractedEntries,
23991
+ addContentBytes: (value) => {
23992
+ contentBytes += value;
23993
+ if (contentBytes > input.maxBytes) {
23994
+ throw new AgentMigrationObjectStoreBundleTooLargeError(contentBytes, input.maxBytes);
23995
+ }
23996
+ }
23997
+ }).then(() => next(), next);
23998
+ });
23999
+ try {
24000
+ await pipeline(input.bundle, createGunzip(), tarExtract);
24001
+ const completedManifest = archiveManifest;
24002
+ if (!completedManifest) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_MISSING");
24003
+ for (const relativePath of expectedEntries.keys()) {
24004
+ if (!extractedEntries.has(relativePath)) {
24005
+ throw new Error(`MIGRATION_OBJECT_STORE_ARCHIVE_ENTRY_MISSING:${relativePath}`);
24006
+ }
24007
+ }
24008
+ return {
24009
+ manifest: completedManifest.manifest,
24010
+ manifestSha256: sha256Buffer2(
24011
+ Buffer.from(canonicalJson2(completedManifest.manifest), "utf8")
24012
+ ),
24013
+ stagingWorkspacePath,
24014
+ contentBytes
24015
+ };
24016
+ } catch (error) {
24017
+ await rm3(stagingWorkspacePath, { recursive: true, force: true });
24018
+ throw error;
24019
+ }
24020
+ }
24021
+ async function writeArchive(tarPack, manifestBuffer, manifest, workspacePath) {
24022
+ await writeBufferedEntry(tarPack, {
24023
+ name: ARCHIVE_MANIFEST_PATH,
24024
+ type: "file",
24025
+ size: manifestBuffer.byteLength,
24026
+ mode: 384,
24027
+ mtime: new Date(manifest.createdAt)
24028
+ }, manifestBuffer);
24029
+ for (const entry of manifest.files) {
24030
+ if (entry.source !== "workspace" || !entry.workspaceRelativePath) {
24031
+ throw new Error("MIGRATION_OBJECT_STORE_UNSUPPORTED_ENTRY");
24032
+ }
24033
+ const relativePath = normalizeWorkspaceRelativePath(entry.workspaceRelativePath);
24034
+ const sourcePath = path20.resolve(entry.sourcePath);
24035
+ const archivePath = `${ARCHIVE_WORKSPACE_PREFIX}${relativePath}`;
24036
+ if (entry.kind === "symlink") {
24037
+ await writeBufferedEntry(tarPack, {
24038
+ name: archivePath,
24039
+ type: "symlink",
24040
+ size: 0,
24041
+ mode: archiveMode(entry.mode),
24042
+ mtime: archiveMtime(entry.mtimeMs),
24043
+ linkname: entry.linkTarget ?? await readlink2(sourcePath)
24044
+ }, Buffer.alloc(0));
23041
24045
  continue;
23042
24046
  }
23043
- if (file.kind !== "file" || typeof file.contentBase64 !== "string") {
23044
- throw new Error("MIGRATION_OBJECT_STORE_FILE_CONTENT_MISSING");
24047
+ const stat5 = await lstat3(sourcePath);
24048
+ if (!stat5.isFile() || stat5.size !== entry.sizeBytes) {
24049
+ throw new Error(`MIGRATION_OBJECT_STORE_FILE_CHANGED:${relativePath}`);
23045
24050
  }
23046
- await writeFile3(targetPath, Buffer.from(file.contentBase64, "base64"), { mode: 384 });
24051
+ const tarEntry = tarPack.entry({
24052
+ name: archivePath,
24053
+ type: "file",
24054
+ size: stat5.size,
24055
+ mode: archiveMode(entry.mode),
24056
+ mtime: archiveMtime(entry.mtimeMs)
24057
+ });
24058
+ await pipeline(createReadStream2(sourcePath), tarEntry);
24059
+ }
24060
+ tarPack.finalize();
24061
+ }
24062
+ async function handleArchiveEntry(input) {
24063
+ if (input.header.name === ARCHIVE_MANIFEST_PATH) {
24064
+ if (input.getArchiveManifest()) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_DUPLICATE");
24065
+ if (input.header.type !== "file") throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_INVALID");
24066
+ const manifestBuffer = await readEntryBuffer(input.stream, MAX_ARCHIVE_MANIFEST_BYTES);
24067
+ input.setArchiveManifest(parseArchiveManifest(manifestBuffer));
24068
+ return;
24069
+ }
24070
+ const archiveManifest = input.getArchiveManifest();
24071
+ if (!archiveManifest) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_MUST_BE_FIRST");
24072
+ if (!input.header.name.startsWith(ARCHIVE_WORKSPACE_PREFIX)) {
24073
+ throw new Error("MIGRATION_OBJECT_STORE_ARCHIVE_ENTRY_UNEXPECTED");
24074
+ }
24075
+ const relativePath = normalizeWorkspaceRelativePath(
24076
+ input.header.name.slice(ARCHIVE_WORKSPACE_PREFIX.length)
24077
+ );
24078
+ if (input.extractedEntries.has(relativePath)) {
24079
+ throw new Error(`MIGRATION_OBJECT_STORE_ARCHIVE_ENTRY_DUPLICATE:${relativePath}`);
24080
+ }
24081
+ const expected = input.getExpectedEntries().get(relativePath);
24082
+ if (!expected) throw new Error(`MIGRATION_OBJECT_STORE_ARCHIVE_ENTRY_UNEXPECTED:${relativePath}`);
24083
+ input.extractedEntries.add(relativePath);
24084
+ const targetPath = path20.join(input.stagingWorkspacePath, relativePath);
24085
+ await mkdir3(path20.dirname(targetPath), { recursive: true });
24086
+ if (expected.kind === "symlink") {
24087
+ if (input.header.type !== "symlink" || input.header.linkname !== expected.linkTarget) {
24088
+ throw new Error(`MIGRATION_OBJECT_STORE_LINK_TARGET_MISMATCH:${relativePath}`);
24089
+ }
24090
+ await drainEntry(input.stream);
24091
+ await symlink(expected.linkTarget ?? "", targetPath);
24092
+ return;
24093
+ }
24094
+ if (input.header.type !== "file" || input.header.size !== expected.sizeBytes) {
24095
+ throw new Error(`MIGRATION_OBJECT_STORE_FILE_SIZE_MISMATCH:${relativePath}`);
24096
+ }
24097
+ input.addContentBytes(input.header.size ?? 0);
24098
+ const hash = createHash9("sha256");
24099
+ const hashPassThrough = new Transform({
24100
+ transform(chunk, _encoding, callback) {
24101
+ hash.update(chunk);
24102
+ callback(null, chunk);
24103
+ }
24104
+ });
24105
+ await pipeline(
24106
+ input.stream,
24107
+ hashPassThrough,
24108
+ createWriteStream(targetPath, { mode: archiveMode(expected.mode) })
24109
+ );
24110
+ if (expected.sha256 && hash.digest("hex") !== expected.sha256) {
24111
+ throw new Error(`MIGRATION_OBJECT_STORE_FILE_HASH_MISMATCH:${relativePath}`);
23047
24112
  }
23048
- return {
23049
- manifest: parsed.manifest,
23050
- manifestSha256: sha256Buffer2(Buffer.from(canonicalJson2(parsed.manifest), "utf8")),
23051
- stagingWorkspacePath
23052
- };
23053
24113
  }
23054
- function parseObjectStoreBundle(buffer) {
24114
+ function parseArchiveManifest(buffer) {
23055
24115
  let parsed;
23056
24116
  try {
23057
24117
  parsed = JSON.parse(buffer.toString("utf8"));
23058
24118
  } catch {
23059
- throw new Error("MIGRATION_OBJECT_STORE_BUNDLE_INVALID_JSON");
24119
+ throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_INVALID_JSON");
23060
24120
  }
23061
24121
  if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
23062
- throw new Error("MIGRATION_OBJECT_STORE_BUNDLE_INVALID");
24122
+ throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_INVALID");
23063
24123
  }
23064
- const bundle = parsed;
23065
- if (bundle.schemaVersion !== AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION) {
24124
+ const archiveManifest = parsed;
24125
+ if (archiveManifest.schemaVersion !== AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION) {
23066
24126
  throw new Error("MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_UNSUPPORTED");
23067
24127
  }
23068
- if (!bundle.manifest || typeof bundle.manifest !== "object" || Array.isArray(bundle.manifest)) {
23069
- throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_MISSING");
24128
+ if (!archiveManifest.manifest || typeof archiveManifest.manifest !== "object" || Array.isArray(archiveManifest.manifest) || archiveManifest.manifest.schemaVersion !== AGENT_MIGRATION_BUNDLE_SCHEMA_VERSION || !Array.isArray(archiveManifest.manifest.files)) {
24129
+ throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_INVALID");
24130
+ }
24131
+ return archiveManifest;
24132
+ }
24133
+ function expectedWorkspaceEntries(manifest) {
24134
+ const result = /* @__PURE__ */ new Map();
24135
+ for (const entry of manifest.files) {
24136
+ if (entry.source !== "workspace" || !entry.workspaceRelativePath) {
24137
+ throw new Error("MIGRATION_OBJECT_STORE_UNSUPPORTED_ENTRY");
24138
+ }
24139
+ const relativePath = normalizeWorkspaceRelativePath(entry.workspaceRelativePath);
24140
+ if (result.has(relativePath)) {
24141
+ throw new Error(`MIGRATION_OBJECT_STORE_MANIFEST_ENTRY_DUPLICATE:${relativePath}`);
24142
+ }
24143
+ result.set(relativePath, entry);
24144
+ }
24145
+ return result;
24146
+ }
24147
+ function assertAgentMigrationObjectStoreBundleSize(manifest, maxBytes) {
24148
+ assertPositiveMaxBytes(maxBytes);
24149
+ let total = 0;
24150
+ for (const entry of manifest.files) {
24151
+ if (entry.source !== "workspace" || !entry.workspaceRelativePath) {
24152
+ throw new Error("MIGRATION_OBJECT_STORE_UNSUPPORTED_ENTRY");
24153
+ }
24154
+ if (entry.kind !== "file") continue;
24155
+ if (!Number.isSafeInteger(entry.sizeBytes) || (entry.sizeBytes ?? -1) < 0) {
24156
+ throw new Error("MIGRATION_OBJECT_STORE_FILE_SIZE_INVALID");
24157
+ }
24158
+ total += entry.sizeBytes ?? 0;
24159
+ if (!Number.isSafeInteger(total)) throw new Error("MIGRATION_OBJECT_STORE_FILE_SIZE_INVALID");
24160
+ }
24161
+ if (total > maxBytes) {
24162
+ throw new AgentMigrationObjectStoreBundleTooLargeError(total, maxBytes);
23070
24163
  }
23071
- if (!Array.isArray(bundle.files)) throw new Error("MIGRATION_OBJECT_STORE_FILES_MISSING");
23072
- return bundle;
24164
+ return total;
23073
24165
  }
23074
24166
  function normalizeWorkspaceRelativePath(relativePath) {
23075
24167
  const normalized = path20.posix.normalize(relativePath.replaceAll("\\", "/"));
@@ -23078,6 +24170,40 @@ function normalizeWorkspaceRelativePath(relativePath) {
23078
24170
  }
23079
24171
  return normalized;
23080
24172
  }
24173
+ function writeBufferedEntry(tarPack, header, buffer) {
24174
+ return new Promise((resolve, reject) => {
24175
+ tarPack.entry(header, buffer, (error) => {
24176
+ if (error) reject(error);
24177
+ else resolve();
24178
+ });
24179
+ });
24180
+ }
24181
+ async function readEntryBuffer(stream, maxBytes) {
24182
+ const chunks = [];
24183
+ let total = 0;
24184
+ for await (const chunk of stream) {
24185
+ const buffer = Buffer.from(chunk);
24186
+ total += buffer.byteLength;
24187
+ if (total > maxBytes) throw new Error("MIGRATION_OBJECT_STORE_MANIFEST_TOO_LARGE");
24188
+ chunks.push(buffer);
24189
+ }
24190
+ return Buffer.concat(chunks, total);
24191
+ }
24192
+ async function drainEntry(stream) {
24193
+ for await (const _chunk of stream) {
24194
+ }
24195
+ }
24196
+ function assertPositiveMaxBytes(maxBytes) {
24197
+ if (!Number.isSafeInteger(maxBytes) || maxBytes <= 0) {
24198
+ throw new Error("MIGRATION_OBJECT_STORE_MAX_BYTES_INVALID");
24199
+ }
24200
+ }
24201
+ function archiveMode(mode) {
24202
+ return typeof mode === "number" ? mode & 511 : 384;
24203
+ }
24204
+ function archiveMtime(mtimeMs) {
24205
+ return typeof mtimeMs === "number" && Number.isFinite(mtimeMs) ? new Date(mtimeMs) : /* @__PURE__ */ new Date(0);
24206
+ }
23081
24207
  function canonicalJson2(value) {
23082
24208
  return JSON.stringify(sortJsonValue2(value));
23083
24209
  }
@@ -23098,8 +24224,8 @@ function sanitizePathSegment(value) {
23098
24224
 
23099
24225
  // src/agentMigrationImport.ts
23100
24226
  import { createHash as createHash10 } from "crypto";
23101
- import { createReadStream as createReadStream2 } from "fs";
23102
- import { access as access2, cp, lstat as lstat4, mkdir as mkdir4, readlink as readlink3, rename, writeFile as writeFile4 } from "fs/promises";
24227
+ import { createReadStream as createReadStream3 } from "fs";
24228
+ import { access as access2, cp, lstat as lstat4, mkdir as mkdir4, readlink as readlink3, rename, writeFile as writeFile3 } from "fs/promises";
23103
24229
  import path21 from "path";
23104
24230
  async function buildAgentMigrationAdoptPlan(input) {
23105
24231
  const slockHome = path21.resolve(input.slockHome);
@@ -23288,19 +24414,25 @@ async function placeWorkspace(sourceWorkspacePath, finalWorkspacePath) {
23288
24414
  if (path21.resolve(sourceWorkspacePath) === path21.resolve(finalWorkspacePath)) return;
23289
24415
  const stagingPath = `${finalWorkspacePath}.migration-${process.pid}-${Date.now()}`;
23290
24416
  await mkdir4(path21.dirname(finalWorkspacePath), { recursive: true });
23291
- await cp(sourceWorkspacePath, stagingPath, { recursive: true, dereference: false, errorOnExist: true, force: false });
24417
+ await cp(sourceWorkspacePath, stagingPath, {
24418
+ recursive: true,
24419
+ dereference: false,
24420
+ verbatimSymlinks: true,
24421
+ errorOnExist: true,
24422
+ force: false
24423
+ });
23292
24424
  await rename(stagingPath, finalWorkspacePath);
23293
24425
  }
23294
24426
  async function writeArrivalReport(reportPath, report) {
23295
24427
  const payload = `${canonicalJson3(report)}
23296
24428
  `;
23297
24429
  await mkdir4(path21.dirname(reportPath), { recursive: true });
23298
- await writeFile4(reportPath, payload, { mode: 384 });
24430
+ await writeFile3(reportPath, payload, { mode: 384 });
23299
24431
  return sha256Buffer3(Buffer.from(payload, "utf8"));
23300
24432
  }
23301
24433
  async function sha256File2(filePath) {
23302
24434
  const hash = createHash10("sha256");
23303
- const stream = createReadStream2(filePath);
24435
+ const stream = createReadStream3(filePath);
23304
24436
  for await (const chunk of stream) {
23305
24437
  hash.update(chunk);
23306
24438
  }
@@ -23325,10 +24457,10 @@ function sanitizePathSegment2(value) {
23325
24457
  }
23326
24458
 
23327
24459
  // src/secretFile.ts
23328
- import { chmodSync, mkdirSync as mkdirSync7, readFileSync as readFileSync9, writeFileSync as writeFileSync7 } from "fs";
24460
+ import { chmodSync as chmodSync2, mkdirSync as mkdirSync7, readFileSync as readFileSync10, writeFileSync as writeFileSync7 } from "fs";
23329
24461
  import path22 from "path";
23330
24462
  function readSecretFileSync(filePath) {
23331
- return readFileSync9(filePath, "utf8").trim();
24463
+ return readFileSync10(filePath, "utf8").trim();
23332
24464
  }
23333
24465
 
23334
24466
  // src/core.ts
@@ -23400,7 +24532,10 @@ var DAEMON_CORE_TRACE_ATTR_CONTRACTS = {
23400
24532
  endAttrs: ["outcome", "error_class"]
23401
24533
  },
23402
24534
  "daemon.computer_control.received": {
23403
- spanAttrs: ["action", "handled"]
24535
+ spanAttrs: ["action", "handled", "operation_id", "request_id"]
24536
+ },
24537
+ "daemon.computer_control.replayed": {
24538
+ spanAttrs: ["action", "operation_id", "outcome"]
23404
24539
  },
23405
24540
  "daemon.ready.sent": {
23406
24541
  spanAttrs: ["runtimes_count", "running_agents_count", "idle_agents_count", "runtime_profile_reports_count"]
@@ -23439,6 +24574,28 @@ var DAEMON_CORE_TRACE_ATTR_CONTRACTS = {
23439
24574
  "daemon.connection.local_disconnect_observed": {
23440
24575
  spanAttrs: ["running_agents_count", "idle_agents_count"]
23441
24576
  },
24577
+ "daemon.migration_transport.object_store": {
24578
+ spanAttrs: [
24579
+ "outcome",
24580
+ "role",
24581
+ "transfer_kind",
24582
+ "agent_id_present",
24583
+ "migration_id_present",
24584
+ "session_id_present",
24585
+ "error_class",
24586
+ "endpoint_class",
24587
+ "http_status",
24588
+ "content_length_present",
24589
+ "upload_body_mode",
24590
+ "bundle_size_bucket",
24591
+ "bundle_content_bytes",
24592
+ "max_bytes",
24593
+ "manifest_sha_present",
24594
+ "attempt",
24595
+ "status",
24596
+ "retry_delay_ms"
24597
+ ]
24598
+ },
23442
24599
  "daemon.agent.activity.produced": {
23443
24600
  // isHeartbeat/is_heartbeat (#460 V1) and process_instance_id (#460 V3)
23444
24601
  // were emitted by agentProcessManager but scrubbed here (pilot violation
@@ -23505,6 +24662,36 @@ function migrationTransferFailureMessage(err) {
23505
24662
  const message = err instanceof Error ? err.message : String(err);
23506
24663
  return message.slice(0, 500);
23507
24664
  }
24665
+ function migrationTransferFailureCode(err) {
24666
+ return err instanceof AgentMigrationObjectStoreBundleTooLargeError ? err.code : void 0;
24667
+ }
24668
+ var MigrationObjectStoreUploadHttpError = class extends Error {
24669
+ constructor(status, archiveBytes) {
24670
+ super(`MIGRATION_OBJECT_STORE_UPLOAD_FAILED:${status}`);
24671
+ this.status = status;
24672
+ this.archiveBytes = archiveBytes;
24673
+ this.name = "MigrationObjectStoreUploadHttpError";
24674
+ }
24675
+ };
24676
+ function migrationObjectStoreFailureTraceAttrs(err) {
24677
+ if (!(err instanceof MigrationObjectStoreUploadHttpError)) return {};
24678
+ return {
24679
+ endpoint_class: "object_store",
24680
+ http_status: err.status,
24681
+ content_length_present: true,
24682
+ upload_body_mode: "spooled_file",
24683
+ bundle_size_bucket: migrationObjectStoreBundleSizeBucket(err.archiveBytes)
24684
+ };
24685
+ }
24686
+ function migrationObjectStoreBundleSizeBucket(bytes) {
24687
+ if (bytes < 1024 * 1024) return "lt_1_mib";
24688
+ if (bytes < 16 * 1024 * 1024) return "1_to_16_mib";
24689
+ if (bytes < 128 * 1024 * 1024) return "16_to_128_mib";
24690
+ if (bytes < 512 * 1024 * 1024) return "128_to_512_mib";
24691
+ if (bytes < 1024 * 1024 * 1024) return "512_mib_to_1_gib";
24692
+ if (bytes < 3 * 1024 * 1024 * 1024) return "1_to_3_gib";
24693
+ return "gte_3_gib";
24694
+ }
23508
24695
  async function migrationStepErrorSuffix(response) {
23509
24696
  try {
23510
24697
  const body = await response.clone().json();
@@ -23534,6 +24721,8 @@ function parseDaemonCliArgs(args) {
23534
24721
  return { serverUrl, apiKey };
23535
24722
  }
23536
24723
  function readDaemonVersion(moduleUrl = import.meta.url) {
24724
+ const baked = process.env.RAFT_DAEMON_VERSION;
24725
+ if (typeof baked === "string" && baked.length > 0) return baked;
23537
24726
  try {
23538
24727
  const require2 = createRequire3(moduleUrl);
23539
24728
  return require2("../package.json").version;
@@ -23562,7 +24751,7 @@ function resolveSlockCliPathOrEmpty(moduleUrl = import.meta.url) {
23562
24751
  }
23563
24752
  async function runBundledSlockCli(argv) {
23564
24753
  process.argv = [process.execPath, "slock", ...argv];
23565
- await import("./dist-VNC64ECP.js");
24754
+ await import("./dist-SCXCWA6D.js");
23566
24755
  }
23567
24756
  function detectRuntimes(tracer = noopTracer) {
23568
24757
  const ids = [];
@@ -23709,6 +24898,7 @@ function summarizeIncomingMessage(msg) {
23709
24898
  var DaemonCore = class {
23710
24899
  options;
23711
24900
  daemonVersion;
24901
+ daemonInstanceId = randomUUID9();
23712
24902
  // When this runner is launched by a managed Computer service, the
23713
24903
  // service exports RAFT_COMPUTER_VERSION (the `@botiverse/raft-computer`
23714
24904
  // bundle version). Reported in `ready` so the server can surface the
@@ -23740,6 +24930,7 @@ var DaemonCore = class {
23740
24930
  traceBundleUploader = null;
23741
24931
  coreStartingAgentIds = /* @__PURE__ */ new Set();
23742
24932
  coreStartPendingDeliveries = /* @__PURE__ */ new Map();
24933
+ handledComputerControlOperationIds = /* @__PURE__ */ new Set();
23743
24934
  constructor(options) {
23744
24935
  this.options = options;
23745
24936
  this.daemonVersion = options.daemonVersion ?? readDaemonVersion();
@@ -23765,6 +24956,7 @@ var DaemonCore = class {
23765
24956
  slockCliPath: this.slockCliPath,
23766
24957
  tracer: this.tracer,
23767
24958
  daemonVersion: this.daemonVersion,
24959
+ daemonInstanceId: this.daemonInstanceId,
23768
24960
  computerVersion: this.computerVersion,
23769
24961
  workerUrl: traceUploadDisabled ? void 0 : process.env.SLOCK_DAEMON_TRACE_UPLOAD_URL || DEFAULT_TRACE_UPLOAD_URL,
23770
24962
  serverConnected: () => connection?.connected ?? false
@@ -23896,7 +25088,12 @@ var DaemonCore = class {
23896
25088
  span.addEvent("daemon.agents.stopped");
23897
25089
  } finally {
23898
25090
  if (this.connection.connected) {
23899
- this.connection.send({ type: "machine:shutdown", reason: shutdownReason });
25091
+ const lifecycleAcks = this.options.getComputerLifecycleAcks?.().filter((ack) => ack.phase === "shutdown");
25092
+ this.connection.send({
25093
+ type: "machine:shutdown",
25094
+ reason: shutdownReason,
25095
+ ...lifecycleAcks && lifecycleAcks.length > 0 ? { lifecycleAcks } : {}
25096
+ });
23900
25097
  span.addEvent("daemon.connection.shutdown_notice_sent", {
23901
25098
  outcome: "sent",
23902
25099
  shutdown_reason: shutdownReason
@@ -24093,7 +25290,8 @@ var DaemonCore = class {
24093
25290
  agent_id_present: Boolean(lease.agentId),
24094
25291
  migration_id_present: Boolean(lease.migrationId),
24095
25292
  session_id_present: Boolean(lease.sessionId),
24096
- error_class: err instanceof Error ? err.name : typeof err
25293
+ error_class: err instanceof Error ? err.name : typeof err,
25294
+ ...migrationObjectStoreFailureTraceAttrs(err)
24097
25295
  }, "error");
24098
25296
  try {
24099
25297
  await this.reportMigrationTransportLost(lease, err);
@@ -24134,23 +25332,44 @@ var DaemonCore = class {
24134
25332
  workspacePath: path23.join(this.agentsDataDir, lease.agentId),
24135
25333
  maxBytes: lease.maxBytes
24136
25334
  });
24137
- const response = await daemonFetch(lease.url, {
24138
- method: "PUT",
24139
- headers: {
24140
- ...this.migrationObjectStoreHeaders(lease),
24141
- "Content-Type": AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE
24142
- },
24143
- body: new Uint8Array(built.bundle)
24144
- });
24145
- if (!response.ok) {
24146
- throw new Error(`MIGRATION_OBJECT_STORE_UPLOAD_FAILED:${response.status}`);
25335
+ const spoolDirectory = await mkdtemp(path23.join(os8.tmpdir(), "raft-agent-migration-upload-"));
25336
+ const spoolPath = path23.join(spoolDirectory, "bundle.tar.gz");
25337
+ let archiveBytes = 0;
25338
+ let uploadStatus = 0;
25339
+ try {
25340
+ await pipeline2(
25341
+ built.bundle,
25342
+ createWriteStream2(spoolPath, { flags: "wx", mode: 384 })
25343
+ );
25344
+ archiveBytes = (await stat4(spoolPath)).size;
25345
+ const response = await daemonFetch(lease.url, {
25346
+ method: "PUT",
25347
+ headers: {
25348
+ ...this.migrationObjectStoreHeaders(lease),
25349
+ "Content-Type": AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE,
25350
+ "Content-Length": String(archiveBytes)
25351
+ },
25352
+ body: Readable3.toWeb(createReadStream4(spoolPath)),
25353
+ duplex: "half"
25354
+ });
25355
+ if (!response.ok) {
25356
+ throw new MigrationObjectStoreUploadHttpError(response.status, archiveBytes);
25357
+ }
25358
+ uploadStatus = response.status;
25359
+ } finally {
25360
+ await rm4(spoolDirectory, { recursive: true, force: true });
24147
25361
  }
24148
25362
  await this.reportMigrationSourceReady(lease, built.manifestSha256);
24149
25363
  this.recordDaemonTrace("daemon.migration_transport.object_store", {
24150
25364
  outcome: "uploaded",
24151
25365
  role: lease.role,
24152
25366
  transfer_kind: lease.transferKind,
24153
- bundle_bytes: built.bundle.byteLength,
25367
+ endpoint_class: "object_store",
25368
+ http_status: uploadStatus,
25369
+ content_length_present: true,
25370
+ upload_body_mode: "spooled_file",
25371
+ bundle_size_bucket: migrationObjectStoreBundleSizeBucket(archiveBytes),
25372
+ bundle_content_bytes: built.contentBytes,
24154
25373
  max_bytes: lease.maxBytes
24155
25374
  });
24156
25375
  }
@@ -24158,14 +25377,13 @@ var DaemonCore = class {
24158
25377
  if (lease.transferKind !== "download") {
24159
25378
  throw new Error("MIGRATION_OBJECT_STORE_TARGET_KIND_MISMATCH");
24160
25379
  }
24161
- const bundle = await this.downloadMigrationObjectStoreBundleWithRetry(lease);
24162
- if (bundle.byteLength > lease.maxBytes) {
24163
- throw new Error("MIGRATION_OBJECT_STORE_BUNDLE_TOO_LARGE");
24164
- }
25380
+ const response = await this.downloadMigrationObjectStoreBundleWithRetry(lease);
25381
+ if (!response.body) throw new Error("MIGRATION_OBJECT_STORE_DOWNLOAD_BODY_MISSING");
24165
25382
  const staged = await stageAgentMigrationObjectStoreBundle({
24166
- bundle,
25383
+ bundle: Readable3.fromWeb(response.body),
24167
25384
  slockHome: this.slockHome,
24168
- sessionId: lease.sessionId
25385
+ sessionId: lease.sessionId,
25386
+ maxBytes: lease.maxBytes
24169
25387
  });
24170
25388
  const targetImport = await this.fetchMigrationTargetImportView(lease.migrationId);
24171
25389
  if (targetImport.agentId !== lease.agentId) {
@@ -24194,7 +25412,7 @@ var DaemonCore = class {
24194
25412
  outcome: "imported",
24195
25413
  role: lease.role,
24196
25414
  transfer_kind: lease.transferKind,
24197
- bundle_bytes: bundle.byteLength,
25415
+ bundle_content_bytes: staged.contentBytes,
24198
25416
  manifest_sha_present: true
24199
25417
  });
24200
25418
  }
@@ -24212,7 +25430,7 @@ var DaemonCore = class {
24212
25430
  headers: this.migrationObjectStoreHeaders(lease)
24213
25431
  });
24214
25432
  if (response.ok) {
24215
- return Buffer.from(await response.arrayBuffer());
25433
+ return response;
24216
25434
  }
24217
25435
  lastStatus = response.status;
24218
25436
  lastErrorClass = null;
@@ -24254,6 +25472,7 @@ var DaemonCore = class {
24254
25472
  body: JSON.stringify({
24255
25473
  role: lease.role,
24256
25474
  transferKind: lease.transferKind,
25475
+ code: migrationTransferFailureCode(err),
24257
25476
  message: migrationTransferFailureMessage(err)
24258
25477
  })
24259
25478
  });
@@ -24825,14 +26044,29 @@ var DaemonCore = class {
24825
26044
  case "computer:restart":
24826
26045
  case "computer:upgrade": {
24827
26046
  const action = msg.type === "computer:restart" ? "restart" : "upgrade";
24828
- const requestId = msg.requestId;
26047
+ const operationId = msg.operationId ?? msg.requestId;
26048
+ const requestId = msg.requestId ?? msg.operationId;
26049
+ const alreadyDurable = operationId ? this.options.getComputerLifecycleAcks?.().some(
26050
+ (ack) => (ack.operationId ?? ack.requestId) === operationId
26051
+ ) ?? false : false;
26052
+ if (operationId && (alreadyDurable || this.handledComputerControlOperationIds.has(operationId))) {
26053
+ this.recordDaemonTrace("daemon.computer_control.replayed", {
26054
+ action,
26055
+ operation_id: operationId,
26056
+ outcome: "ignored"
26057
+ });
26058
+ break;
26059
+ }
26060
+ if (operationId) this.handledComputerControlOperationIds.add(operationId);
24829
26061
  this.recordDaemonTrace("daemon.computer_control.received", {
24830
26062
  action,
24831
26063
  handled: Boolean(this.options.onComputerControl),
26064
+ ...operationId ? { operation_id: operationId } : {},
24832
26065
  ...requestId ? { request_id: requestId } : {}
24833
26066
  });
24834
26067
  if (this.options.onComputerControl) {
24835
26068
  const ctx = {
26069
+ operationId,
24836
26070
  requestId,
24837
26071
  emitUpgradeProgress: (ev) => {
24838
26072
  if (!requestId) return;
@@ -24853,6 +26087,16 @@ var DaemonCore = class {
24853
26087
  }
24854
26088
  break;
24855
26089
  }
26090
+ case "computer:lifecycle:receipt": {
26091
+ if (this.options.onComputerLifecycleReceipt) {
26092
+ void Promise.resolve(this.options.onComputerLifecycleReceipt(msg.operationId, msg.phase)).catch((err) => {
26093
+ logger.warn(
26094
+ `[Daemon] lifecycle receipt persistence failed: ${err instanceof Error ? err.message : String(err)}`
26095
+ );
26096
+ });
26097
+ }
26098
+ break;
26099
+ }
24856
26100
  }
24857
26101
  }
24858
26102
  onReminderFire(job) {
@@ -24881,14 +26125,21 @@ var DaemonCore = class {
24881
26125
  const runtimeProfileReports = this.agentManager.getAgentRuntimeProfileReports();
24882
26126
  this.connection.send({
24883
26127
  type: "ready",
24884
- capabilities: ["agent:start", "agent:stop", "agent:deliver", "workspace:files"],
26128
+ capabilities: [
26129
+ "agent:start",
26130
+ "agent:stop",
26131
+ "agent:deliver",
26132
+ "workspace:files",
26133
+ ...this.options.computerControlViaSupervisor ? [COMPUTER_CAPABILITY_SUPERVISOR_MUTATIONS] : []
26134
+ ],
24885
26135
  runtimes,
24886
26136
  runningAgents: runningAgentIds,
24887
26137
  hostname: this.options.hostname ?? os8.hostname(),
24888
26138
  os: this.options.osDescription ?? `${os8.platform()} ${os8.arch()}`,
24889
26139
  daemonVersion: this.daemonVersion,
24890
26140
  ...this.computerVersion ? { computerVersion: this.computerVersion } : {},
24891
- migrationTransport: this.getMigrationTransportReady()
26141
+ migrationTransport: this.getMigrationTransportReady(),
26142
+ ...this.options.getComputerLifecycleAcks ? { lifecycleAcks: this.options.getComputerLifecycleAcks() } : {}
24892
26143
  });
24893
26144
  this.recordDaemonTrace("daemon.ready.sent", {
24894
26145
  runtimes_count: runtimes.length,
@@ -24929,6 +26180,21 @@ var DaemonCore = class {
24929
26180
  );
24930
26181
  });
24931
26182
  }
26183
+ if (this.options.onComputerRestartReconcile) {
26184
+ void Promise.resolve().then(
26185
+ () => this.options.onComputerRestartReconcile((done) => {
26186
+ this.connection.send({ type: "computer:restart:done", ...done });
26187
+ this.recordDaemonTrace("daemon.computer_restart.reconciled", {
26188
+ request_id: done.requestId,
26189
+ ok: done.ok
26190
+ });
26191
+ })
26192
+ ).catch((err) => {
26193
+ logger.error(
26194
+ `[Daemon] computer restart reconcile failed: ${err instanceof Error ? err.message : String(err)}`
26195
+ );
26196
+ });
26197
+ }
24932
26198
  for (const agentId of runningAgentIds) {
24933
26199
  const sessionId = this.agentManager.getAgentSessionId(agentId);
24934
26200
  const launchId = this.agentManager.getAgentLaunchId(agentId);
@@ -24990,6 +26256,9 @@ export {
24990
26256
  resolveWorkspaceDirectoryPath,
24991
26257
  scanWorkspaceDirectories,
24992
26258
  deleteWorkspaceDirectory,
26259
+ detectLegacyDaemonSupervisor,
26260
+ detectLegacyDaemonSupervisorWithProbe,
26261
+ legacyDaemonSupervisorFallbackCommands,
24993
26262
  AGENT_MIGRATION_TRANSPORT_HOST_ENV,
24994
26263
  AGENT_MIGRATION_TRANSPORT_PORT_ENV,
24995
26264
  AGENT_MIGRATION_TRANSPORT_PUBLIC_URL_ENV,
@@ -25002,8 +26271,10 @@ export {
25002
26271
  buildAgentMigrationExportManifest,
25003
26272
  AGENT_MIGRATION_OBJECT_STORE_BUNDLE_SCHEMA_VERSION,
25004
26273
  AGENT_MIGRATION_OBJECT_STORE_CONTENT_TYPE,
26274
+ AgentMigrationObjectStoreBundleTooLargeError,
25005
26275
  buildAgentMigrationObjectStoreBundle,
25006
26276
  stageAgentMigrationObjectStoreBundle,
26277
+ assertAgentMigrationObjectStoreBundleSize,
25007
26278
  buildAgentMigrationAdoptPlan,
25008
26279
  verifyAgentMigrationAdoptPlan,
25009
26280
  executeAgentMigrationAdoptPlan,