subharness 0.0.5 → 0.0.7

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 (148) hide show
  1. package/README.md +59 -3
  2. package/dist/adapters/claude-process.js +8 -1
  3. package/dist/adapters/claude-process.js.map +1 -1
  4. package/dist/adapters/claude-tools.d.ts +6 -2
  5. package/dist/adapters/claude-tools.js +14 -12
  6. package/dist/adapters/claude-tools.js.map +1 -1
  7. package/dist/adapters/claude-worker-client.d.ts +49 -0
  8. package/dist/adapters/claude-worker-client.js +359 -0
  9. package/dist/adapters/claude-worker-client.js.map +1 -0
  10. package/dist/adapters/claude-worker-process.d.ts +20 -0
  11. package/dist/adapters/claude-worker-process.js +76 -0
  12. package/dist/adapters/claude-worker-process.js.map +1 -0
  13. package/dist/adapters/claude-worker-protocol.d.ts +38 -0
  14. package/dist/adapters/claude-worker-protocol.js +2 -0
  15. package/dist/adapters/claude-worker-protocol.js.map +1 -0
  16. package/dist/adapters/claude-worker.d.ts +1 -0
  17. package/dist/adapters/claude-worker.js +126 -0
  18. package/dist/adapters/claude-worker.js.map +1 -0
  19. package/dist/adapters/claude.d.ts +16 -6
  20. package/dist/adapters/claude.js +138 -68
  21. package/dist/adapters/claude.js.map +1 -1
  22. package/dist/cli/catalog-worker.js.map +1 -1
  23. package/dist/cli/dashboard-client.js +19 -30
  24. package/dist/cli/dashboard-client.js.map +1 -1
  25. package/dist/cli/main.js +53 -45
  26. package/dist/cli/main.js.map +1 -1
  27. package/dist/errors.d.ts +2 -2
  28. package/dist/errors.js.map +1 -1
  29. package/dist/index.d.ts +6 -0
  30. package/dist/index.js +3 -0
  31. package/dist/index.js.map +1 -1
  32. package/dist/runtime/approval-registry.d.ts +9 -0
  33. package/dist/runtime/approval-registry.js +143 -4
  34. package/dist/runtime/approval-registry.js.map +1 -1
  35. package/dist/runtime/capture.d.ts +22 -0
  36. package/dist/runtime/capture.js +320 -0
  37. package/dist/runtime/capture.js.map +1 -0
  38. package/dist/runtime/catalog.d.ts +39 -0
  39. package/dist/runtime/catalog.js +84 -0
  40. package/dist/runtime/catalog.js.map +1 -0
  41. package/dist/runtime/client.d.ts +2 -1
  42. package/dist/runtime/client.js +52 -65
  43. package/dist/runtime/client.js.map +1 -1
  44. package/dist/runtime/coordinator.d.ts +44 -7
  45. package/dist/runtime/coordinator.js +265 -31
  46. package/dist/runtime/coordinator.js.map +1 -1
  47. package/dist/runtime/daemon.js +12 -6
  48. package/dist/runtime/daemon.js.map +1 -1
  49. package/dist/runtime/dashboard-workspace.js +5 -1
  50. package/dist/runtime/dashboard-workspace.js.map +1 -1
  51. package/dist/runtime/definition.d.ts +6 -1
  52. package/dist/runtime/definition.js +31 -1
  53. package/dist/runtime/definition.js.map +1 -1
  54. package/dist/runtime/native-owner.js +7 -1
  55. package/dist/runtime/native-owner.js.map +1 -1
  56. package/dist/runtime/pagination.d.ts +9 -0
  57. package/dist/runtime/pagination.js +36 -0
  58. package/dist/runtime/pagination.js.map +1 -0
  59. package/dist/runtime/sdk-observation.d.ts +8 -0
  60. package/dist/runtime/sdk-observation.js +75 -0
  61. package/dist/runtime/sdk-observation.js.map +1 -0
  62. package/dist/runtime/sdk-projection.d.ts +8 -0
  63. package/dist/runtime/sdk-projection.js +19 -0
  64. package/dist/runtime/sdk-projection.js.map +1 -0
  65. package/dist/runtime/sdk-service.d.ts +11 -0
  66. package/dist/runtime/sdk-service.js +109 -0
  67. package/dist/runtime/sdk-service.js.map +1 -0
  68. package/dist/runtime/select-native.d.ts +4 -1
  69. package/dist/runtime/select-native.js +14 -17
  70. package/dist/runtime/select-native.js.map +1 -1
  71. package/dist/runtime/service.d.ts +11 -1
  72. package/dist/runtime/service.js +178 -3
  73. package/dist/runtime/service.js.map +1 -1
  74. package/dist/runtime/session-launcher.js +1 -1
  75. package/dist/runtime/session-launcher.js.map +1 -1
  76. package/dist/runtime/snapshots.d.ts +103 -0
  77. package/dist/runtime/snapshots.js +124 -0
  78. package/dist/runtime/snapshots.js.map +1 -0
  79. package/dist/runtime/state.d.ts +26 -0
  80. package/dist/runtime/state.js +86 -17
  81. package/dist/runtime/state.js.map +1 -1
  82. package/dist/runtime/task-data.d.ts +38 -0
  83. package/dist/runtime/task-data.js +2 -0
  84. package/dist/runtime/task-data.js.map +1 -0
  85. package/dist/runtime/transport.d.ts +13 -0
  86. package/dist/runtime/transport.js +166 -0
  87. package/dist/runtime/transport.js.map +1 -0
  88. package/dist/runtime/types.d.ts +28 -9
  89. package/dist/runtime/types.js.map +1 -1
  90. package/dist/runtime/worker-client.js +2 -0
  91. package/dist/runtime/worker-client.js.map +1 -1
  92. package/dist/runtime/worker-server.js +105 -24
  93. package/dist/runtime/worker-server.js.map +1 -1
  94. package/dist/sdk/connected-types.d.ts +42 -0
  95. package/dist/sdk/connected-types.js +2 -0
  96. package/dist/sdk/connected-types.js.map +1 -0
  97. package/dist/sdk/connected.d.ts +3 -0
  98. package/dist/sdk/connected.js +232 -0
  99. package/dist/sdk/connected.js.map +1 -0
  100. package/dist/sdk/execution-definition.d.ts +3 -0
  101. package/dist/sdk/execution-definition.js +59 -0
  102. package/dist/sdk/execution-definition.js.map +1 -0
  103. package/dist/sdk/execution-driver.d.ts +6 -0
  104. package/dist/sdk/execution-driver.js +86 -0
  105. package/dist/sdk/execution-driver.js.map +1 -0
  106. package/dist/sdk/execution-observation.d.ts +3 -0
  107. package/dist/sdk/execution-observation.js +35 -0
  108. package/dist/sdk/execution-observation.js.map +1 -0
  109. package/dist/sdk/execution-options.d.ts +17 -0
  110. package/dist/sdk/execution-options.js +115 -0
  111. package/dist/sdk/execution-options.js.map +1 -0
  112. package/dist/sdk/execution-types.d.ts +72 -0
  113. package/dist/sdk/execution-types.js +2 -0
  114. package/dist/sdk/execution-types.js.map +1 -0
  115. package/dist/sdk/execution.d.ts +3 -0
  116. package/dist/sdk/execution.js +3 -0
  117. package/dist/sdk/execution.js.map +1 -0
  118. package/dist/sdk/hosted-error.d.ts +3 -0
  119. package/dist/sdk/hosted-error.js +14 -0
  120. package/dist/sdk/hosted-error.js.map +1 -0
  121. package/dist/sdk/hosted.d.ts +23 -0
  122. package/dist/sdk/hosted.js +204 -0
  123. package/dist/sdk/hosted.js.map +1 -0
  124. package/dist/sdk/runner.d.ts +5 -0
  125. package/dist/sdk/runner.js +107 -0
  126. package/dist/sdk/runner.js.map +1 -0
  127. package/dist/sdk/tools.js +4 -1
  128. package/dist/sdk/tools.js.map +1 -1
  129. package/package.json +3 -3
  130. package/sdk/access-config.md +2 -0
  131. package/sdk/adapter-contract.md +8 -0
  132. package/sdk/agent.md +1 -1
  133. package/sdk/approvals.md +2 -0
  134. package/sdk/completion-notifications.md +2 -0
  135. package/sdk/distribution.md +4 -2
  136. package/sdk/examples/chat-tool.ts +126 -0
  137. package/sdk/execution.md +743 -0
  138. package/sdk/index.md +45 -21
  139. package/sdk/message-delivery.md +2 -0
  140. package/sdk/permissions.md +2 -0
  141. package/sdk/plugins/sub-agents.md +4 -2
  142. package/sdk/project-team.md +23 -1
  143. package/sdk/sessions.md +2 -0
  144. package/sdk/tools.md +3 -1
  145. package/sdk/v1-runtime.md +7 -5
  146. package/dist/cli/catalog.d.ts +0 -26
  147. package/dist/cli/catalog.js +0 -41
  148. package/dist/cli/catalog.js.map +0 -1
package/sdk/index.md CHANGED
@@ -1,26 +1,50 @@
1
- # SDK and CLI
1
+ # SDK and CLI reference
2
2
 
3
- The CLI runs generic Codex, Claude Code, fx, OpenCode, GitHub Copilot, and Cursor agents without definition files. The optional TypeScript SDK defines reusable specialists on those same external harnesses. The CLI coordinates sessions, queues, follow-ups, and nested delegation in caller-supplied working directories.
3
+ This index is the entry point to the authoritative subharness contracts. The TypeScript SDK supports application-owned execution and connections to the shared local coordinator. The CLI lets a coding agent or developer run native harnesses directly, reuse specialists, and coordinate sessions, queues, responses, and approvals.
4
4
 
5
- - [Distribution](distribution.md): package identity, local installation, and release boundaries.
5
+ ## SDK API
6
+
7
+ - [Connected and embedded execution](execution.md): client and runner ownership, sessions, tasks, complete responses, approvals, and hosted delegation.
8
+ - [Agent definitions](agent.md): package exports, fields, harness options, and definition examples.
9
+ - [Custom tools](tools.md): validated application functions exposed through native harness integrations.
10
+ - [Subagents](plugins/sub-agents.md): nested delegation, lineage, context, and result-delivery boundaries.
11
+
12
+ ## CLI
13
+
14
+ - [CLI](cli/index.md): commands, input, admission, waiting, follow-ups, control, and native permission responses.
15
+ - [CLI output](cli/output.md): compact text, typed JSONL records, states, and exit codes.
16
+ - [Dashboard presentation](cli/dashboard-design.md): the read-only live terminal hierarchy and interaction contract.
17
+ - [Agent discovery](config.md): repository and global definitions, naming, and personal worktree settings.
6
18
  - [Agent skill](agent-skill.md): the installable skill that teaches a coding agent to delegate with the CLI.
7
- - [Agent definitions](agent.md): package exports, fields, harness options, and examples.
8
- - [Custom tools](tools.md): validated tool functions exposed through native harness integrations.
9
- - [Discovery](config.md): repository/global definitions and personal worktree settings.
10
- - [Personal access](access-config.md): subscription discovery, explicit API keys, and project OIDC.
11
- - [Native permissions](permissions.md): session permission options, native limits, and background delegation.
12
- - [Permission requests](approvals.md): request-specific schemas, structured answers, and approval lifecycle.
13
- - [Harnesses](harnesses.md): selection, capabilities, and fallback boundaries.
14
- - [CLI](cli/index.md): commands and response waiting.
15
- - [Output](cli/output.md): compact text and typed JSONL records.
16
- - [Error diagnostics](diagnostics.md): failure categories, safe context, and recovery guidance.
17
- - [Sessions](sessions.md): task identity, state, and recovery.
18
- - [Message delivery](message-delivery.md): queue, steer, interrupt, and cancellation.
19
- - [Subagents](plugins/sub-agents.md): nested delegation and context boundaries.
20
- - [Response delivery](completion-notifications.md): return points and parent continuation.
21
- - [Runtime](v1-runtime.md): execution ownership, loading, limits, and failure handling.
22
- - [Native adapters](adapter-contract.md): integration behavior and capability limits.
23
19
 
24
- These documents describe the v1 contract. They do not authorize automatic conversation migration, a custom model harness, sandbox provisioning, or a separate pipeline-definition API.
20
+ ## Lifecycle and access
21
+
22
+ - [Sessions](sessions.md): task identity, state, queue ownership, and recovery boundaries.
23
+ - [Message delivery](message-delivery.md): queue, steer, interrupt, cancellation, and failure handling.
24
+ - [Response delivery](completion-notifications.md): complete responses, return points, and parent continuation.
25
+ - [Permission requests](approvals.md): request-specific CLI schemas, structured SDK actions, ownership, and lifecycle.
26
+ - [Authentication](authentication.md): native credentials, subscriptions, billing, and trust boundaries.
27
+ - [Personal access configuration](access-config.md): subscription discovery, explicit API keys, project OIDC, and local renewal.
28
+ - [Native permissions](permissions.md): session policies, native limits, and background delegation.
29
+ - [Error diagnostics](diagnostics.md): safe failure context and recovery guidance.
30
+ - [Distribution](distribution.md): package identity, installation, verification, and release boundaries.
31
+ - [Harness selection](harnesses.md): supported targets, capabilities, and fallback boundaries.
25
32
 
26
- The adapter contracts cover [fx](fx.md), [OpenCode](opencode.md), [GitHub Copilot](copilot.md), and [Cursor](cursor.md). The shared configuration for the three additional harnesses is defined in [Additional native harnesses](additional-harnesses.md). The [repository team](project-team.md) defines the roles used to develop this project.
33
+ ## Harness details
34
+
35
+ - [Additional native harnesses](additional-harnesses.md): shared configuration for OpenCode, GitHub Copilot, and Cursor.
36
+ - [fx](fx.md): fx ACP behavior, tools, access, permissions, and lifecycle.
37
+ - [OpenCode](opencode.md): OpenCode integration and supported access routes.
38
+ - [GitHub Copilot](copilot.md): Copilot integration and supported access routes.
39
+ - [Cursor](cursor.md): Cursor subscription and API-key integration boundaries.
40
+
41
+ ## Maintainer internals
42
+
43
+ - [Native adapter contract](adapter-contract.md): integration behavior and capability limits.
44
+ - [v1 runtime](v1-runtime.md): execution ownership, loading, limits, and failure handling.
45
+ - [Dashboard inspection](cli/dashboard-inspection.md): coordinator projection used by the terminal dashboard.
46
+ - [Evaluations](evals.md): maintained evaluation inputs and scoring boundaries.
47
+ - [Repository agent team](project-team.md): reusable roles used to develop this project.
48
+ - [PR integration](pr-integration.md): reviewed-head and integration requirements.
49
+
50
+ These documents describe the v1 contract. They do not authorize automatic conversation migration, a custom model harness, sandbox provisioning, or a separate pipeline-definition API.
@@ -1,5 +1,7 @@
1
1
  # Message Delivery
2
2
 
3
+ The [execution SDK](execution.md) binds these queue, steer, interrupt, and cancellation semantics to session/task handles. Observer abortion detaches observation; it does not cancel work. Session or embedded-runner close stops owned execution explicitly; connected-client disconnect does not.
4
+
3
5
  `subharness send <session-id> --delivery <queue|steer|interrupt> [--detach] --prompt <text>` controls delivery. `queue` is the default. Each session has one active library task and a FIFO queue; a library task can contain multiple native turns while coordinating descendants.
4
6
 
5
7
  | Mode | Effect |
@@ -1,5 +1,7 @@
1
1
  # Native Permissions
2
2
 
3
+ The [execution SDK](execution.md) uses the same native permission options. Embedded SDK-hosted declared-child tools receive native custom-tool permissions; they do not install CLI launcher shell rules. Host callbacks are trusted application code and are not confined by a native sandbox.
4
+
3
5
  The Codex, Claude Code, and fx constructors accept optional native permission settings directly alongside model options. These settings configure the native session without modifying persistent native settings or creating a Subharness sandbox. OpenCode instead uses its isolated native ask policy, Copilot uses native manual permission mode, and neither exposes a public permission selector. Cursor exposes its documented SDK `sandboxMode` for API-key access; subscription ACP access rejects explicit sandbox settings and supports the documented once-only native approvals. Supported native tool approvals are surfaced to the caller through the [structured approval flow](approvals.md); an explicit valid caller decision is required before authorization. The installed harness evaluates the selected policy, and the external execution environment enforces its remaining restrictions.
4
6
 
5
7
  Omitted settings preserve native configuration. Explicit settings remain fixed for session follow-ups. A child uses its own definition and native configuration; it does not inherit the parent's explicit permission options. Invalid definitions fail before execution. Unsupported or observably rejected explicit settings fail without fallback to another harness or permission policy.
@@ -1,5 +1,7 @@
1
1
  # Subagents
2
2
 
3
+ The invocation rules below describe CLI-hosted sessions. The [execution SDK](../execution.md) also supports in-memory definitions through explicitly hosted delegation tools, with private parent binding and the same task lineage/completion semantics. Embedded SDK sessions do not create or require the CLI launcher, its shell grants, or a coordinator service. Native adapter transport and permission limits still apply.
4
+
3
5
  An agent's optional `subagents` map declares and authorizes the agents it can invoke. Values are ordinary `AgentDefinition` objects; children can have their own subagents. Declaration alone does not execute them or register them in a repository/global catalog.
4
6
 
5
7
  ```ts
@@ -29,9 +31,9 @@ The launcher restores its coordinator location and parent context before invokin
29
31
 
30
32
  For Claude Code, declaring at least one subagent adds native permission rules for the current session's exact launcher. Equivalent quoted or unquoted spellings are allowed only when they identify the same literal executable. These rules authorize `run subagent:<name>` for the declared names, plus the CLI's `list`, `--help`, `send`, `wait`, `status`, `queue`, `cancel`, and `resume` operations. They do not authorize launching repository or global agents through `run`, another executable, or arbitrary shell commands. Follow-up and observation commands retain their documented identifier-based behavior; the permission rules do not introduce a new task-access policy.
31
33
 
32
- The adapter combines these rules with declared custom-tool permissions. Those rules do not write user/project permission settings or change the native permission mode; explicit constructor options independently select session permission settings as defined in [Native Permissions](../permissions.md). Native deny rules, explicit approval requirements, managed policy, and sandbox restrictions remain authoritative. A request that still requires approval returns `INPUT_REQUIRED`. Each child starts with its own native tool permissions; permission to launch it does not grant permission for its edits or shell commands. A session without declared subagents receives no delegation rules. If a launcher path cannot be represented as a literal command in the native permission syntax, startup fails with `INVALID_CONFIG` rather than adding a broader rule.
34
+ The adapter combines these rules with declared custom-tool permissions. Those rules do not write user/project permission settings or change the native permission mode; explicit constructor options independently select session permission settings as defined in [Native Permissions](../permissions.md). Native deny rules, explicit approval requirements, managed policy, and sandbox restrictions remain authoritative. Supported permission requests during an active turn use the [structured approval flow](../approvals.md); unsupported interactive input and startup-time requests fail with `INPUT_REQUIRED`. Each child starts with its own native tool permissions; permission to launch it does not grant permission for its edits or shell commands. A session without declared subagents receives no delegation rules. If a launcher path cannot be represented as a literal command in the native permission syntax, startup fails with `INVALID_CONFIG` rather than adding a broader rule.
33
35
 
34
- Codex receives the same declared-child instructions and private launcher, but the adapter does not add native allow rules for them. Codex must already have effective permission to execute the launcher, read the files needed by that execution, and contact the coordinator. Native behavior differs across Codex versions, managed policies, sandbox configurations, and host environments. In some combinations, commands that access protected locations such as `.subharness/`, execute the private launcher, or use loopback networking can require approval or remain unavailable; this is an environment-dependent limitation, not a universal Codex rule. A resulting approval request returns `INPUT_REQUIRED`, including when the requested command would launch an authorized declared child. The library does not automatically approve the request, disable sandboxing, or replace shell delegation with another transport.
36
+ Codex receives the same declared-child instructions and private launcher, but the adapter does not add native allow rules for them. Codex must already have effective permission to execute the launcher, read the files needed by that execution, and contact the coordinator. Native behavior differs across Codex versions, managed policies, sandbox configurations, and host environments. In some combinations, commands that access protected locations such as `.subharness/`, execute the private launcher, or use loopback networking can require approval or remain unavailable; this is an environment-dependent limitation, not a universal Codex rule. Supported permission requests during an active turn use the [structured approval flow](../approvals.md), including requests to launch an authorized declared child; unsupported interactive input and startup-time requests fail with `INPUT_REQUIRED`. The library does not automatically approve the request, disable sandboxing, or replace shell delegation with another transport.
35
37
 
36
38
  For every harness, the native execution environment must allow the CLI to read its private launcher and contact the coordinator over loopback HTTP. A native sandbox that blocks local networking also blocks CLI delegation. The library does not relax that policy automatically; the caller supplies explicit native permission options, native settings, or an external execution environment. A lead can instead own independent review outside a managed agent's native delegation flow when the environment cannot grant these prerequisites.
37
39
 
@@ -1,6 +1,6 @@
1
1
  # Repository Agent Team
2
2
 
3
- This repository keeps six reusable agents in `.subharness/agents/`. An agent defines a stable responsibility, model, and tool access. A skill supplies task-specific instructions that the agent reads when relevant. Adding a technique or library does not require another agent definition.
3
+ This repository keeps nine reusable agents in `.subharness/agents/`. An agent defines a stable responsibility, model, and tool access. A skill supplies task-specific instructions that the agent reads when relevant. Adding a technique or library does not require another agent definition.
4
4
 
5
5
  ## Roles
6
6
 
@@ -9,6 +9,9 @@ This repository keeps six reusable agents in `.subharness/agents/`. An agent def
9
9
  | `architect` | Codex, `gpt-6-astra`, high effort | Evaluate architecture and API decisions; develop requested design concepts and assets; perform independent visual review when assigned. |
10
10
  | `developer` | Codex, `gpt-5.6-sol`, high effort | Implement documented behavior and application structure with focused TDD and independent review. |
11
11
  | `visual-engineer` | fx, `anthropic/claude-fable-5.1`, native default effort | Implement approved interface styling and native vgpu/WGSL effects using the relevant skill. |
12
+ | `api-researcher` | Codex, `gpt-5.6-luna`, low effort | Collect primary-source API evidence: signatures, defaults, events, errors, and lifecycle rules. |
13
+ | `systems-researcher` | Codex, `gpt-5.6-luna`, low effort | Collect evidence from related systems, including job queues, process runners, event streams, actors, and UI state synchronization. |
14
+ | `planner` | Codex, `gpt-6-astra`, high effort | Turn settled contracts into bounded implementation assignments and verification criteria in ignored scratch files. |
12
15
  | `researcher` | fx, `google/gemini-3.8-flash`, native default effort | Answer a bounded technical or design question with primary-source evidence. |
13
16
  | `reviewer` | Claude Code, `claude-opus-5[1m]`, high effort | Independently review correctness, lifecycle, credential routing, and contract compliance without editing files. |
14
17
  | `integrator` | Codex, `gpt-5.6-sol`, high effort | Merge only the exact PRs and reviewed heads explicitly authorized by the lead for the current assignment, following [PR integration](pr-integration.md). |
@@ -23,6 +26,18 @@ The repository's Codex roles explicitly select `approvalPolicy: "never"`, `sandb
23
26
 
24
27
  Implementation roles return unstaged working-tree changes and verification evidence. Local Git staging and commits belong to the lead unless the assignment explicitly authorizes them. When an implementation task requires moving or deleting ordinary files, roles use filesystem operations; subsequent Git staging records the renames. By default, Codex workspace-write protects `.git`, `.agents`, and `.codex` inside the writable workspace. It also protects the Git directory named by a `.git` pointer file, even when that directory is inside the workspace; for a linked worktree, that directory is in the main checkout's Git directory and holds the worktree's index. A required change under those protected paths is reported with the exact operation, affected paths, and partial effects for lead-managed execution. A copied replacement does not complete a move while the original remains.
25
28
 
29
+ ## Assigning work by complexity
30
+
31
+ Use `api-researcher` for bounded source searches and API inventories. Use `systems-researcher` for related problems outside agent orchestration. Both use the explicitly selected Codex model, read `.agents/skills/source-research/SKILL.md`, and write only the caller-named files under `.context/research/`. Their output records source URLs or paths, retrieval dates, revisions, observed behavior, and uncertainty. They distinguish facts from inference, do not rank architectural alternatives or settle contracts, and return missing evidence to the lead. The existing fx `researcher` remains available for general technical and visual evidence tasks. The two research roles have different standing evidence responsibilities: `api-researcher` inventories caller-visible interfaces, while `systems-researcher` investigates ownership, failure handling, delivery, and retention across related domains. Keeping those lenses explicit helps a design survey cover both interface conventions and operational behavior. Individual libraries and technologies remain task inputs, not additional permanent roles.
32
+
33
+ Use `architect` for reasoning across that evidence, including API alternatives with concrete signatures and usage examples, lifecycle ownership, cancellation, errors, compatibility, and misuse cases. Recommendations do not authorize implementation. The lead settles clear choices under `AGENTS.md` and asks the human only for unresolved product tradeoffs or signatures outside delegated authority.
34
+
35
+ Use `planner` only after the relevant decisions are settled in repository documentation. It reads the actual affected implementation and writes only the caller-named files under `.context/research/`. Its assignments identify the governing contracts, owned files, dependencies, behavior-focused failing tests, validation commands, and acceptance criteria. It reports missing decisions instead of choosing public behavior. Plans and progress records are scratch artifacts; they never replace repository contracts, authorize implementation, or become public documentation. The lead validates the assignments and owns task boundaries and implementation authorization.
36
+
37
+ Use `developer` for implementation and bounded review fixes, and `reviewer` for independent review. Documentation work uses the existing developer or architect with an explicit file scope; it does not need another permanent role. Graphics-specific research uses the existing researcher with the graphics skill when relevant. The `api-researcher`, `systems-researcher`, and `planner` return results to the lead without delegation. The lead supplies bounded questions, sources or search angles, output paths, and stopping criteria so economical evidence collection does not turn into unbounded design work.
38
+
39
+ These assignments express task complexity, not a guaranteed price or model benchmark. Models are fixed in definitions; there is no automatic routing based on a guessed task difficulty, silent fallback, or credential change. When the selected model or capability is unavailable, report that limitation to the lead. A follow-up can narrow an unanswered research question in the same session; a new independent angle gets a separate session.
40
+
26
41
  ## Skills and task context
27
42
 
28
43
  Repository skills live in `.agents/skills/<name>/SKILL.md`. The short index in `AGENTS.md` explains when each skill applies. Agents read only the relevant skill and supporting references for their current task. Skill contents are not concatenated into every agent's instructions.
@@ -37,6 +52,9 @@ subharness run repo:architect --prompt "Read website/design.md and .agents/skill
37
52
  subharness run repo:visual-engineer --prompt "Use .agents/skills/web-interface/SKILL.md. Implement the hero layout documented in website/design.md. Limit changes to the hero styles."
38
53
  subharness run repo:developer --prompt "Use .agents/skills/web-interface/SKILL.md. Read website/design.md. Check the hero's semantic HTML and keyboard behavior without changing styles."
39
54
  subharness run repo:developer --prompt "Use .agents/skills/webgpu-graphics/SKILL.md. Read website/graphics.md. Verify the mascot camera's documented framing with focused tests."
55
+ subharness run repo:api-researcher --prompt "Use .agents/skills/source-research/SKILL.md. Read sdk/sessions.md. Record official SDK cancellation signatures in .context/research/sdk-cancellation.md."
56
+ subharness run repo:systems-researcher --prompt "Use .agents/skills/source-research/SKILL.md. Read sdk/message-delivery.md. Record queue and observer lifecycle evidence in .context/research/queue-lifecycle.md."
57
+ subharness run repo:planner --prompt "Read sdk/sessions.md and sdk/message-delivery.md. Inspect src/runtime/coordinator.ts. Write bounded verification assignments for those settled contracts to .context/research/session-verification-plan.md."
40
58
  subharness run repo:researcher --prompt "Use .agents/skills/source-research/SKILL.md. Read sdk/fx.md and src/adapters/fx.ts. Explain cancellation behavior with file references."
41
59
  subharness run repo:reviewer --prompt "Review the mascot camera changes against website/graphics.md. Report actionable findings without editing files."
42
60
  ```
@@ -45,6 +63,10 @@ The website's illustrative conversation shows tasks delegated to Claude Code and
45
63
 
46
64
  ## Delegation and review
47
65
 
66
+ Every implementation handoff and final PR review includes a file-purpose audit against the target branch. The planner includes this in acceptance criteria, the developer removes temporary artifacts from its changes, and the reviewer inspects the complete added and changed file inventory, including documentation and supporting files. Findings identify the file and why it has no lasting repository purpose. The lead verifies the final inventory before declaring the PR ready. A bounded review states its coverage; it does not establish that the whole PR has passed this audit.
67
+
68
+ Temporary proposals, plans, progress logs, research notes, one-off diagnostics, and review output belong in ignored `.context/` files. Settled decisions belong in canonical documentation; superseded proposals and purposeless redirect stubs are removed. Intentional regression fixtures, maintained examples, evaluation tools, and product documentation remain repository assets. File purpose, rather than its name alone, determines whether it belongs in the final changes.
69
+
48
70
  CLI and runtime work uses the existing architect, developer, and reviewer roles. Separate developer sessions can own independent modules; scope and governing contracts distinguish their assignments without adding permanent roles. The architect evaluates native protocol constraints, the developer implements and integrates behavior with TDD, and the reviewer independently checks user-facing behavior, lifecycle, and credential routing. The lead coordinates contracts, assignments, and final verification. Implementation and fixes run through repository agents whenever supported, so follow-ups, queues, and review cycles exercise subharness itself. Reproducible coordination failures are evidence for library improvements under the same contract and review rules.
49
71
 
50
72
  Repository role instructions follow the same delegation preference as the public skill and managed child instructions: use one attached `run` through known host background-command controls, continue independent work, and collect its output. Use `--detach` followed later by `wait` when those controls are unavailable or uncertain. A hosted `run` already observes the first response and does not require a redundant `wait` or unconditional `status`. This preference does not authorize undeclared children or override a role's delegation restrictions.
package/sdk/sessions.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # Sessions and Tasks
2
2
 
3
+ Applications can use the [execution SDK](execution.md) through an embedded runner or a connected client. Embedded records belong to the runner; connected records belong to the same shared coordinator as CLI records. Session close stops owned execution, while client disconnect releases observation without cancelling work.
4
+
3
5
  An agent definition describes reusable behavior. A session is one native conversation in a fixed execution directory. A task is a unit of work within that session. Tasks and sessions have separate opaque identifiers and are not shell process IDs.
4
6
 
5
7
  Each `run` creates a new session; `send` creates follow-up tasks or steers the active task. A session retains native conversation state and its loaded instructions, tools, and harness configuration between tasks. The external harness owns its context and compaction.
package/sdk/tools.md CHANGED
@@ -1,5 +1,7 @@
1
1
  # Custom Tools
2
2
 
3
+ With the embedded [execution SDK](execution.md), inline tool closures execute in the application process with its unchanged cwd and environment, rather than the CLI session worker. Captured application state remains live; callbacks may be shared across sessions. SDK cancellation drains admitted callbacks and does not force-stop arbitrary JavaScript.
4
+
3
5
  `tool({ description, inputSchema, execute })` defines a function that a native harness can invoke. The map key in `agent.tools` is its public name. Declaring a tool does not execute it.
4
6
 
5
7
  ```ts
@@ -27,7 +29,7 @@ All three fields are required. `description` is a nonempty string. `inputSchema`
27
29
 
28
30
  Validation runs before execution; invalid arguments never reach the function. Unsupported schemas fail during definition validation. Non-serializable or oversized outputs and thrown exceptions become tool errors. Tool results are limited to 1 MiB. Errors do not masquerade as successful outputs.
29
31
 
30
- Tools run in their session worker's execution directory with that worker's environment. The adapter registers them in a native namespace without replacing the harness's native tools or model loop. Declaring a custom tool authorizes that agent to invoke it. Native tool permission policies remain with the harness.
32
+ Connected and CLI-hosted tools run in the retained definition graph owner's creation directory and environment. Managed children share that captured callback context even when their native harness uses a different requested directory; use explicit paths or arguments for child-specific operations. Embedded SDK-hosted closures use the application context described above. The adapter registers them in a native namespace without replacing the harness's native tools or model loop. Declaring a custom tool authorizes that agent to invoke it. Native tool permission policies remain with the harness.
31
33
 
32
34
  ## Image results
33
35
 
package/sdk/v1-runtime.md CHANGED
@@ -1,10 +1,10 @@
1
1
  # V1 Runtime Contract
2
2
 
3
- The first usable version supplies a TypeScript definition SDK and the `subharness` CLI with Codex, Claude Code, fx, OpenCode, GitHub Copilot, and Cursor adapters. The library coordinates existing harnesses; it does not implement a model loop, sandbox, worktree manager, or native permission system.
3
+ The first usable version supplies a TypeScript definition and execution SDK and the `subharness` CLI with Codex, Claude Code, fx, OpenCode, GitHub Copilot, and Cursor adapters. The library coordinates existing harnesses; it does not implement a model loop, sandbox, worktree manager, or native permission system.
4
4
 
5
5
  ## Package and definitions
6
6
 
7
- The package is `subharness`, with the primary executable `subharness` and identical `agent` compatibility alias. Node.js 22.18 or newer is required. ESM exports include `agent`, `tool`, `toolResult`, `codex`, `claudeCode`, `fx`, `opencode`, `copilot`, `cursor`, and their definition/configuration types. The public SDK defines reusable specialists; direct CLI harness targets also execute without a definition. Execution in v1 uses the CLI. Definition objects have readonly configuration fields and no execution methods. They contain functions and schemas and are not a serialization format.
7
+ The package is `subharness`, with the primary executable `subharness` and identical `agent` compatibility alias. Node.js 22.18 or newer is required. ESM exports include `agent`, `tool`, `toolResult`, `codex`, `claudeCode`, `fx`, `opencode`, `copilot`, `cursor`, and their definition/configuration types. The public SDK defines reusable specialists; direct CLI harness targets also execute without a definition. Execution uses either the CLI or the connected or embedded [execution SDK](execution.md). The SDK additionally exports the client, runner, handle, result, access, approval, and error types defined there. The daemon, worker, catalog, and launcher rules below describe CLI execution; an embedded runner owns its coordinator and inline tool closures in the host process, while a connected client shares the CLI coordinator. Definition objects have readonly configuration fields and no execution methods. They contain functions and schemas and are not a serialization format.
8
8
 
9
9
  ```ts
10
10
  import { agent, codex, claudeCode, tool } from "subharness";
@@ -28,7 +28,7 @@ An omitted `--cwd` uses the command's working directory. `--prompt-file` paths r
28
28
 
29
29
  An on-demand local coordinator owns sessions, queues, task relationships, and response records independently of individual CLI commands. It starts automatically; users do not install or manage a service. Each native session runs in a separate worker process whose working directory is the selected execution directory. Definition loading and custom tool execution in that worker use the same directory. Direct harness sessions carry a built-in target descriptor instead of a definition source reference and do not load TypeScript modules. They supply no specialist instructions, custom tools, or declared children; native instructions and project settings remain effective. Workers inherit the submitting environment, subject to the adapter's explicit authentication selection.
30
30
 
31
- `check` is a CLI startup probe rather than an execution operation. It resolves the target and access configuration as `run` does, opens the native session in an isolated worker, and closes it without admitting a task or calling the adapter's turn interface. Success is withheld until the isolated worker exits and adapter-owned native processes confirm termination. Cleanup failure or uncertain native termination produces an error; after a failed graceful close, worker termination remains bounded and retains the cleanup diagnostic. It does not expose an SDK execution method and does not require a coordinator for ordinary direct or specialist checks. Managed declared-child resolution still requires the active parent context used by `run`.
31
+ `check` is a CLI startup probe rather than an execution operation. It resolves the target and access configuration as `run` does, opens the native session in an isolated worker, and closes it without admitting a task or calling the adapter's turn interface. Success is withheld until the isolated worker exits and adapter-owned native processes confirm termination. Cleanup failure or uncertain native termination produces an error; after a failed graceful close, worker termination remains bounded and retains the cleanup diagnostic. The connected SDK exposes its own startup probe as `client.agents.check` under the [execution contract](execution.md); neither probe submits a task. The CLI probe does not require a coordinator for ordinary direct or specialist checks. Managed declared-child resolution still requires the active parent context used by `run`.
32
32
 
33
33
  Readiness means only that the selected target's startup checks passed at that moment. It does not guarantee quota, successful task execution, shell or child-launch permissions, or continued availability, and it does not recursively check descendants. The probe may create an empty native conversation, a temporary session launcher, and adapter-owned temporary files. Loading personal access settings may update Git's local exclude file. Normal worker close removes library-owned temporary files. A removal failure is reported even though files can remain, and abrupt environment termination still cannot guarantee file cleanup.
34
34
 
@@ -66,13 +66,15 @@ Ordinary text/JSON tool results and complete responses are limited to 1 MiB. Ric
66
66
 
67
67
  A managed task cannot delegate follow-up work into its own session or an ancestor's session. Such an admission returns `INVALID_PARENT` before changing any execution: that queued work would otherwise wait for the very task whose completion depends on it. Invalid delegation and replacement requests never cancel existing work.
68
68
 
69
- Each candidate coordinator, rather than the CLI command that spawned it, holds an operating-system-backed startup lock from its final endpoint check through service startup and atomic endpoint publication. The lock is released automatically if the candidate exits. After acquiring it, a candidate retires without publishing when the retained endpoint gives an authenticated health response for the recorded coordinator instance. This prevents a caller exit or a later candidate from exposing competing endpoint publication.
69
+ The CLI and connected SDK select the same coordinator directory: an explicit SDK `stateDirectory`, otherwise `AGENT_STATE_DIR`, otherwise `~/.subharness/state/shared`. Connection authenticates the instance and requires protocol version 1 with the applicable `sdk-v1` or `cli-v1` capability.
70
+
71
+ Each candidate coordinator, rather than the CLI command that spawned it, holds an operating-system-backed startup lock from its final endpoint check through service startup and atomic endpoint publication. The lock is released automatically if the candidate exits. After acquiring it, a candidate retires without publishing when the retained endpoint gives a compatible authenticated health response for the recorded coordinator instance. It starts only when metadata is absent, or a well-formed stale record has a proven-dead owner and an unresponsive endpoint. Malformed, unauthorized, incompatible, or uncertain endpoints fail explicitly without replacement. This prevents a caller exit or a later candidate from exposing competing endpoint publication.
70
72
 
71
73
  Startup callers do not infer whether their candidate published from an endpoint observation and do not signal a candidate based on such an observation. When its startup deadline expires, a caller sends its candidate a private retirement request. The candidate serializes that request with its publication transition while it still owns the startup lock. If retirement wins, the candidate closes any service that was never published, releases startup ownership, and confirms that it cannot publish later. If publication wins, including when another caller has already admitted work, the candidate reports its published endpoint and remains running. The original caller then uses that endpoint instead of terminating the coordinator.
72
74
 
73
75
  Lock contention is bounded by the spawning command's startup deadline. Waiting for the candidate's publication-or-retirement response uses an additional fixed confirmation window, so command completion remains bounded. If the candidate does not respond, startup fails with `STARTUP_FAILED` stating that retirement could not be confirmed, and the caller leaves the candidate untouched. A later authenticated endpoint discovery may therefore find that candidate. An unconfirmed result never claims that the process stopped and never authorizes killing a potentially published coordinator.
74
76
 
75
- Coordinators leave endpoint records in place during shutdown. Legacy pathname lock artifacts do not grant startup ownership and are left untouched. An unavailable endpoint, an unrelated HTTP server on the recorded port, or a legacy record without the current authenticated instance identity does not suppress replacement startup. A replacement coordinator atomically overwrites the record, and tasks owned by a replaced coordinator are not reconstructed. An interrupted coordinator response is reported as unavailable without exposing native diagnostics or automatically repeating the request. Disconnecting an observer detaches that observation; it does not cancel execution.
77
+ Coordinators leave endpoint records in place during shutdown. Legacy pathname lock artifacts do not grant startup ownership and are left untouched. An unavailable endpoint alone does not prove absence. A live or unknown owner, authentication failure, incompatible protocol, or instance mismatch forbids replacement startup. A permitted replacement atomically overwrites only a proven-stale record; tasks owned by the previous coordinator are not reconstructed. An interrupted coordinator response is reported as unavailable without exposing native diagnostics or automatically repeating the request. Disconnecting an observer detaches that observation; it does not cancel execution.
76
78
  A successful detached task-creation request ends its service observation explicitly after the admission record while the coordinator continues to own the task.
77
79
 
78
80
  Catalog discovery evaluates TypeScript in a short-lived process with the selected execution directory as its working directory. Module stdout and stderr are not mixed into CLI output. Session workers retain their loaded instructions, tools, and harness configuration. New sessions, including delegated child sessions, load the current definition source; the library does not serialize or freeze arbitrary TypeScript closures across sessions.
@@ -1,26 +0,0 @@
1
- import { type ErrorInfo } from "../errors.js";
2
- import type { AgentReference, ExecutionReference } from "../runtime/types.js";
3
- export interface CatalogSnapshot {
4
- entries: {
5
- id: string;
6
- name: string;
7
- description: string;
8
- scope: "repo" | "global";
9
- file: string;
10
- }[];
11
- children: {
12
- name: string;
13
- description: string;
14
- }[];
15
- }
16
- export type CatalogReply = {
17
- result: CatalogSnapshot;
18
- error?: never;
19
- } | {
20
- result?: never;
21
- error: ErrorInfo;
22
- };
23
- /** Definition modules run in their selected directory without sharing the CLI's output streams. */
24
- export declare function loadCatalog(cwd: string, parent?: ExecutionReference): Promise<CatalogSnapshot>;
25
- /** Declared-child lookup evaluates only the active parent's definition source. */
26
- export declare function loadDeclaredChildren(cwd: string, parent: AgentReference): Promise<CatalogSnapshot['children']>;
@@ -1,41 +0,0 @@
1
- import { fork } from "node:child_process";
2
- import { fileURLToPath } from "node:url";
3
- import { AgentError } from "../errors.js";
4
- /** Definition modules run in their selected directory without sharing the CLI's output streams. */
5
- export function loadCatalog(cwd, parent) {
6
- return loadCatalogSnapshot(cwd, parent, true);
7
- }
8
- /** Declared-child lookup evaluates only the active parent's definition source. */
9
- export async function loadDeclaredChildren(cwd, parent) {
10
- return (await loadCatalogSnapshot(cwd, parent, false)).children;
11
- }
12
- function loadCatalogSnapshot(cwd, parent, discover) {
13
- return new Promise((resolve, reject) => {
14
- const extension = import.meta.url.endsWith(".ts") ? "ts" : "js";
15
- const child = fork(fileURLToPath(new URL(`./catalog-worker.${extension}`, import.meta.url)), [], {
16
- cwd, env: process.env, stdio: ["ignore", "ignore", "ignore", "ipc"],
17
- execArgv: extension === "ts" ? ["--import", import.meta.resolve("tsx")] : [],
18
- });
19
- let reply;
20
- const failed = () => reject(new AgentError("INVALID_DEFINITION", "The agent catalog worker exited before returning its catalog."));
21
- child.once("error", failed);
22
- child.once("exit", () => {
23
- if (!reply)
24
- failed();
25
- else if (reply.error)
26
- reject(new AgentError(reply.error.code, reply.error.message));
27
- else
28
- resolve(reply.result);
29
- });
30
- child.once("message", (message) => {
31
- reply = message;
32
- child.send({ received: true }, (error) => { if (error)
33
- child.kill(); });
34
- });
35
- child.send({ cwd, parent, discover }, (error) => { if (error) {
36
- child.kill();
37
- failed();
38
- } });
39
- });
40
- }
41
- //# sourceMappingURL=catalog.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"catalog.js","sourceRoot":"","sources":["../../src/cli/catalog.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,oBAAoB,CAAC;AAC1C,OAAO,EAAE,aAAa,EAAE,MAAM,UAAU,CAAC;AACzC,OAAO,EAAE,UAAU,EAAkB,MAAM,cAAc,CAAC;AAS1D,mGAAmG;AACnG,MAAM,UAAU,WAAW,CAAC,GAAW,EAAE,MAA2B;IAClE,OAAO,mBAAmB,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,CAAC,CAAC;AAChD,CAAC;AAED,kFAAkF;AAClF,MAAM,CAAC,KAAK,UAAU,oBAAoB,CAAC,GAAW,EAAE,MAAsB;IAC5E,OAAO,CAAC,MAAM,mBAAmB,CAAC,GAAG,EAAE,MAAM,EAAE,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC;AAClE,CAAC;AAED,SAAS,mBAAmB,CAAC,GAAW,EAAE,MAAsC,EAAE,QAAiB;IACjG,OAAO,IAAI,OAAO,CAAC,CAAC,OAAO,EAAE,MAAM,EAAE,EAAE;QACrC,MAAM,SAAS,GAAG,OAAO,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,IAAI,CAAC;QAChE,MAAM,KAAK,GAAG,IAAI,CAAC,aAAa,CAAC,IAAI,GAAG,CAAC,oBAAoB,SAAS,EAAE,EAAE,OAAO,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,EAAE;YAC/F,GAAG,EAAE,GAAG,EAAE,OAAO,CAAC,GAAG,EAAE,KAAK,EAAE,CAAC,QAAQ,EAAE,QAAQ,EAAE,QAAQ,EAAE,KAAK,CAAC;YACnE,QAAQ,EAAE,SAAS,KAAK,IAAI,CAAC,CAAC,CAAC,CAAC,UAAU,EAAE,OAAO,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE;SAC7E,CAAC,CAAC;QACH,IAAI,KAA+B,CAAC;QACpC,MAAM,MAAM,GAAG,GAAG,EAAE,CAAC,MAAM,CAAC,IAAI,UAAU,CAAC,oBAAoB,EAAE,+DAA+D,CAAC,CAAC,CAAC;QACnI,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;QAC5B,KAAK,CAAC,IAAI,CAAC,MAAM,EAAE,GAAG,EAAE;YACtB,IAAI,CAAC,KAAK;gBAAE,MAAM,EAAE,CAAC;iBAChB,IAAI,KAAK,CAAC,KAAK;gBAAE,MAAM,CAAC,IAAI,UAAU,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC;;gBAC/E,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QAC7B,CAAC,CAAC,CAAC;QACH,KAAK,CAAC,IAAI,CAAC,SAAS,EAAE,CAAC,OAAqB,EAAE,EAAE;YAC9C,KAAK,GAAG,OAAO,CAAC;YAChB,KAAK,CAAC,IAAI,CAAC,EAAE,QAAQ,EAAE,IAAI,EAAE,EAAE,CAAC,KAAK,EAAE,EAAE,GAAG,IAAI,KAAK;gBAAE,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC1E,CAAC,CAAC,CAAC;QACH,KAAK,CAAC,IAAI,CAAC,EAAE,GAAG,EAAE,MAAM,EAAE,QAAQ,EAAE,EAAE,CAAC,KAAK,EAAE,EAAE,GAAG,IAAI,KAAK,EAAE,CAAC;YAAC,KAAK,CAAC,IAAI,EAAE,CAAC;YAAC,MAAM,EAAE,CAAC;QAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC/F,CAAC,CAAC,CAAC;AACL,CAAC","sourcesContent":["import { fork } from \"node:child_process\";\nimport { fileURLToPath } from \"node:url\";\nimport { AgentError, type ErrorInfo } from \"../errors.js\";\nimport type { AgentReference, ExecutionReference } from \"../runtime/types.js\";\n\nexport interface CatalogSnapshot {\n entries: { id: string; name: string; description: string; scope: \"repo\" | \"global\"; file: string }[];\n children: { name: string; description: string }[];\n}\nexport type CatalogReply = { result: CatalogSnapshot; error?: never } | { result?: never; error: ErrorInfo };\n\n/** Definition modules run in their selected directory without sharing the CLI's output streams. */\nexport function loadCatalog(cwd: string, parent?: ExecutionReference): Promise<CatalogSnapshot> {\n return loadCatalogSnapshot(cwd, parent, true);\n}\n\n/** Declared-child lookup evaluates only the active parent's definition source. */\nexport async function loadDeclaredChildren(cwd: string, parent: AgentReference): Promise<CatalogSnapshot['children']> {\n return (await loadCatalogSnapshot(cwd, parent, false)).children;\n}\n\nfunction loadCatalogSnapshot(cwd: string, parent: ExecutionReference | undefined, discover: boolean): Promise<CatalogSnapshot> {\n return new Promise((resolve, reject) => {\n const extension = import.meta.url.endsWith(\".ts\") ? \"ts\" : \"js\";\n const child = fork(fileURLToPath(new URL(`./catalog-worker.${extension}`, import.meta.url)), [], {\n cwd, env: process.env, stdio: [\"ignore\", \"ignore\", \"ignore\", \"ipc\"],\n execArgv: extension === \"ts\" ? [\"--import\", import.meta.resolve(\"tsx\")] : [],\n });\n let reply: CatalogReply | undefined;\n const failed = () => reject(new AgentError(\"INVALID_DEFINITION\", \"The agent catalog worker exited before returning its catalog.\"));\n child.once(\"error\", failed);\n child.once(\"exit\", () => {\n if (!reply) failed();\n else if (reply.error) reject(new AgentError(reply.error.code, reply.error.message));\n else resolve(reply.result);\n });\n child.once(\"message\", (message: CatalogReply) => {\n reply = message;\n child.send({ received: true }, (error) => { if (error) child.kill(); });\n });\n child.send({ cwd, parent, discover }, (error) => { if (error) { child.kill(); failed(); } });\n });\n}\n"]}