pi-subagents 0.81.0 → 0.82.0

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.
Files changed (141) hide show
  1. package/CHANGELOG.md +38 -0
  2. package/bundle/agents.js +3 -3
  3. package/bundle/child-tool-plan.js +2 -2
  4. package/bundle/{chunk-LSRUTHT7.js → chunk-43SCHIMD.js} +1 -1
  5. package/bundle/{chunk-G5DKFLLI.js → chunk-4SDU2BZX.js} +15 -10
  6. package/bundle/{chunk-V2JWDB5U.js → chunk-52UBALJL.js} +2 -2
  7. package/bundle/{chunk-3DC5KBVP.js → chunk-5TYMSZX3.js} +1 -1
  8. package/bundle/{chunk-CEKS3TFO.js → chunk-7IVSUMQQ.js} +6 -6
  9. package/bundle/{chunk-KSWQVGDW.js → chunk-7PCKZHR5.js} +225 -18
  10. package/bundle/{chunk-563BHAZ5.js → chunk-7YMXOYEU.js} +33 -25
  11. package/bundle/{chunk-XMFLCKMQ.js → chunk-B5EKXDHE.js} +336 -130
  12. package/bundle/{chunk-ZBC44JJ3.js → chunk-CIZQXJ5Q.js} +22 -9
  13. package/bundle/{chunk-L5ZHE4L4.js → chunk-GC4DSPMH.js} +4 -4
  14. package/bundle/{chunk-ARRKBB2B.js → chunk-GJECHSAR.js} +2 -2
  15. package/bundle/{chunk-2ZSNH26H.js → chunk-M2CTFYT3.js} +7 -7
  16. package/bundle/{chunk-TUWLXTAM.js → chunk-MHZ4G23A.js} +681 -320
  17. package/bundle/{chunk-WSBNENFS.js → chunk-NGGAFDL6.js} +14 -4
  18. package/bundle/{chunk-VJHOELQP.js → chunk-NRQ75MGH.js} +160 -78
  19. package/bundle/{chunk-BJN5LUQY.js → chunk-OYF6AFDY.js} +1 -1
  20. package/bundle/{chunk-EYNJ6VL6.js → chunk-PLCCBLPY.js} +2 -2
  21. package/bundle/{chunk-74RT5YQE.js → chunk-RMQFMMAT.js} +123 -33
  22. package/bundle/{chunk-V6MR5TOQ.js → chunk-SIJ4S3EN.js} +25 -19
  23. package/bundle/{chunk-NNLASTQE.js → chunk-VH5OAWVG.js} +19 -5
  24. package/bundle/{chunk-BPS2AGBZ.js → chunk-W2SZ22EM.js} +93 -52
  25. package/bundle/{chunk-V3BIUPLU.js → chunk-WVD4UEL4.js} +256 -52
  26. package/bundle/{chunk-ZP3HODFH.js → chunk-XSWOTIA3.js} +1 -1
  27. package/bundle/{chunk-3IF2PGW7.js → chunk-YKEWIB4M.js} +1 -1
  28. package/bundle/{chunk-26C3WLYQ.js → chunk-ZLINIYTP.js} +497 -272
  29. package/bundle/{chunk-2XYWN7QJ.js → chunk-ZQGSDHL6.js} +2 -2
  30. package/bundle/control-channel.js +2 -2
  31. package/bundle/index.js +1 -1
  32. package/bundle/intercom-bridge.js +2 -2
  33. package/bundle/preflight.js +8 -8
  34. package/bundle/project-panes.js +3 -3
  35. package/docs/agents.md +31 -0
  36. package/docs/configuration.md +9 -1
  37. package/docs/tool-reference.md +3 -1
  38. package/docs/workflows.md +16 -0
  39. package/package.json +2 -2
  40. package/skills/pi-subagents/references/execution-controls.md +5 -4
  41. package/src/agents/agent-management.js +3 -3
  42. package/src/agents/agent-memory.js +3 -1
  43. package/src/agents/agents.js +6 -6
  44. package/src/agents/frontmatter.d.ts +2 -0
  45. package/src/agents/frontmatter.js +15 -1
  46. package/src/agents/skills.js +2 -1
  47. package/src/extension/config.js +3 -0
  48. package/src/extension/herdr-pi-bridge.js +17 -10
  49. package/src/extension/index.js +82 -2
  50. package/src/extension/schemas.js +3 -3
  51. package/src/intercom/native-supervisor-channel.js +20 -0
  52. package/src/missions/lifecycle.js +7 -1
  53. package/src/runs/background/active-async-capacity.d.ts +1 -0
  54. package/src/runs/background/active-async-capacity.js +9 -3
  55. package/src/runs/background/async-execution.js +20 -10
  56. package/src/runs/background/async-job-tracker.d.ts +6 -1
  57. package/src/runs/background/async-job-tracker.js +9 -4
  58. package/src/runs/background/async-status.d.ts +2 -0
  59. package/src/runs/background/async-status.js +21 -2
  60. package/src/runs/background/await-async-run.js +3 -7
  61. package/src/runs/background/boot-id.d.ts +12 -0
  62. package/src/runs/background/boot-id.js +47 -0
  63. package/src/runs/background/interrupted-elsewhere.d.ts +22 -0
  64. package/src/runs/background/interrupted-elsewhere.js +68 -0
  65. package/src/runs/background/notify.d.ts +2 -0
  66. package/src/runs/background/notify.js +13 -0
  67. package/src/runs/background/result-delivery-ownership.d.ts +6 -0
  68. package/src/runs/background/result-delivery-ownership.js +19 -1
  69. package/src/runs/background/result-watcher.d.ts +3 -1
  70. package/src/runs/background/result-watcher.js +24 -8
  71. package/src/runs/background/run-child-session.d.ts +1 -6
  72. package/src/runs/background/run-child-session.js +1 -1
  73. package/src/runs/background/run-status.js +2 -1
  74. package/src/runs/background/stale-run-reconciler.d.ts +25 -0
  75. package/src/runs/background/stale-run-reconciler.js +52 -13
  76. package/src/runs/background/subagent-runner-bootstrap.js +3 -0
  77. package/src/runs/background/subagent-runner.d.ts +4 -0
  78. package/src/runs/background/subagent-runner.js +13 -5
  79. package/src/runs/background/subagent-wait.d.ts +1 -1
  80. package/src/runs/background/subagent-wait.js +6 -1
  81. package/src/runs/background/terminal-run-index.d.ts +1 -0
  82. package/src/runs/background/terminal-run-index.js +4 -2
  83. package/src/runs/foreground/async-stop-action.js +3 -1
  84. package/src/runs/foreground/execution.js +6 -3
  85. package/src/runs/foreground/foreground-history.d.ts +16 -2
  86. package/src/runs/foreground/foreground-history.js +133 -31
  87. package/src/runs/foreground/subagent-executor.d.ts +11 -0
  88. package/src/runs/foreground/subagent-executor.js +277 -74
  89. package/src/runs/shared/child-launch.d.ts +2 -2
  90. package/src/runs/shared/child-session.d.ts +3 -2
  91. package/src/runs/shared/child-session.js +51 -8
  92. package/src/runs/shared/child-tool-plan.d.ts +7 -0
  93. package/src/runs/shared/child-tool-plan.js +21 -6
  94. package/src/runs/shared/herdr-connection.d.ts +17 -8
  95. package/src/runs/shared/herdr-connection.js +19 -7
  96. package/src/runs/shared/herdr-external-adapters.d.ts +3 -2
  97. package/src/runs/shared/herdr-external-adapters.js +1 -1
  98. package/src/runs/shared/herdr-machine.d.ts +12 -2
  99. package/src/runs/shared/herdr-machine.js +55 -9
  100. package/src/runs/shared/herdr-pane-host.d.ts +88 -0
  101. package/src/runs/shared/herdr-pane-host.js +155 -0
  102. package/src/runs/shared/herdr-placed-run.d.ts +27 -150
  103. package/src/runs/shared/herdr-placed-run.js +48 -395
  104. package/src/runs/shared/local-machine-access.d.ts +5 -0
  105. package/src/runs/shared/local-machine-access.js +28 -0
  106. package/src/runs/shared/orca-progress-tabs.d.ts +0 -1
  107. package/src/runs/shared/orca-progress-tabs.js +1 -24
  108. package/src/runs/shared/parallel-utils.d.ts +1 -1
  109. package/src/runs/shared/placed-run-owner.d.ts +49 -0
  110. package/src/runs/shared/placed-run-owner.js +93 -0
  111. package/src/runs/shared/placement-host.d.ts +99 -0
  112. package/src/runs/shared/placement-host.js +157 -0
  113. package/src/runs/shared/rex-machine.d.ts +25 -0
  114. package/src/runs/shared/rex-machine.js +83 -0
  115. package/src/runs/shared/rex-pane-host.d.ts +62 -0
  116. package/src/runs/shared/rex-pane-host.js +327 -0
  117. package/src/shared/completion-owner.d.ts +5 -0
  118. package/src/shared/completion-owner.js +5 -0
  119. package/src/shared/session-identity.d.ts +2 -0
  120. package/src/shared/session-identity.js +26 -0
  121. package/src/shared/types.d.ts +45 -6
  122. package/src/tui/fleet.d.ts +1 -0
  123. package/src/tui/fleet.js +24 -15
  124. package/src/tui/render.d.ts +6 -0
  125. package/src/tui/render.js +3 -3
  126. package/src/tui/subagent-messages.js +1 -0
  127. package/src/workflows/scripted-workflow.d.ts +1 -1
  128. package/src/workflows/workflow-auto-resume.d.ts +32 -0
  129. package/src/workflows/workflow-auto-resume.js +102 -0
  130. package/src/workflows/workflow-launch-record.d.ts +27 -0
  131. package/src/workflows/workflow-launch-record.js +48 -0
  132. package/src/workflows/workflow-resume-claim.d.ts +82 -0
  133. package/src/workflows/workflow-resume-claim.js +210 -0
  134. package/src/workflows/workflow-resume.d.ts +56 -0
  135. package/src/workflows/workflow-resume.js +106 -0
  136. package/src/workflows/workflow-reuse.d.ts +15 -9
  137. package/src/workflows/workflow-reuse.js +77 -14
  138. package/src/workflows/workflow-revival.d.ts +2 -0
  139. package/src/workflows/workflow-revival.js +2 -1
  140. package/src/workflows/workflow-stop-cause.d.ts +6 -0
  141. package/src/workflows/workflow-stop-cause.js +8 -0
@@ -1,5 +1,7 @@
1
1
  import {
2
2
  checkPidLiveness,
3
+ checkRecordedPidLiveness,
4
+ currentBootId,
3
5
  currentPidNamespaceScope,
4
6
  isTerminalAsyncState,
5
7
  normalizeWorktreeBranchPrefix,
@@ -9,13 +11,13 @@ import {
9
11
  validateAuthorityPolicy,
10
12
  validateMissionStoreConfig,
11
13
  validateModelResponseAliases
12
- } from "./chunk-VJHOELQP.js";
14
+ } from "./chunk-NRQ75MGH.js";
13
15
  import {
14
16
  getAgentDir,
15
17
  readStatus,
16
18
  validatePermissionConfig,
17
19
  writePrivateAtomicJson
18
- } from "./chunk-ZBC44JJ3.js";
20
+ } from "./chunk-CIZQXJ5Q.js";
19
21
  import {
20
22
  FLEET_KEYBINDING_ACTIONS,
21
23
  RUNNER_LAUNCHER_NAME_PATTERN,
@@ -252,8 +254,13 @@ function abandonedRunnerReleaseVerdict(status, proofState, options, anyTerminalS
252
254
  if (thresholdMs === false) return { state: "retained", reason: `${proofReason}; abandoned-timeout policy is disabled` };
253
255
  if (anyTerminalState ? !isTerminalAsyncState(status.state) : status.state !== "failed") return { state: "retained", reason: `${proofReason}; abandoned-timeout policy requires a ${anyTerminalState ? "terminal" : "failed"} run, not ${status.state}` };
254
256
  if (typeof status.pid !== "number" || !Number.isInteger(status.pid) || status.pid < 1) return { state: "retained", reason: `${proofReason}; runner PID is missing or invalid` };
255
- if (status.pidNamespaceScope !== void 0 && status.pidNamespaceScope !== (options.pidNamespaceScope ?? currentPidNamespaceScope)()) return { state: "retained", reason: `${proofReason}; runner PID namespace differs from this process, so liveness is unknown` };
256
- const liveness = (options.pidLiveness ?? checkPidLiveness)(status.pid);
257
+ const observedScope = (options.pidNamespaceScope ?? currentPidNamespaceScope)();
258
+ if (status.pidNamespaceScope !== void 0 && status.pidNamespaceScope !== observedScope) return { state: "retained", reason: `${proofReason}; runner PID namespace differs from this process, so liveness is unknown` };
259
+ const liveness = checkRecordedPidLiveness({ pid: status.pid, pidNamespaceScope: status.pidNamespaceScope, bootId: status.bootId }, {
260
+ observedScope,
261
+ observedBootId: (options.bootId ?? currentBootId)(),
262
+ probe: options.pidLiveness ?? ((pid) => checkPidLiveness(pid))
263
+ });
257
264
  if (liveness !== "dead") return { state: "retained", reason: `${proofReason}; runner PID liveness is ${liveness}` };
258
265
  const lastActivityAt = status.lastActivityAt ?? status.lastUpdate ?? status.endedAt;
259
266
  if (typeof lastActivityAt !== "number" || !Number.isFinite(lastActivityAt)) return { state: "retained", reason: `${proofReason}; last activity timestamp is missing or invalid` };
@@ -666,6 +673,9 @@ function validateConfig(config) {
666
673
  if (config.enableSlashCommands !== void 0 && typeof config.enableSlashCommands !== "boolean") {
667
674
  throw new Error("config.enableSlashCommands must be a boolean");
668
675
  }
676
+ if (config.autoResume !== void 0 && typeof config.autoResume !== "boolean") {
677
+ throw new Error("config.autoResume must be a boolean");
678
+ }
669
679
  if (config.toolActivation !== void 0 && config.toolActivation !== "auto" && config.toolActivation !== "dynamic" && config.toolActivation !== "eager") {
670
680
  throw new Error('config.toolActivation must be "auto", "dynamic", or "eager"');
671
681
  }
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  PROJECT_SUBAGENTS_RELATIVE_DIR
3
- } from "./chunk-3DC5KBVP.js";
3
+ } from "./chunk-5TYMSZX3.js";
4
4
  import {
5
5
  DEFAULT_FILE_SYSTEM_RETRY_DELAYS_MS,
6
6
  DEFAULT_GLOBAL_CONCURRENCY_LIMIT,
@@ -22,7 +22,7 @@ import {
22
22
  withFileLease,
23
23
  writeAtomicJson,
24
24
  writePrivateAtomicJson
25
- } from "./chunk-ZBC44JJ3.js";
25
+ } from "./chunk-CIZQXJ5Q.js";
26
26
  import {
27
27
  DIRS,
28
28
  SUBAGENT_LIFECYCLE_ARTIFACT_VERSION,
@@ -177,8 +177,8 @@ function sessionDirs(asyncDirRoot, sessionId) {
177
177
  throw error;
178
178
  }
179
179
  }
180
- function recentMarkerFiles(dirs, limit) {
181
- return dirs.flatMap(markerFiles).sort((left, right) => right.name.localeCompare(left.name)).slice(0, limit).map((marker) => path2.join(marker.dir, marker.name));
180
+ function recentMarkerFiles(dirs, limit, endedAfter) {
181
+ return dirs.flatMap(markerFiles).filter((marker) => endedAfter === void 0 || !(Number(marker.name.slice(0, TIMESTAMP_WIDTH)) < endedAfter)).sort((left, right) => right.name.localeCompare(left.name)).slice(0, limit).map((marker) => path2.join(marker.dir, marker.name));
182
182
  }
183
183
  function readTerminalRunToolCallIndex(asyncDirRoot, toolCallId) {
184
184
  const runIds = [];
@@ -206,7 +206,7 @@ function readTerminalRunToolCallIndex(asyncDirRoot, toolCallId) {
206
206
  }
207
207
  function readRecentTerminalRunIndex(asyncDirRoot, options = {}) {
208
208
  const limit = options.limit === void 0 ? Number.POSITIVE_INFINITY : Math.max(0, Math.floor(options.limit));
209
- const candidates = recentMarkerFiles(sessionDirs(asyncDirRoot, options.sessionId), limit);
209
+ const candidates = recentMarkerFiles(sessionDirs(asyncDirRoot, options.sessionId), limit, options.endedAfter);
210
210
  const runIds = [];
211
211
  const seen = /* @__PURE__ */ new Set();
212
212
  for (const marker of candidates) {
@@ -742,11 +742,11 @@ function resolveInheritedNestedRoute(route) {
742
742
  return void 0;
743
743
  }
744
744
  }
745
- function inheritedNestedRouteOf(runtime) {
746
- return runtime?.nestedRoute ? resolveInheritedNestedRoute(runtime.nestedRoute) : void 0;
745
+ function inheritedNestedRouteOf(runtime2) {
746
+ return runtime2?.nestedRoute ? resolveInheritedNestedRoute(runtime2.nestedRoute) : void 0;
747
747
  }
748
- function inheritedNestedParentAddressOf(runtime) {
749
- const parent = runtime?.nestedParent;
748
+ function inheritedNestedParentAddressOf(runtime2) {
749
+ const parent = runtime2?.nestedParent;
750
750
  if (!parent || !isSafeNestedId(parent.parentRunId)) return void 0;
751
751
  const depth = Math.min(Math.max(1, clampNumber(parent.depth) ?? 1), MAX_DEPTH);
752
752
  return {
@@ -5585,7 +5585,12 @@ function parsePersistedBinding(value, source) {
5585
5585
  function readMissionBinding(asyncDir) {
5586
5586
  const bindingPath = path12.join(asyncDir, MISSION_BINDING_FILE);
5587
5587
  if (!fs11.existsSync(bindingPath)) return void 0;
5588
- return parsePersistedBinding(JSON.parse(fs11.readFileSync(bindingPath, "utf-8")), bindingPath);
5588
+ const raw = fs11.readFileSync(bindingPath, "utf-8");
5589
+ try {
5590
+ return parsePersistedBinding(JSON.parse(raw), bindingPath);
5591
+ } catch (error) {
5592
+ throw new Error(`Invalid mission binding file '${bindingPath}': ${error instanceof Error ? error.message : String(error)}`, { cause: error });
5593
+ }
5589
5594
  }
5590
5595
  function syncMissionFromAsyncCompletion(value) {
5591
5596
  if (!value || typeof value !== "object" || Array.isArray(value)) return void 0;
@@ -6156,8 +6161,66 @@ function cleanupResultIndexes(resultsDir, now = Date.now(), maxAgeMs = 24 * 60 *
6156
6161
  return removed;
6157
6162
  }
6158
6163
 
6164
+ // src/shared/completion-owner.ts
6165
+ import { randomUUID as randomUUID6 } from "node:crypto";
6166
+ var COMPLETION_OWNER_KEY = /* @__PURE__ */ Symbol.for("pi-subagents.completion-owner-id");
6167
+ var OWNING_SESSION_COMPLETION_OWNER = "owning-session";
6168
+ function currentCompletionOwnerId() {
6169
+ const runtime2 = globalThis;
6170
+ runtime2[COMPLETION_OWNER_KEY] ??= randomUUID6();
6171
+ return runtime2[COMPLETION_OWNER_KEY];
6172
+ }
6173
+
6174
+ // src/runs/background/boot-id.ts
6175
+ import { execFileSync as execFileSync2 } from "node:child_process";
6176
+ import * as fs14 from "node:fs";
6177
+
6178
+ // src/runs/background/pid-namespace.ts
6179
+ import * as fs13 from "node:fs";
6180
+ var resolved = false;
6181
+ var cachedScope;
6182
+ function currentPidNamespaceScope() {
6183
+ if (resolved) return cachedScope;
6184
+ resolved = true;
6185
+ if (process.platform !== "linux") return void 0;
6186
+ try {
6187
+ const scope = fs13.readlinkSync("/proc/self/ns/pid", "utf-8").trim();
6188
+ cachedScope = scope || void 0;
6189
+ } catch {
6190
+ cachedScope = void 0;
6191
+ }
6192
+ return cachedScope;
6193
+ }
6194
+
6195
+ // src/runs/background/boot-id.ts
6196
+ function readBootIdFromOs() {
6197
+ try {
6198
+ if (process.platform === "linux") return fs14.readFileSync("/proc/sys/kernel/random/boot_id", "utf-8").trim() || void 0;
6199
+ if (process.platform === "darwin") {
6200
+ return execFileSync2("sysctl", ["-n", "kern.bootsessionuuid"], { encoding: "utf-8", timeout: 1e3, stdio: ["ignore", "pipe", "ignore"] }).trim() || void 0;
6201
+ }
6202
+ } catch {
6203
+ }
6204
+ return void 0;
6205
+ }
6206
+ var BOOT_ID_KEY = /* @__PURE__ */ Symbol.for("pi-subagents.boot-id.v1");
6207
+ var runtime = globalThis;
6208
+ var reader = readBootIdFromOs;
6209
+ function currentBootId() {
6210
+ const cached = runtime[BOOT_ID_KEY];
6211
+ if (cached) return cached.value;
6212
+ const value = reader();
6213
+ runtime[BOOT_ID_KEY] = { value };
6214
+ return value;
6215
+ }
6216
+ function currentRecordedPid() {
6217
+ const pidNamespaceScope = currentPidNamespaceScope();
6218
+ const bootId = currentBootId();
6219
+ return { pid: process.pid, ...pidNamespaceScope ? { pidNamespaceScope } : {}, ...bootId ? { bootId } : {} };
6220
+ }
6221
+
6159
6222
  // src/runs/background/stale-run-reconciler.ts
6160
- import * as fs15 from "node:fs";
6223
+ import * as fs16 from "node:fs";
6161
6224
  import * as path15 from "node:path";
6162
6225
 
6163
6226
  // src/runs/background/parallel-groups.ts
@@ -6191,25 +6254,15 @@ function flatToLogicalStepIndex(flatIndex, chainStepCount, groups) {
6191
6254
  return Math.max(0, chainStepCount - 1);
6192
6255
  }
6193
6256
 
6194
- // src/runs/background/pid-namespace.ts
6195
- import * as fs13 from "node:fs";
6196
- var resolved = false;
6197
- var cachedScope;
6198
- function currentPidNamespaceScope() {
6199
- if (resolved) return cachedScope;
6200
- resolved = true;
6201
- if (process.platform !== "linux") return void 0;
6202
- try {
6203
- const scope = fs13.readlinkSync("/proc/self/ns/pid", "utf-8").trim();
6204
- cachedScope = scope || void 0;
6205
- } catch {
6206
- cachedScope = void 0;
6207
- }
6208
- return cachedScope;
6257
+ // src/workflows/workflow-stop-cause.ts
6258
+ var WORKFLOW_STOP_CAUSE_RUNTIME_REPLACED = "runtime-replaced";
6259
+ var WORKFLOW_STOP_CAUSE_OWNER_EXITED = "owner-exited";
6260
+ function isReusableWorkflowStopCause(cause) {
6261
+ return cause === WORKFLOW_STOP_CAUSE_RUNTIME_REPLACED || cause === WORKFLOW_STOP_CAUSE_OWNER_EXITED;
6209
6262
  }
6210
6263
 
6211
6264
  // src/runs/background/workflow-terminal-proof.ts
6212
- import * as fs14 from "node:fs";
6265
+ import * as fs15 from "node:fs";
6213
6266
  import * as path14 from "node:path";
6214
6267
  var TERMINAL_WORKFLOW_STATES = /* @__PURE__ */ new Set(["completed", "failed", "stopped"]);
6215
6268
  function isTerminalAsyncState(state) {
@@ -6247,7 +6300,7 @@ function readWorkflowChildProcessEvidence(workflowAsyncDir, steps) {
6247
6300
  }
6248
6301
  function launchFailedBeforeRunner(step, childDir) {
6249
6302
  if (step.status !== "failed" || !step.error) return false;
6250
- return !childDir || !["process-terminal.json", "runner-startup.json"].some((file) => fs14.existsSync(path14.join(childDir, file)));
6303
+ return !childDir || !["process-terminal.json", "runner-startup.json"].some((file) => fs15.existsSync(path14.join(childDir, file)));
6251
6304
  }
6252
6305
  function readWorkflowChildEvidence(workflowAsyncDir, step) {
6253
6306
  const label = step.workflowKey ?? step.agent;
@@ -6255,7 +6308,7 @@ function readWorkflowChildEvidence(workflowAsyncDir, step) {
6255
6308
  if (!step.async) return void 0;
6256
6309
  if (!step.runId || path14.basename(step.runId) !== step.runId) return { state: "unknown", reason: `async workflow child ${label} is missing run id` };
6257
6310
  const childDir = path14.join(path14.dirname(workflowAsyncDir), step.runId);
6258
- if (!fs14.existsSync(childDir)) return launchFailedBeforeRunner(step) ? void 0 : { state: "unknown", reason: `async workflow child ${label} directory is missing` };
6311
+ if (!fs15.existsSync(childDir)) return launchFailedBeforeRunner(step) ? void 0 : { state: "unknown", reason: `async workflow child ${label} directory is missing` };
6259
6312
  const childStatus = readStatus(childDir);
6260
6313
  if (!childStatus) return launchFailedBeforeRunner(step, childDir) ? void 0 : { state: "unknown", reason: `async workflow child ${label} status is missing or unreadable` };
6261
6314
  if (!isTerminalAsyncState(childStatus.state)) return { state: "pending", reason: `async workflow child ${label} is still ${childStatus.state}` };
@@ -6302,17 +6355,17 @@ function readRunnerStartupDiagnostics(asyncDir) {
6302
6355
  const maxBytes = 64 * 1024;
6303
6356
  let content;
6304
6357
  try {
6305
- const stat = fs15.statSync(stderrPath);
6358
+ const stat = fs16.statSync(stderrPath);
6306
6359
  if (stat.size <= 0) return void 0;
6307
- const fd = fs15.openSync(stderrPath, "r");
6360
+ const fd = fs16.openSync(stderrPath, "r");
6308
6361
  try {
6309
6362
  const bytesToRead = Math.min(stat.size, maxBytes);
6310
6363
  const start = Math.max(0, stat.size - bytesToRead);
6311
6364
  const buffer = Buffer.alloc(bytesToRead);
6312
- fs15.readSync(fd, buffer, 0, bytesToRead, start);
6365
+ fs16.readSync(fd, buffer, 0, bytesToRead, start);
6313
6366
  content = buffer.toString("utf-8").trim();
6314
6367
  } finally {
6315
- fs15.closeSync(fd);
6368
+ fs16.closeSync(fd);
6316
6369
  }
6317
6370
  } catch {
6318
6371
  return void 0;
@@ -6327,15 +6380,15 @@ function isNotFoundError(error) {
6327
6380
  }
6328
6381
  function appendJsonlBestEffort(filePath, payload) {
6329
6382
  try {
6330
- fs15.mkdirSync(path15.dirname(filePath), { recursive: true });
6331
- fs15.appendFileSync(filePath, `${JSON.stringify(payload)}
6383
+ fs16.mkdirSync(path15.dirname(filePath), { recursive: true });
6384
+ fs16.appendFileSync(filePath, `${JSON.stringify(payload)}
6332
6385
  `, "utf-8");
6333
6386
  } catch {
6334
6387
  }
6335
6388
  }
6336
6389
  function regularFileExists(filePath) {
6337
6390
  try {
6338
- return fs15.statSync(filePath).isFile();
6391
+ return fs16.statSync(filePath).isFile();
6339
6392
  } catch (error) {
6340
6393
  if (isNotFoundError(error)) return false;
6341
6394
  throw error;
@@ -6343,7 +6396,7 @@ function regularFileExists(filePath) {
6343
6396
  }
6344
6397
  function readResultRepairData(resultPath) {
6345
6398
  try {
6346
- const data = JSON.parse(fs15.readFileSync(resultPath, "utf-8"));
6399
+ const data = JSON.parse(fs16.readFileSync(resultPath, "utf-8"));
6347
6400
  if (data.error !== void 0 && typeof data.error !== "string") throw new Error(`Invalid async result file '${resultPath}': error must be a string.`);
6348
6401
  const state = data.success ? "complete" : data.state === "stopped" ? "stopped" : data.state === "rejected" ? "rejected" : data.state === "partial" ? "partial" : data.state === "paused" || data.exitCode === 0 ? "paused" : "failed";
6349
6402
  const results = Array.isArray(data.results) ? data.results.map((entry, index) => {
@@ -6460,13 +6513,15 @@ function settledWorkflowChildStatus(asyncDir, workflowRunId, step, now) {
6460
6513
  if (settled.stopped === void 0) delete settled.stopped;
6461
6514
  return settled;
6462
6515
  }
6463
- function buildFailedRepair(status, asyncDir, now, reason) {
6516
+ function buildFailedRepair(status, asyncDir, now, reason, ownerExited = false, adoptCompletionOwnerId) {
6464
6517
  const runId = status.runId || path15.basename(asyncDir);
6465
6518
  const pid = typeof status.pid === "number" ? status.pid : "unknown";
6519
+ const exitedWorkflow = ownerExited && status.mode === "workflow" ? status.workflow : void 0;
6520
+ const completionOwnerId = exitedWorkflow ? adoptCompletionOwnerId || OWNING_SESSION_COMPLETION_OWNER : status.completionOwnerId;
6466
6521
  const terminal3 = readProcessTerminal(asyncDir, { runId }) ?? status.processTerminal;
6467
6522
  const runnerExit = terminal3?.state === "observed" || terminal3?.state === "unknown" ? terminal3.instances?.find((instance) => instance.kind === "runner" && instance.processInstanceId === terminal3.runnerProcessInstanceId) : void 0;
6468
6523
  const exitText = runnerExit?.kind === "runner" ? `exited with code ${runnerExit.exitCode ?? "none"}${runnerExit.signal ? ` (signal ${runnerExit.signal})` : ""}` : "exited or disappeared";
6469
- const baseMessage = reason ?? `Async runner process ${pid} ${exitText} before writing a result. Marked run failed by stale-run reconciliation.`;
6524
+ const baseMessage = reason ?? (exitedWorkflow ? `The Pi process (PID ${pid}) that ran workflow ${runId} exited before the workflow finished. Marked run failed by stale-run reconciliation. Its finished children are kept.` : `Async runner process ${pid} ${exitText} before writing a result. Marked run failed by stale-run reconciliation.`);
6470
6525
  const diagnostics = readRunnerStartupDiagnostics(asyncDir);
6471
6526
  const message = diagnostics ? `${baseMessage}
6472
6527
 
@@ -6502,7 +6557,10 @@ ${diagnostics}` : baseMessage;
6502
6557
  activityState: void 0,
6503
6558
  lastUpdate: now,
6504
6559
  endedAt: now,
6505
- steps: repairedSteps
6560
+ steps: repairedSteps,
6561
+ // Read from the pre-repair status: the repair time would make an old crash look new.
6562
+ ...exitedWorkflow ? { workflow: { ...exitedWorkflow, stopCause: WORKFLOW_STOP_CAUSE_OWNER_EXITED, ownerExitedAt: status.lastUpdate ?? status.startedAt } } : {},
6563
+ ...completionOwnerId ? { completionOwnerId } : {}
6506
6564
  };
6507
6565
  const resultAgent = repairedSteps[status.currentStep ?? 0]?.agent ?? repairedSteps[0]?.agent ?? "subagent";
6508
6566
  return {
@@ -6512,7 +6570,9 @@ ${diagnostics}` : baseMessage;
6512
6570
  id: runId,
6513
6571
  agent: resultAgent,
6514
6572
  mode: status.mode,
6515
- ...status.completionOwnerId ? { completionOwnerId: status.completionOwnerId } : {},
6573
+ ...exitedWorkflow ? { workflow: { stopCause: WORKFLOW_STOP_CAUSE_OWNER_EXITED } } : {},
6574
+ ...completionOwnerId ? { completionOwnerId } : {},
6575
+ ...status.completionOwnerProcess ? { completionOwnerProcess: status.completionOwnerProcess } : {},
6516
6576
  ...status.parentWorkflowRunId ? { parentWorkflowRunId: status.parentWorkflowRunId } : {},
6517
6577
  ...status.workflowKey ? { workflowKey: status.workflowKey } : {},
6518
6578
  success: false,
@@ -6538,8 +6598,8 @@ ${diagnostics}` : baseMessage;
6538
6598
  }
6539
6599
  };
6540
6600
  }
6541
- function writeFailedRepair(asyncDir, status, resultPath, now, reason) {
6542
- const repair = buildFailedRepair(status, asyncDir, now, reason);
6601
+ function writeFailedRepair(asyncDir, status, resultPath, now, reason, ownerExited = false, adoptCompletionOwnerId) {
6602
+ const repair = buildFailedRepair(status, asyncDir, now, reason, ownerExited, adoptCompletionOwnerId);
6543
6603
  if (repair.result.sessionId) writeAsyncResultFile(resultPath, repair.result);
6544
6604
  writeAtomicJson(path15.join(asyncDir, "status.json"), repair.status);
6545
6605
  updateActiveRunIndex(asyncDir, repair.status.state, repair.status.toolCallId);
@@ -6599,7 +6659,7 @@ function checkPidLiveness(pid, kill = process.kill, probeZombie = false) {
6599
6659
  kill(pid, 0);
6600
6660
  if (probeZombie && process.platform === "linux") {
6601
6661
  try {
6602
- const stat = fs15.readFileSync(`/proc/${pid}/stat`, "utf-8");
6662
+ const stat = fs16.readFileSync(`/proc/${pid}/stat`, "utf-8");
6603
6663
  const closeParen = stat.lastIndexOf(") ");
6604
6664
  if (closeParen >= 0 && stat[closeParen + 2] === "Z") return "dead";
6605
6665
  } catch {
@@ -6613,6 +6673,19 @@ function checkPidLiveness(pid, kill = process.kill, probeZombie = false) {
6613
6673
  return "unknown";
6614
6674
  }
6615
6675
  }
6676
+ function isRecordedPid(value) {
6677
+ if (!value || typeof value !== "object") return false;
6678
+ const { pid, pidNamespaceScope, bootId } = value;
6679
+ return typeof pid === "number" && Number.isSafeInteger(pid) && pid > 0 && (pidNamespaceScope === void 0 || typeof pidNamespaceScope === "string") && (bootId === void 0 || typeof bootId === "string");
6680
+ }
6681
+ function checkRecordedPidLiveness(recorded, observation = { observedScope: currentPidNamespaceScope(), observedBootId: currentBootId() }) {
6682
+ const { observedScope, observedBootId } = observation;
6683
+ if (recorded.pidNamespaceScope === observedScope && recorded.bootId && observedBootId && recorded.bootId !== observedBootId) return "dead";
6684
+ const scopeMismatch = recorded.pidNamespaceScope !== void 0 && recorded.pidNamespaceScope !== observedScope;
6685
+ const scopeVerified = recorded.pidNamespaceScope !== void 0 && recorded.pidNamespaceScope === observedScope;
6686
+ const liveness = observation.probe ? observation.probe(recorded.pid) : checkPidLiveness(recorded.pid, observation.kill, scopeVerified);
6687
+ return liveness === "dead" && scopeMismatch ? "unknown" : liveness;
6688
+ }
6616
6689
  function reconcileAsyncRun(asyncDir, options = {}, observeStatus) {
6617
6690
  const now = options.now?.() ?? Date.now();
6618
6691
  const status = readStatus(asyncDir);
@@ -6665,11 +6738,11 @@ function reconcileAsyncRun(asyncDir, options = {}, observeStatus) {
6665
6738
  return { status: null, repaired: false, resultPath };
6666
6739
  }
6667
6740
  }
6668
- const observedScope = options.pidNamespaceScope ? options.pidNamespaceScope() : currentPidNamespaceScope();
6669
- const pidScopeMismatch = effectiveStatus.pidNamespaceScope !== void 0 && effectiveStatus.pidNamespaceScope !== observedScope;
6670
- const pidScopeVerified = effectiveStatus.pidNamespaceScope !== void 0 && effectiveStatus.pidNamespaceScope === observedScope;
6671
- const observedLiveness = checkPidLiveness(effectiveStatus.pid, options.kill, pidScopeVerified);
6672
- const liveness = observedLiveness === "dead" && pidScopeMismatch ? "unknown" : observedLiveness;
6741
+ const liveness = checkRecordedPidLiveness({ pid: effectiveStatus.pid, pidNamespaceScope: effectiveStatus.pidNamespaceScope, bootId: effectiveStatus.bootId }, {
6742
+ kill: options.kill,
6743
+ observedScope: options.pidNamespaceScope ? options.pidNamespaceScope() : currentPidNamespaceScope(),
6744
+ observedBootId: options.bootId ? options.bootId() : currentBootId()
6745
+ });
6673
6746
  if (liveness !== "dead") {
6674
6747
  const staleAfterMs = options.staleAlivePidMs ?? 24 * 60 * 60 * 1e3;
6675
6748
  const lastUpdate = effectiveStatus.lastUpdate ?? effectiveStatus.startedAt;
@@ -6678,7 +6751,7 @@ function reconcileAsyncRun(asyncDir, options = {}, observeStatus) {
6678
6751
  const message = `Async runner PID ${effectiveStatus.pid} ${probe}; status has not updated for ${now - lastUpdate}ms, so stale-run reconciliation marked the run failed because PID ownership is unverified.`;
6679
6752
  return writeFailedRepair(asyncDir, effectiveStatus, resultPath, now, message);
6680
6753
  }
6681
- return writeFailedRepair(asyncDir, effectiveStatus, resultPath, now);
6754
+ return writeFailedRepair(asyncDir, effectiveStatus, resultPath, now, void 0, true, options.adoptCompletionOwnerId);
6682
6755
  }
6683
6756
 
6684
6757
  // src/policy/authority.ts
@@ -6908,7 +6981,7 @@ async function runSetupCommand(command, args, options) {
6908
6981
  }
6909
6982
 
6910
6983
  // src/runs/shared/worktree.ts
6911
- import * as fs16 from "node:fs";
6984
+ import * as fs17 from "node:fs";
6912
6985
  import * as os2 from "node:os";
6913
6986
  import * as path16 from "node:path";
6914
6987
  var DEFAULT_WORKTREE_PROVIDER = "auto";
@@ -7045,7 +7118,7 @@ function currentWorktreePatch(worktreePath, baseCommit) {
7045
7118
  assertWorktreeMutationAllowed();
7046
7119
  let tempDir;
7047
7120
  try {
7048
- tempDir = fs16.mkdtempSync(path16.join(os2.tmpdir(), "pi-worktree-index-"));
7121
+ tempDir = fs17.mkdtempSync(path16.join(os2.tmpdir(), "pi-worktree-index-"));
7049
7122
  } catch (error) {
7050
7123
  return { error: error instanceof Error ? error.message : String(error) };
7051
7124
  }
@@ -7060,7 +7133,7 @@ function currentWorktreePatch(worktreePath, baseCommit) {
7060
7133
  return { patch: diff.stdout };
7061
7134
  } finally {
7062
7135
  try {
7063
- fs16.rmSync(tempDir, { recursive: true, force: true });
7136
+ fs17.rmSync(tempDir, { recursive: true, force: true });
7064
7137
  } catch {
7065
7138
  }
7066
7139
  }
@@ -7070,7 +7143,7 @@ function validateWorktreePatchRepresentsCurrentWorktree(worktreePath, baseCommit
7070
7143
  if (validationError) return validationError;
7071
7144
  let capturedPatch;
7072
7145
  try {
7073
- capturedPatch = fs16.readFileSync(patchPath, "utf-8");
7146
+ capturedPatch = fs17.readFileSync(patchPath, "utf-8");
7074
7147
  } catch (error) {
7075
7148
  return error instanceof Error ? error.message : String(error);
7076
7149
  }
@@ -7124,9 +7197,9 @@ function normalizeComparableCwd(cwd) {
7124
7197
  try {
7125
7198
  let realpath;
7126
7199
  try {
7127
- realpath = fs16.realpathSync.native(existing);
7200
+ realpath = fs17.realpathSync.native(existing);
7128
7201
  } catch {
7129
- realpath = fs16.realpathSync(existing);
7202
+ realpath = fs17.realpathSync(existing);
7130
7203
  }
7131
7204
  return path16.join(realpath, ...missingSegments.reverse());
7132
7205
  } catch {
@@ -7326,7 +7399,7 @@ function buildNativeProjectPath(dedicatedRoot, repoRoot) {
7326
7399
  }
7327
7400
  function ensureProjectWorktreeDir(dedicatedRoot, repoRoot) {
7328
7401
  try {
7329
- fs16.mkdirSync(buildNativeProjectPath(dedicatedRoot, repoRoot), { recursive: true });
7402
+ fs17.mkdirSync(buildNativeProjectPath(dedicatedRoot, repoRoot), { recursive: true });
7330
7403
  } catch (error) {
7331
7404
  const message = error instanceof Error ? error.message : String(error);
7332
7405
  throw new Error(`failed to create worktree base directory ${dedicatedRoot}: ${message}`);
@@ -7386,7 +7459,7 @@ function linkNodeModulesIfPresent(toplevel, worktreePath) {
7386
7459
  const nodeModulesLinkPath = path16.join(worktreePath, "node_modules");
7387
7460
  const hasDirectoryEntry = (candidate) => {
7388
7461
  try {
7389
- fs16.lstatSync(candidate);
7462
+ fs17.lstatSync(candidate);
7390
7463
  return true;
7391
7464
  } catch (error) {
7392
7465
  if (error instanceof Error && "code" in error && error.code === "ENOENT") return false;
@@ -7397,14 +7470,14 @@ function linkNodeModulesIfPresent(toplevel, worktreePath) {
7397
7470
  if (hasDirectoryEntry(nodeModulesLinkPath)) return false;
7398
7471
  let sourceRealPath;
7399
7472
  try {
7400
- if (!fs16.statSync(nodeModulesPath).isDirectory()) throw new Error("source node_modules is not a directory");
7401
- sourceRealPath = fs16.realpathSync.native(nodeModulesPath);
7473
+ if (!fs17.statSync(nodeModulesPath).isDirectory()) throw new Error("source node_modules is not a directory");
7474
+ sourceRealPath = fs17.realpathSync.native(nodeModulesPath);
7402
7475
  } catch (error) {
7403
7476
  if (error instanceof Error && "code" in error && error.code === "ENOENT") return false;
7404
7477
  throw error;
7405
7478
  }
7406
- fs16.symlinkSync(nodeModulesPath, nodeModulesLinkPath, process.platform === "win32" ? "junction" : "dir");
7407
- if (!fs16.lstatSync(nodeModulesLinkPath).isSymbolicLink() || fs16.realpathSync.native(nodeModulesLinkPath) !== sourceRealPath) {
7479
+ fs17.symlinkSync(nodeModulesPath, nodeModulesLinkPath, process.platform === "win32" ? "junction" : "dir");
7480
+ if (!fs17.lstatSync(nodeModulesLinkPath).isSymbolicLink() || fs17.realpathSync.native(nodeModulesLinkPath) !== sourceRealPath) {
7408
7481
  throw new Error("created link does not resolve to the source node_modules");
7409
7482
  }
7410
7483
  return true;
@@ -7438,10 +7511,10 @@ function resolveWorktreeSetupHook(repoRoot, config) {
7438
7511
  } else {
7439
7512
  throw new Error("worktree setup hook must be an absolute path or a repo-relative path");
7440
7513
  }
7441
- if (!fs16.existsSync(resolvedPath)) {
7514
+ if (!fs17.existsSync(resolvedPath)) {
7442
7515
  throw new Error(`worktree setup hook not found: ${resolvedPath}`);
7443
7516
  }
7444
- if (fs16.statSync(resolvedPath).isDirectory()) {
7517
+ if (fs17.statSync(resolvedPath).isDirectory()) {
7445
7518
  throw new Error(`worktree setup hook must be a file, got directory: ${resolvedPath}`);
7446
7519
  }
7447
7520
  return {
@@ -7542,7 +7615,7 @@ async function createNativeWorktree(tx, toplevel, cwdRelative, runId, index, bas
7542
7615
  const branch = await tx.git(toplevel, ["show-ref", "--verify", "--quiet", `refs/heads/${naming.requestedBranch}`], [0, 1]);
7543
7616
  let pathExists = false;
7544
7617
  try {
7545
- fs16.lstatSync(worktreePath);
7618
+ fs17.lstatSync(worktreePath);
7546
7619
  pathExists = true;
7547
7620
  } catch (error) {
7548
7621
  if (!(error instanceof Error) || !("code" in error) || error.code !== "ENOENT") throw error;
@@ -7594,7 +7667,7 @@ async function createWorktrunkWorktree(tx, toplevel, cwdRelative, runId, index,
7594
7667
  const worktreePathCandidate = path16.resolve(output.path);
7595
7668
  let stat;
7596
7669
  try {
7597
- stat = fs16.lstatSync(worktreePathCandidate);
7670
+ stat = fs17.lstatSync(worktreePathCandidate);
7598
7671
  } catch (error) {
7599
7672
  throw new Error(`Worktrunk provisioning returned a missing worktree path: ${worktreePathCandidate}`, { cause: error instanceof Error ? error : void 0 });
7600
7673
  }
@@ -7637,21 +7710,21 @@ function removeSyntheticPath(worktree, syntheticPath) {
7637
7710
  }
7638
7711
  let stat;
7639
7712
  try {
7640
- stat = fs16.lstatSync(resolved2);
7713
+ stat = fs17.lstatSync(resolved2);
7641
7714
  } catch (error) {
7642
7715
  const code = error && typeof error === "object" && "code" in error ? error.code : void 0;
7643
7716
  if (code === "ENOENT") return;
7644
7717
  throw error;
7645
7718
  }
7646
7719
  if (stat.isSymbolicLink()) {
7647
- fs16.unlinkSync(resolved2);
7720
+ fs17.unlinkSync(resolved2);
7648
7721
  return;
7649
7722
  }
7650
7723
  if (stat.isDirectory()) {
7651
- fs16.rmSync(resolved2, { recursive: true, force: true });
7724
+ fs17.rmSync(resolved2, { recursive: true, force: true });
7652
7725
  return;
7653
7726
  }
7654
- fs16.rmSync(resolved2, { force: true });
7727
+ fs17.rmSync(resolved2, { force: true });
7655
7728
  }
7656
7729
  function removeSyntheticPathsBeforeDiff(worktree) {
7657
7730
  if (worktree.syntheticPaths.length === 0) return;
@@ -7695,7 +7768,7 @@ function captureWorktreeDiff(setup, worktree, agent, patchPath) {
7695
7768
  const diffStat = runGitChecked(worktree.path, ["diff", "--cached", ...MACHINE_DIFF_OPTIONS, "--stat", setup.baseCommit]).trim();
7696
7769
  const patch = runGitChecked(worktree.path, ["diff", "--cached", ...MACHINE_PATCH_OPTIONS, setup.baseCommit]);
7697
7770
  const numstat = runGitChecked(worktree.path, ["diff", "--cached", ...MACHINE_DIFF_OPTIONS, "--numstat", setup.baseCommit]);
7698
- fs16.writeFileSync(patchPath, patch, "utf-8");
7771
+ fs17.writeFileSync(patchPath, patch, "utf-8");
7699
7772
  if (!patch.trim()) {
7700
7773
  return emptyDiff(worktree.index, agent, worktree.branch, patchPath);
7701
7774
  }
@@ -7715,14 +7788,14 @@ function captureWorktreeDiff(setup, worktree, agent, patchPath) {
7715
7788
  }
7716
7789
  function writeEmptyPatch(patchPath) {
7717
7790
  try {
7718
- fs16.writeFileSync(patchPath, "", "utf-8");
7791
+ fs17.writeFileSync(patchPath, "", "utf-8");
7719
7792
  } catch {
7720
7793
  }
7721
7794
  }
7722
7795
  function handoffRecordsPatch(manifestPath, patchPath) {
7723
- if (!manifestPath || !fs16.existsSync(manifestPath)) return false;
7796
+ if (!manifestPath || !fs17.existsSync(manifestPath)) return false;
7724
7797
  try {
7725
- const manifest = JSON.parse(fs16.readFileSync(manifestPath, "utf-8"));
7798
+ const manifest = JSON.parse(fs17.readFileSync(manifestPath, "utf-8"));
7726
7799
  if (manifest.version !== 1 || !Array.isArray(manifest.groups)) return false;
7727
7800
  const resolvedPatchPath = path16.resolve(patchPath);
7728
7801
  return manifest.groups.some((group) => Array.isArray(group.children) && group.children.some(
@@ -7779,9 +7852,9 @@ function cleanupSingleWorktree(setup, worktree, intent) {
7779
7852
  const captured = (intent.capturedDiffs ?? setup.capturedDiffs)?.find((diff) => diff.index === worktree.index);
7780
7853
  let patchValidationError;
7781
7854
  let patchCaptured = false;
7782
- if (captured !== void 0 && captured.error === void 0 && fs16.existsSync(captured.patchPath) && handoffRecordsPatch(intent.handoffManifestPath, captured.patchPath)) {
7855
+ if (captured !== void 0 && captured.error === void 0 && fs17.existsSync(captured.patchPath) && handoffRecordsPatch(intent.handoffManifestPath, captured.patchPath)) {
7783
7856
  try {
7784
- if (fs16.statSync(captured.patchPath).size > 0) {
7857
+ if (fs17.statSync(captured.patchPath).size > 0) {
7785
7858
  patchValidationError = validateWorktreePatchRepresentsCurrentWorktree(worktree.path, setup.baseCommit, captured.patchPath);
7786
7859
  patchCaptured = patchValidationError === void 0;
7787
7860
  }
@@ -7911,7 +7984,7 @@ async function compensateSetup(tx) {
7911
7984
  throw new Error(tx.progress.unknown);
7912
7985
  }
7913
7986
  await git(["worktree", "remove", "--force", attempt.path]);
7914
- } else if (fs16.existsSync(attempt.path)) {
7987
+ } else if (fs17.existsSync(attempt.path)) {
7915
7988
  tx.unknown("Unregistered partial allocation retained");
7916
7989
  throw new Error(tx.progress.unknown);
7917
7990
  }
@@ -8031,7 +8104,7 @@ async function createWorktrees(cwd, runId, count, options = {}) {
8031
8104
  function diffWorktrees(setup, agents, diffsDir) {
8032
8105
  assertWorktreeMutationAllowed();
8033
8106
  try {
8034
- fs16.mkdirSync(diffsDir, { recursive: true });
8107
+ fs17.mkdirSync(diffsDir, { recursive: true });
8035
8108
  } catch {
8036
8109
  return [];
8037
8110
  }
@@ -8216,7 +8289,14 @@ export {
8216
8289
  resultCandidateFilesForToolCall,
8217
8290
  missionObserverResultCandidateFiles,
8218
8291
  cleanupResultIndexes,
8292
+ OWNING_SESSION_COMPLETION_OWNER,
8293
+ currentCompletionOwnerId,
8219
8294
  currentPidNamespaceScope,
8295
+ currentBootId,
8296
+ currentRecordedPid,
8297
+ WORKFLOW_STOP_CAUSE_RUNTIME_REPLACED,
8298
+ WORKFLOW_STOP_CAUSE_OWNER_EXITED,
8299
+ isReusableWorkflowStopCause,
8220
8300
  isTerminalAsyncState,
8221
8301
  withWorkflowChildRunModel,
8222
8302
  readWorkflowChildProcessEvidence,
@@ -8224,6 +8304,8 @@ export {
8224
8304
  readWorkflowTerminalProof,
8225
8305
  reconcileNestedAsyncDescendants,
8226
8306
  checkPidLiveness,
8307
+ isRecordedPid,
8308
+ checkRecordedPidLiveness,
8227
8309
  reconcileAsyncRun,
8228
8310
  resolveAuthorityDecision,
8229
8311
  validateAuthorityPolicy,
@@ -4,7 +4,7 @@ import {
4
4
  import {
5
5
  resolveWatchPath,
6
6
  writeAtomicJson
7
- } from "./chunk-ZBC44JJ3.js";
7
+ } from "./chunk-CIZQXJ5Q.js";
8
8
  import {
9
9
  POLL_INTERVAL_MS
10
10
  } from "./chunk-5LFLVSTM.js";
@@ -1,12 +1,12 @@
1
1
  import {
2
2
  getProjectSubagentsDir
3
- } from "./chunk-3DC5KBVP.js";
3
+ } from "./chunk-5TYMSZX3.js";
4
4
  import {
5
5
  discoverAgents,
6
6
  formatUnknownAgentError,
7
7
  resolveAgentName,
8
8
  unknownAgentDiagnosticContext
9
- } from "./chunk-ZBC44JJ3.js";
9
+ } from "./chunk-CIZQXJ5Q.js";
10
10
 
11
11
  // src/agents/agent-refinements.ts
12
12
  import { createHash, randomUUID } from "node:crypto";