@zhushanwen/subagent-core 0.2.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.
- package/README.md +114 -0
- package/dist/chunk-3VOERJPJ.js +22 -0
- package/dist/chunk-A4IVZWVX.js +31 -0
- package/dist/execution/engine/engines/zcode/constants.cjs +54 -0
- package/dist/execution/engine/engines/zcode/constants.d.cts +31 -0
- package/dist/execution/engine/engines/zcode/constants.d.ts +31 -0
- package/dist/execution/engine/engines/zcode/constants.js +22 -0
- package/dist/execution/engine/engines/zcode/reader.cjs +276 -0
- package/dist/execution/engine/engines/zcode/reader.d.cts +20 -0
- package/dist/execution/engine/engines/zcode/reader.d.ts +20 -0
- package/dist/execution/engine/engines/zcode/reader.js +239 -0
- package/dist/execution/engine/paths.cjs +55 -0
- package/dist/execution/engine/paths.d.cts +8 -0
- package/dist/execution/engine/paths.d.ts +8 -0
- package/dist/execution/engine/paths.js +26 -0
- package/dist/execution/relay-env.cjs +62 -0
- package/dist/execution/relay-env.d.cts +33 -0
- package/dist/execution/relay-env.d.ts +33 -0
- package/dist/execution/relay-env.js +20 -0
- package/dist/index.cjs +1852 -0
- package/dist/index.d.cts +1184 -0
- package/dist/index.d.ts +1184 -0
- package/dist/index.js +1810 -0
- package/dist/types-BxyAidGf.d.cts +875 -0
- package/dist/types-BxyAidGf.d.ts +875 -0
- package/package.json +99 -0
- package/src/__tests__/agent-opts-resolver-schema-prompt.test.ts +142 -0
- package/src/__tests__/append-system-prompt-assembly.test.ts +242 -0
- package/src/__tests__/builtin-workflows-structure.test.ts +180 -0
- package/src/__tests__/derive-closed-display-parity.test.ts +93 -0
- package/src/__tests__/fr4-get-state-handshake.test.ts +125 -0
- package/src/__tests__/fr8-orphan-recovery.test.ts +259 -0
- package/src/__tests__/m2-append-content-probe.test.ts +73 -0
- package/src/__tests__/manifest-store.test.ts +368 -0
- package/src/__tests__/record-store-cache.test.ts +335 -0
- package/src/__tests__/record-store-index.test.ts +560 -0
- package/src/__tests__/record-store-last-line.test.ts +129 -0
- package/src/__tests__/review-fix-loop-script.test.ts +288 -0
- package/src/__tests__/review-fix-loop-utils.test.ts +2377 -0
- package/src/__tests__/robustness-low-batch1.test.ts +286 -0
- package/src/__tests__/robustness-medium-batch1.test.ts +69 -0
- package/src/__tests__/robustness-medium-batch2.test.ts +65 -0
- package/src/__tests__/robustness-medium-batch3.test.ts +30 -0
- package/src/__tests__/robustness-medium-batch4.test.ts +358 -0
- package/src/__tests__/session-runner.test.ts +69 -0
- package/src/__tests__/smoke.test.ts +9 -0
- package/src/__tests__/stream-sink.test.ts +203 -0
- package/src/core/__tests__/host-services.test.ts +144 -0
- package/src/core/__tests__/logger.test.ts +78 -0
- package/src/core/__tests__/notify-ports.test.ts +104 -0
- package/src/core/host-services.ts +97 -0
- package/src/core/logger.ts +47 -0
- package/src/core/notify-ports.ts +126 -0
- package/src/execution/__tests__/__fixtures__/notifier-golden-snapshots.json +53 -0
- package/src/execution/__tests__/__fixtures__/truncline.snapshot.json +1 -0
- package/src/execution/__tests__/agent-result-mapper.test.ts +150 -0
- package/src/execution/__tests__/alive-store.test.ts +147 -0
- package/src/execution/__tests__/ask-user-transit-e2e.test.ts +490 -0
- package/src/execution/__tests__/channel-registry-handshake.test.ts +242 -0
- package/src/execution/__tests__/chat-engine-routing.test.ts +610 -0
- package/src/execution/__tests__/chatmode-first-round-closure-spawn.test.ts +190 -0
- package/src/execution/__tests__/concurrency-pool.test.ts +250 -0
- package/src/execution/__tests__/config.test.ts +302 -0
- package/src/execution/__tests__/delivery-methods.test.ts +424 -0
- package/src/execution/__tests__/dialog-queue.test.ts +299 -0
- package/src/execution/__tests__/epipe-fallback.test.ts +241 -0
- package/src/execution/__tests__/execute-and-await-worktree.test.ts +243 -0
- package/src/execution/__tests__/execute-nesting.test.ts +323 -0
- package/src/execution/__tests__/execute-options-mapper.test.ts +200 -0
- package/src/execution/__tests__/execution-record.test.ts +1394 -0
- package/src/execution/__tests__/explicit-agent-ref-guard.test.ts +171 -0
- package/src/execution/__tests__/finalize-record.test.ts +367 -0
- package/src/execution/__tests__/finalized-marker.test.ts +104 -0
- package/src/execution/__tests__/format-schema-instruction.test.ts +169 -0
- package/src/execution/__tests__/gc-timer.test.ts +184 -0
- package/src/execution/__tests__/get-record-for-action-restart.test.ts +254 -0
- package/src/execution/__tests__/helpers/mock-extension-api.ts +30 -0
- package/src/execution/__tests__/helpers/spawn-mock.ts +242 -0
- package/src/execution/__tests__/host-mode.test.ts +87 -0
- package/src/execution/__tests__/lifecycle-manager-lock.test.ts +211 -0
- package/src/execution/__tests__/lifecycle-manager.test.ts +383 -0
- package/src/execution/__tests__/lifecycle-predicates.test.ts +116 -0
- package/src/execution/__tests__/manifest-parentid.test.ts +117 -0
- package/src/execution/__tests__/model-resolver.test.ts +465 -0
- package/src/execution/__tests__/nested-visibility-env-propagation.test.ts +287 -0
- package/src/execution/__tests__/nested-visibility.test.ts +325 -0
- package/src/execution/__tests__/output-collector.test.ts +358 -0
- package/src/execution/__tests__/path-encoding.test.ts +104 -0
- package/src/execution/__tests__/pi-invocation.test.ts +134 -0
- package/src/execution/__tests__/record-store.test.ts +1057 -0
- package/src/execution/__tests__/records-cwd-isolation.test.ts +91 -0
- package/src/execution/__tests__/recursive-visibility-baseline.test.ts +339 -0
- package/src/execution/__tests__/recursive-visibility-env.test.ts +273 -0
- package/src/execution/__tests__/relay-env.test.ts +42 -0
- package/src/execution/__tests__/resource-policy.test.ts +109 -0
- package/src/execution/__tests__/rpc-mode.test.ts +89 -0
- package/src/execution/__tests__/run-and-finalize-chatmode.test.ts +267 -0
- package/src/execution/__tests__/run-spawn-chatmode-settled.test.ts +253 -0
- package/src/execution/__tests__/run-spawn-edges.test.ts +687 -0
- package/src/execution/__tests__/run-spawn-integration.test.ts +933 -0
- package/src/execution/__tests__/run-spawn-resume.test.ts +322 -0
- package/src/execution/__tests__/run-spawn-rpc-mode.test.ts +196 -0
- package/src/execution/__tests__/run-spawn-stdout-callback-throw.test.ts +199 -0
- package/src/execution/__tests__/session-context-resolver.test.ts +167 -0
- package/src/execution/__tests__/session-file-gc.test.ts +293 -0
- package/src/execution/__tests__/session-reconstructor.test.ts +379 -0
- package/src/execution/__tests__/session-runner-epipe.test.ts +178 -0
- package/src/execution/__tests__/session-runner-schema-env.test.ts +350 -0
- package/src/execution/__tests__/spawn-args.test.ts +445 -0
- package/src/execution/__tests__/spawn-event-adapter-rpc.test.ts +189 -0
- package/src/execution/__tests__/spawn-event-adapter.test.ts +167 -0
- package/src/execution/__tests__/spawn-worktree-guidance.test.ts +207 -0
- package/src/execution/__tests__/spawned-children.test.ts +92 -0
- package/src/execution/__tests__/start-sync-model-guard.test.ts +150 -0
- package/src/execution/__tests__/stdin-writer.test.ts +462 -0
- package/src/execution/__tests__/stream-sink-retirement.test.ts +261 -0
- package/src/execution/__tests__/subagent-service-abort.test.ts +60 -0
- package/src/execution/__tests__/subagent-service-message-close.test.ts +629 -0
- package/src/execution/__tests__/subagent-service-parent-guard.test.ts +180 -0
- package/src/execution/__tests__/subagent-service.test.ts +788 -0
- package/src/execution/__tests__/subprocess-agent-runner-routing.test.ts +310 -0
- package/src/execution/__tests__/subprocess-agent-runner.test.ts +612 -0
- package/src/execution/__tests__/temp-prompt.test.ts +53 -0
- package/src/execution/__tests__/timeout-integration.test.ts +615 -0
- package/src/execution/__tests__/tombstone-store.test.ts +73 -0
- package/src/execution/__tests__/turn-limiter-semantics.test.ts +194 -0
- package/src/execution/__tests__/turn-limiter.test.ts +65 -0
- package/src/execution/__tests__/ui-channels.test.ts +187 -0
- package/src/execution/__tests__/ui-interaction-model.test.ts +67 -0
- package/src/execution/__tests__/ui-request-handler-factory.test.ts +369 -0
- package/src/execution/__tests__/ui-request-handler.test.ts +204 -0
- package/src/execution/__tests__/ui-request-observability.test.ts +113 -0
- package/src/execution/__tests__/ui-request-queue.test.ts +133 -0
- package/src/execution/__tests__/worktree-manager.test.ts +633 -0
- package/src/execution/__tests__/worktree-pid-registration.integration.test.ts +229 -0
- package/src/execution/__tests__/worktree-reconcile.integration.test.ts +181 -0
- package/src/execution/__tests__/worktree-registry.test.ts +199 -0
- package/src/execution/agent-registry.ts +199 -0
- package/src/execution/agent-result-mapper.ts +90 -0
- package/src/execution/alive-store.ts +119 -0
- package/src/execution/argv-mirror.ts +113 -0
- package/src/execution/best-effort.ts +38 -0
- package/src/execution/channel-registry-access.ts +144 -0
- package/src/execution/concurrency-pool.ts +116 -0
- package/src/execution/config.ts +165 -0
- package/src/execution/dialog-queue.ts +330 -0
- package/src/execution/engine/__tests__/common/data-dir.test.ts +78 -0
- package/src/execution/engine/__tests__/common/errors.test.ts +132 -0
- package/src/execution/engine/__tests__/common/event-journal.test.ts +177 -0
- package/src/execution/engine/__tests__/common/kill-chain.test.ts +192 -0
- package/src/execution/engine/__tests__/common/nesting-guard.test.ts +81 -0
- package/src/execution/engine/__tests__/common/persona-router.test.ts +123 -0
- package/src/execution/engine/__tests__/common/pool-manager.test.ts +154 -0
- package/src/execution/engine/__tests__/common/schema-emulation.test.ts +128 -0
- package/src/execution/engine/__tests__/conformance/__fixtures__/pi-golden-events.json +28 -0
- package/src/execution/engine/__tests__/conformance/agent-event-invariants.ts +141 -0
- package/src/execution/engine/__tests__/conformance/contract.abort.test.ts +109 -0
- package/src/execution/engine/__tests__/conformance/contract.agent-events.test.ts +101 -0
- package/src/execution/engine/__tests__/conformance/contract.probe.test.ts +77 -0
- package/src/execution/engine/__tests__/conformance/contract.read-degradation.test.ts +104 -0
- package/src/execution/engine/__tests__/conformance/engine-conformance.live.test.ts +201 -0
- package/src/execution/engine/__tests__/conformance/golden-replay.pi.test.ts +76 -0
- package/src/execution/engine/__tests__/conformance/golden-replay.zcode.test.ts +79 -0
- package/src/execution/engine/__tests__/engine-discovery.test.ts +87 -0
- package/src/execution/engine/__tests__/model-prompt.test.ts +197 -0
- package/src/execution/engine/__tests__/paths.test.ts +39 -0
- package/src/execution/engine/__tests__/registry.test.ts +120 -0
- package/src/execution/engine/__tests__/routing.test.ts +231 -0
- package/src/execution/engine/common/data-dir.ts +66 -0
- package/src/execution/engine/common/errors.ts +183 -0
- package/src/execution/engine/common/event-journal.ts +254 -0
- package/src/execution/engine/common/journal-replay.ts +62 -0
- package/src/execution/engine/common/kill-chain.ts +221 -0
- package/src/execution/engine/common/nesting-guard.ts +50 -0
- package/src/execution/engine/common/persona-router.ts +108 -0
- package/src/execution/engine/common/pool-manager.ts +226 -0
- package/src/execution/engine/common/schema-emulation.ts +189 -0
- package/src/execution/engine/common/session-view-projection.ts +51 -0
- package/src/execution/engine/engine-discovery.ts +65 -0
- package/src/execution/engine/engines/pi/__tests__/pi-engine.test.ts +469 -0
- package/src/execution/engine/engines/pi/__tests__/reader.test.ts +155 -0
- package/src/execution/engine/engines/pi/__tests__/task-spec-mapper.test.ts +164 -0
- package/src/execution/engine/engines/pi/pi-engine.ts +415 -0
- package/src/execution/engine/engines/pi/reader.ts +48 -0
- package/src/execution/engine/engines/pi/registration.ts +35 -0
- package/src/execution/engine/engines/pi/task-spec-mapper.ts +100 -0
- package/src/execution/engine/engines/zcode/__tests__/__fixtures__/zcode-golden-spawn.json +39 -0
- package/src/execution/engine/engines/zcode/__tests__/launcher.test.ts +150 -0
- package/src/execution/engine/engines/zcode/__tests__/parser.test.ts +246 -0
- package/src/execution/engine/engines/zcode/__tests__/preparer.test.ts +228 -0
- package/src/execution/engine/engines/zcode/__tests__/reader.test.ts +210 -0
- package/src/execution/engine/engines/zcode/__tests__/registration.test.ts +71 -0
- package/src/execution/engine/engines/zcode/__tests__/zcode-engine.live.test.ts +127 -0
- package/src/execution/engine/engines/zcode/__tests__/zcode-engine.test.ts +580 -0
- package/src/execution/engine/engines/zcode/constants.ts +43 -0
- package/src/execution/engine/engines/zcode/golden-sample.ts +39 -0
- package/src/execution/engine/engines/zcode/launcher.ts +161 -0
- package/src/execution/engine/engines/zcode/parser.ts +436 -0
- package/src/execution/engine/engines/zcode/preparer.ts +363 -0
- package/src/execution/engine/engines/zcode/reader.ts +381 -0
- package/src/execution/engine/engines/zcode/registration.ts +37 -0
- package/src/execution/engine/engines/zcode/zcode-engine.ts +658 -0
- package/src/execution/engine/host-task-spec.ts +47 -0
- package/src/execution/engine/model-prompt.ts +158 -0
- package/src/execution/engine/paths.ts +42 -0
- package/src/execution/engine/port.ts +153 -0
- package/src/execution/engine/registry.ts +133 -0
- package/src/execution/engine/routing.ts +218 -0
- package/src/execution/engine/types.ts +309 -0
- package/src/execution/execute-options-mapper.ts +115 -0
- package/src/execution/execution-record.ts +984 -0
- package/src/execution/finalize-record.ts +254 -0
- package/src/execution/finalized-marker.ts +70 -0
- package/src/execution/get-state-handshake.ts +104 -0
- package/src/execution/host-mode.ts +56 -0
- package/src/execution/idle-gc.ts +47 -0
- package/src/execution/lifecycle-manager.ts +513 -0
- package/src/execution/lifecycle-predicates.ts +65 -0
- package/src/execution/manifest-store.ts +256 -0
- package/src/execution/model-config-service.ts +250 -0
- package/src/execution/model-resolver.ts +248 -0
- package/src/execution/notifier.ts +372 -0
- package/src/execution/notify-ledger.ts +580 -0
- package/src/execution/output-collector.ts +228 -0
- package/src/execution/path-encoding.ts +60 -0
- package/src/execution/pi-invocation.ts +120 -0
- package/src/execution/record-entry.ts +132 -0
- package/src/execution/record-store.ts +1265 -0
- package/src/execution/relay-env.ts +37 -0
- package/src/execution/session-context-resolver.ts +64 -0
- package/src/execution/session-file-gc.ts +120 -0
- package/src/execution/session-pending.ts +170 -0
- package/src/execution/session-reconstructor.ts +678 -0
- package/src/execution/session-runner.ts +1789 -0
- package/src/execution/sessions-index.ts +304 -0
- package/src/execution/spawn-event-adapter.ts +363 -0
- package/src/execution/stdin-writer.ts +198 -0
- package/src/execution/stream-sink.ts +126 -0
- package/src/execution/subagent-service.ts +2268 -0
- package/src/execution/subprocess-agent-runner.ts +317 -0
- package/src/execution/temp-prompt.ts +62 -0
- package/src/execution/tombstone-store.ts +72 -0
- package/src/execution/turn-limiter.ts +102 -0
- package/src/execution/types.ts +1023 -0
- package/src/execution/ui-channels.ts +216 -0
- package/src/execution/ui-interaction-model.ts +48 -0
- package/src/execution/ui-request-handler-factory.ts +243 -0
- package/src/execution/ui-request-observability.ts +81 -0
- package/src/execution/ui-request-queue.ts +184 -0
- package/src/execution/worktree-manager.ts +688 -0
- package/src/execution/worktree-registry.ts +279 -0
- package/src/index.ts +87 -0
- package/src/orchestration/__tests__/__fixtures__/worker-template.snapshot.txt +349 -0
- package/src/orchestration/__tests__/agent-call-catch-fallback.test.ts +202 -0
- package/src/orchestration/__tests__/agent-call-stream.test.ts +152 -0
- package/src/orchestration/__tests__/args-validator.test.ts +143 -0
- package/src/orchestration/__tests__/config-loader.test.ts +503 -0
- package/src/orchestration/__tests__/error-recovery-handlers.test.ts +809 -0
- package/src/orchestration/__tests__/error-recovery-postmessage-defense.test.ts +404 -0
- package/src/orchestration/__tests__/error-recovery-serialize-failed-result.test.ts +56 -0
- package/src/orchestration/__tests__/error-recovery-workflow-call.test.ts +166 -0
- package/src/orchestration/__tests__/execute-agent-call.test.ts +451 -0
- package/src/orchestration/__tests__/launcher-nested-workflow.test.ts +600 -0
- package/src/orchestration/__tests__/lifecycle-runid-injection.test.ts +96 -0
- package/src/orchestration/__tests__/lifecycle.test.ts +659 -0
- package/src/orchestration/__tests__/non-cloneable-return-e2e.test.ts +95 -0
- package/src/orchestration/__tests__/review-fix-loop-scriptpath-failfast.test.ts +183 -0
- package/src/orchestration/__tests__/script-lint.test.ts +831 -0
- package/src/orchestration/__tests__/skill-discovery.test.ts +210 -0
- package/src/orchestration/__tests__/test-mocks.ts +197 -0
- package/src/orchestration/__tests__/worker-exit-without-result.test.ts +368 -0
- package/src/orchestration/__tests__/worker-host.test.ts +120 -0
- package/src/orchestration/__tests__/worker-returnmeta-passthrough.test.ts +164 -0
- package/src/orchestration/__tests__/worker-script-builder-runtime.test.ts +563 -0
- package/src/orchestration/__tests__/worker-script-builder.test.ts +309 -0
- package/src/orchestration/__tests__/worker-script-template-snapshot.test.ts +129 -0
- package/src/orchestration/__tests__/workflow-nesting-e2e.test.ts +317 -0
- package/src/orchestration/__tests__/workflow-script-lint-memo.test.ts +110 -0
- package/src/orchestration/agent-opts-resolver.ts +174 -0
- package/src/orchestration/args-validator.ts +127 -0
- package/src/orchestration/config-loader.ts +316 -0
- package/src/orchestration/error-recovery.ts +1018 -0
- package/src/orchestration/execute-agent-call.ts +256 -0
- package/src/orchestration/launcher.ts +455 -0
- package/src/orchestration/lifecycle.ts +399 -0
- package/src/orchestration/models/__tests__/budget.test.ts +307 -0
- package/src/orchestration/models/agent-call.ts +83 -0
- package/src/orchestration/models/budget.ts +118 -0
- package/src/orchestration/models/ports.ts +164 -0
- package/src/orchestration/models/run-runtime.ts +104 -0
- package/src/orchestration/models/run-spec.ts +83 -0
- package/src/orchestration/models/run-state.ts +44 -0
- package/src/orchestration/models/trace.ts +183 -0
- package/src/orchestration/models/types.ts +301 -0
- package/src/orchestration/models/workflow-run.ts +254 -0
- package/src/orchestration/models/workflow-script-registry.ts +35 -0
- package/src/orchestration/models/workflow-script.ts +117 -0
- package/src/orchestration/script-lint.ts +766 -0
- package/src/orchestration/skill-discovery.ts +135 -0
- package/src/orchestration/worker-handle.ts +115 -0
- package/src/orchestration/worker-host.ts +98 -0
- package/src/orchestration/worker-script-builder.ts +421 -0
- package/src/orchestration/workflow-files.ts +85 -0
- package/src/orchestration/workflow-script-registry-impl.ts +133 -0
- package/src/shared/__tests__/agent-ref.test.ts +34 -0
- package/src/shared/__tests__/meta-parser.test.ts +304 -0
- package/src/shared/__tests__/model-ref.test.ts +306 -0
- package/src/shared/__tests__/resource-discovery-manifest-cache.test.ts +288 -0
- package/src/shared/__tests__/resource-discovery.test.ts +749 -0
- package/src/shared/__tests__/resource-meta.test.ts +51 -0
- package/src/shared/__tests__/schema-jsonify.test.ts +81 -0
- package/src/shared/__tests__/timer-delay.test.ts +61 -0
- package/src/shared/agent-event.ts +13 -0
- package/src/shared/agent-ref.ts +57 -0
- package/src/shared/meta-parser.ts +261 -0
- package/src/shared/model-ref.ts +286 -0
- package/src/shared/resource-discovery.ts +835 -0
- package/src/shared/resource-meta.ts +65 -0
- package/src/shared/schema-env.ts +44 -0
- package/src/shared/schema-jsonify.ts +58 -0
- package/src/shared/timer-delay.ts +54 -0
- package/src/shared/xml-injection.ts +35 -0
- package/workflows/README.md +81 -0
- package/workflows/_shared/agent-refs.cjs +40 -0
- package/workflows/chain.js +137 -0
- package/workflows/map-reduce.js +180 -0
- package/workflows/parallel.js +154 -0
- package/workflows/review-fix-loop-utils.cjs +1542 -0
- package/workflows/review-fix-loop.js +1605 -0
- package/workflows/scatter-gather.js +184 -0
|
@@ -0,0 +1,1023 @@
|
|
|
1
|
+
// src/types.ts
|
|
2
|
+
//
|
|
3
|
+
// 跨层共享的核心类型契约。Core/Runtime/TUI 三层均可 import 本文件。
|
|
4
|
+
//
|
|
5
|
+
// 分层铁律:
|
|
6
|
+
// - Core 不 import Runtime/TUI(零 Pi 依赖,可单测)
|
|
7
|
+
// - Runtime 编排 Core,产出 Details/Record 给 TUI
|
|
8
|
+
// - TUI 只读 Record/Details 快照,永不持有可变引用
|
|
9
|
+
|
|
10
|
+
import type { GuiRenderResult } from "@xyz-agent/extension-protocol";
|
|
11
|
+
|
|
12
|
+
import type { ModelInfo, ModelRegistryLike } from "./model-resolver.ts";
|
|
13
|
+
|
|
14
|
+
// ============================================================
|
|
15
|
+
// 全局常量
|
|
16
|
+
// ============================================================
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* 未显式指定 agent 时的兜底名。
|
|
20
|
+
*
|
|
21
|
+
* 必须是真实存在、可被 agentRegistry 发现的 agent(用户 agentDir 内置的通用 agent)。
|
|
22
|
+
* Service 层(resolveIdentity)与 TUI 层(extractAgentName)共用此常量,保证
|
|
23
|
+
* 「调用时显示的名」与「实际加载的 agent.md」一致。
|
|
24
|
+
*
|
|
25
|
+
* [HISTORICAL] 旧实现两处各硬编码:service 用 "default"(虚构名),format 用
|
|
26
|
+
* "worker"(真实但不是兜底语义,worker agent 已在 2026-08 agent 重构中删除)。
|
|
27
|
+
* 导致不传 agent 时,block 标题显示 worker,但实际执行兜底逻辑不一致。统一为
|
|
28
|
+
* general-purpose 后名实相符。
|
|
29
|
+
*/
|
|
30
|
+
export const DEFAULT_AGENT_NAME = "general-purpose";
|
|
31
|
+
|
|
32
|
+
// ============================================================
|
|
33
|
+
// 执行状态机
|
|
34
|
+
// ============================================================
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* 唯一执行状态。所有路径共用。v4 B-1 两态收敛:旧 idle 折入 running、
|
|
38
|
+
* 旧 cancelled 折入 closed(closedReason='cancelled' 区分)。
|
|
39
|
+
*
|
|
40
|
+
* running = 活跃态。含两种子态(由派生谓词区分,见 lifecycle-predicates.ts):
|
|
41
|
+
* - 对话模式等待续聊(旧 idle):进程可能保活(isIdle=hasIdleTimer)或已回收
|
|
42
|
+
* 待冷路径 resume(isResumable=running && 无活进程句柄)。
|
|
43
|
+
* - 正在执行(有活进程句柄)。
|
|
44
|
+
*
|
|
45
|
+
* closed = 统一终态(done/failed/crashed/cancelled 合并)。具体关闭原因由
|
|
46
|
+
* {@link ClosedReason} 子枚举表达(如 user-close / gc / cancelled / parent-shutdown)。
|
|
47
|
+
* ExecutionRecord.closedReason 携带 L2 原因,投影层按需派生对外语义(error / ended)。
|
|
48
|
+
*/
|
|
49
|
+
export type ExecutionStatus = "running" | "closed";
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* closed 终态的 L2 关闭原因子枚举。
|
|
53
|
+
*
|
|
54
|
+
* 与 ExecutionStatus="closed" 配合使用,表达「为什么关闭」:
|
|
55
|
+
* parent-shutdown — 父进程 session_shutdown 时回收子进程
|
|
56
|
+
* parent-fork — 父进程 fork 新 session 时清理旧子进程
|
|
57
|
+
* parent-new — 父进程创建新 subagent 时清理旧子进程
|
|
58
|
+
* user-close — 用户手动 close action(含对话模式 close)
|
|
59
|
+
* cancelled — 用户取消(close(force:true) / cancelBackground)
|
|
60
|
+
* gc — 通用完成/失败(一次执行自然结束、超时、错误等无专属 reason 的终态)
|
|
61
|
+
* disconnected — .finalized sidecar 存在但无 reason 内容(磁盘重建兜底):
|
|
62
|
+
* 正常结束但死因不可考——旧格式 sidecar(v8.5 前写入的是空文件)、
|
|
63
|
+
* 或外部工具手工创建。替代旧的误导性 "gc" 兜底(自然完成 vs 断联
|
|
64
|
+
* 不分),message/fork-from 据此给出可行动指引。
|
|
65
|
+
*/
|
|
66
|
+
export type ClosedReason = 'parent-shutdown' | 'parent-fork' | 'parent-new' | 'user-close' | 'cancelled' | 'gc' | 'disconnected';
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* [v8.5 D] 可透明重生的终态原因集:message action 对这些 closed 记录同 id 续写原
|
|
70
|
+
* sessionFile(resurrectClosed 回边),不再要求 fork-from 换新 id。
|
|
71
|
+
*
|
|
72
|
+
* 取值以 `.finalized` sidecar 实际写入的 ClosedReason 字面量为准:
|
|
73
|
+
* disconnected — 断联(sidecar 空/损坏兜底 + pi-invocation 中断写入)
|
|
74
|
+
* parent-shutdown — 父进程 session_shutdown 回收
|
|
75
|
+
* 其余 reason 刻意排除:user-close/cancelled 是用户主动告别(close 语义不可旁路);
|
|
76
|
+
* gc 是自然完成(追问走 fork-from 或新 start);parent-fork/parent-new 同理是编排性
|
|
77
|
+
* 清理,历史分支语义已由 fork-from 承接。
|
|
78
|
+
*/
|
|
79
|
+
export const RECONNECTABLE_FINAL_REASONS = ["disconnected", "parent-shutdown"] as const satisfies readonly ClosedReason[];
|
|
80
|
+
|
|
81
|
+
export type ReconnectableFinalReason = (typeof RECONNECTABLE_FINAL_REASONS)[number];
|
|
82
|
+
|
|
83
|
+
/** 窄化守卫:closedReason 是否落在可重生集内。 */
|
|
84
|
+
export function isReconnectableFinalReason(reason: string | undefined): reason is ReconnectableFinalReason {
|
|
85
|
+
return (RECONNECTABLE_FINAL_REASONS as readonly string[]).includes(reason ?? "");
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* [v8.5 D] 透明重生守卫拒绝专用错误:messageHandler 的 endedMessageGuard 必须原样
|
|
90
|
+
* 透传本类错误(自带完整行动语言),不得按 A1 分流规则改写——否则 worktree/异进程
|
|
91
|
+
* 占用文案会被「fork-from 指引」覆盖,误导 agent 走已被判死的通道。
|
|
92
|
+
*/
|
|
93
|
+
export class ResurrectDeniedError extends Error {}
|
|
94
|
+
|
|
95
|
+
/** ClosedReason 全枚举值(运行时守卫用——防御性解析外部输入时校验成员资格)。 */
|
|
96
|
+
export const CLOSED_REASONS: readonly ClosedReason[] = [
|
|
97
|
+
'parent-shutdown',
|
|
98
|
+
'parent-fork',
|
|
99
|
+
'parent-new',
|
|
100
|
+
'user-close',
|
|
101
|
+
'cancelled',
|
|
102
|
+
'gc',
|
|
103
|
+
];
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* 终态三态对外语义(U3 C-outcome 一等披露)。
|
|
107
|
+
*
|
|
108
|
+
* 由 completeRecord 唯一写入点按 deriveOutcome 一次计算(判定顺序:cancelled 优先
|
|
109
|
+
* → error 非空 → completed),消费方(project/list/notify 文案/渲染器)只读本字段,
|
|
110
|
+
* 不再各自手写成败推导 switch(三处同构 switch 已随 U3 收敛删除)。
|
|
111
|
+
*
|
|
112
|
+
* [D6 显式取舍] parent-shutdown/parent-fork/parent-new 合成关闭(subagent-service
|
|
113
|
+
* disposeAllRecords 合成 result 恒写 error:"closed due to ...")落 "failed"——语义为
|
|
114
|
+
* 「父进程关闭时子 agent 未完成即失败」,选定行为而非疏漏,勿当 bug 改回 cancelled。
|
|
115
|
+
*/
|
|
116
|
+
export type ExecutionOutcome = "completed" | "failed" | "cancelled";
|
|
117
|
+
|
|
118
|
+
/**
|
|
119
|
+
* 对外投影的 outcome 联合:含历史 record(outcome 字段诞生前的存量数据)兼容态。
|
|
120
|
+
* 投影层(projectOutcome 唯一出口)对无 outcome 字段的 closed record 按
|
|
121
|
+
* deriveOutcome(closedReason, error) 兜底派生;"closed-legacy" 预留给连派生输入都
|
|
122
|
+
* 不足以判读的存量形态,消费方必须处理该成员(不得因未知值崩溃)。
|
|
123
|
+
*/
|
|
124
|
+
export type ProjectedOutcome = ExecutionOutcome | "closed-legacy";
|
|
125
|
+
|
|
126
|
+
/**
|
|
127
|
+
* 对外四态(设计决策 10 细则 3):内部 ExecutionStatus(v4 B-1 两态)收敛为 agent
|
|
128
|
+
* 可理解的状态语义。真实映射只有两条:
|
|
129
|
+
* running → active / closed → ended(closed 统一终态,含 cancelled)。
|
|
130
|
+
* mapExternalState 不消费 ClosedReason——closed 恒映射 ended。
|
|
131
|
+
*
|
|
132
|
+
* waiting / error 是历史多态映射(idle→waiting / failed+crashed→error)的遗留声明:
|
|
133
|
+
* 对外四态联合契约不变,但当前状态机不产生这两个值。
|
|
134
|
+
*
|
|
135
|
+
* 原始 ExecutionStatus 进 list item 的 status 字段供调试;state 是对外主字段。
|
|
136
|
+
* 映射实现见 subagent-actions.ts mapExternalState——未来内部加态必须扩展该处,
|
|
137
|
+
* 漏加会在 default 分支编译报错,不影响对外契约。
|
|
138
|
+
*/
|
|
139
|
+
export type ExternalState = "active" | "waiting" | "ended" | "error";
|
|
140
|
+
|
|
141
|
+
/** 执行模式。background = 调用方立即拿 handle 返回,子 agent 在 detached promise 里跑。 */
|
|
142
|
+
export type ExecutionMode = "background";
|
|
143
|
+
|
|
144
|
+
// ============================================================
|
|
145
|
+
// Agent 事件流(Core → Record 的唯一更新驱动)
|
|
146
|
+
// ============================================================
|
|
147
|
+
|
|
148
|
+
/**
|
|
149
|
+
* Pi session.subscribe 上报的事件。Runtime 把它喂给 updateFromEvent。
|
|
150
|
+
*
|
|
151
|
+
* 设计:AgentEvent 携带 updateFromEvent 收口进 record 所需的**全部数据**——
|
|
152
|
+
* tool_end 带 result(供 turn.toolCalls 存完整 ToolCall),无需翻译层旁路累积。
|
|
153
|
+
*
|
|
154
|
+
* ACP 词汇对照(D11 注记级校准,零行为变更;新引擎实现者按本表对齐语义,
|
|
155
|
+
* 详见 docs/architecture/subagent-engine-gui-visibility.md §3.3 D11):
|
|
156
|
+
* text_delta / thinking_delta ↔ ACP content blocks(text / thinking)
|
|
157
|
+
* tool_start / tool_end ↔ ACP tool_call / tool_call_update
|
|
158
|
+
* turn_end / message_end ↔ ACP prompt turn 终态(stop_reason + usage)
|
|
159
|
+
* compaction ↔ ACP session/compaction
|
|
160
|
+
* 本协议以 pi 为语义锚点(D3)——命名不迁移,对照表仅保证未来 AcpEngine 适配器
|
|
161
|
+
* 与跨引擎 trace 映射的翻译成本最低。
|
|
162
|
+
*/
|
|
163
|
+
export type AgentEvent =
|
|
164
|
+
| { type: "tool_start"; toolName: string; args?: unknown }
|
|
165
|
+
| { type: "tool_end"; toolName: string; args?: unknown; result?: ToolCallResult; isError?: boolean }
|
|
166
|
+
| { type: "text_delta"; delta: string }
|
|
167
|
+
| { type: "thinking_delta"; delta: string }
|
|
168
|
+
| { type: "turn_end"; summary?: string }
|
|
169
|
+
| { type: "message_end"; usage?: AgentUsage; error?: string }
|
|
170
|
+
| { type: "compaction" }
|
|
171
|
+
| { type: "error"; message: string };
|
|
172
|
+
|
|
173
|
+
/** token 用量(message_end 时由 Core 累加进 record.totalTokens)。 */
|
|
174
|
+
export interface AgentUsage {
|
|
175
|
+
input: number;
|
|
176
|
+
output: number;
|
|
177
|
+
cacheRead: number;
|
|
178
|
+
cacheWrite: number;
|
|
179
|
+
/** 本 message 的成本(USD,来自 SDK usage.cost.total)。可选——无成本数据时缺省。 */
|
|
180
|
+
cost?: number;
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
export interface AgentUsageTotal extends AgentUsage {
|
|
184
|
+
/** 上述四项之和。投影时不再手工求和。 */
|
|
185
|
+
total: number;
|
|
186
|
+
/** 累计成本(USD,来自 SdkEvent.message.usage.cost.total 求和)。无成本数据时为 0。 */
|
|
187
|
+
cost: number;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
/**
|
|
191
|
+
* eventLog 条目(getEventLog 派生产出的元素)。所有字段 readonly。
|
|
192
|
+
*
|
|
193
|
+
* text_output / thinking 类型已移除——它们是 100 字切片的碎片副产物,
|
|
194
|
+
* 现在完整内容收口在 record.turns[] 里,eventLog 只承载离散语义事件
|
|
195
|
+
* (tool 调用 / turn 边界 / error)。
|
|
196
|
+
*/
|
|
197
|
+
export interface AgentEventLogEntry {
|
|
198
|
+
readonly type: "tool_start" | "tool_end" | "turn_end" | "error";
|
|
199
|
+
readonly label: string;
|
|
200
|
+
/** 事件发生的墙钟时间戳(Date.now(),ms)。由 getEventLog 从 turns[] 派生时记录。 */
|
|
201
|
+
readonly ts: number;
|
|
202
|
+
readonly status?: "running" | "done" | "failed";
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
/**
|
|
206
|
+
* [STEP3] displayItem:从 turns[] 派生的展示项(对齐 nicobailon getDisplayItems)。
|
|
207
|
+
*
|
|
208
|
+
* 与 eventLog 的区别:eventLog 承载离散语义事件(tool_start/tool_end/turn_end),
|
|
209
|
+
* displayItem 承载「可渲染单元」(toolCall 含完整 name+args 供 formatToolCall 格式化;
|
|
210
|
+
* text 含 assistant 正文)。renderResult compact 分支改用 displayItems 后,
|
|
211
|
+
* 行格式与 nicobailon 完全一致(→ formatToolCall)。
|
|
212
|
+
*/
|
|
213
|
+
export interface DisplayItem {
|
|
214
|
+
readonly type: "toolCall" | "text";
|
|
215
|
+
/** toolCall:tool 名称(bash/read/edit...);text:无。 */
|
|
216
|
+
readonly name?: string;
|
|
217
|
+
/** toolCall:tool 原始 args(供 formatToolCall 提取路径/命令);text:无。 */
|
|
218
|
+
readonly args?: Record<string, unknown>;
|
|
219
|
+
/** toolCall:执行状态(running 时无✓/✗标记);text:正文文本。 */
|
|
220
|
+
readonly status?: "running" | "done" | "failed";
|
|
221
|
+
/** text:assistant 正文(compact 时取首行/截断)。 */
|
|
222
|
+
readonly text?: string;
|
|
223
|
+
}
|
|
224
|
+
|
|
225
|
+
// ============================================================
|
|
226
|
+
// Agent 结果(一次执行的 outcome)
|
|
227
|
+
// ============================================================
|
|
228
|
+
|
|
229
|
+
/**
|
|
230
|
+
* SDK AgentSessionEvent 的最小可用子集(duck-typed,避免强耦合 SDK 类型)。
|
|
231
|
+
* 由 session-runner 内部消费,驱动累积器和事件翻译。
|
|
232
|
+
*/
|
|
233
|
+
export type SdkEvent = {
|
|
234
|
+
type: string;
|
|
235
|
+
toolCallId?: string;
|
|
236
|
+
toolName?: string;
|
|
237
|
+
args?: unknown;
|
|
238
|
+
result?: ToolCallResult;
|
|
239
|
+
isError?: boolean;
|
|
240
|
+
message?: {
|
|
241
|
+
usage?: AgentUsage & { cost?: { total: number } };
|
|
242
|
+
stopReason?: string;
|
|
243
|
+
errorMessage?: string;
|
|
244
|
+
/** 消息角色(message_start 事件携带,user/assistant/toolResult/custom)。 */
|
|
245
|
+
role?: string;
|
|
246
|
+
};
|
|
247
|
+
assistantMessageEvent?: { type?: string; delta?: string };
|
|
248
|
+
reason?: string;
|
|
249
|
+
};
|
|
250
|
+
|
|
251
|
+
/** tool 调用结果(tool_execution_end 时累积,含 structured-output 的 details)。 */
|
|
252
|
+
export interface ToolCallResult {
|
|
253
|
+
content?: unknown[];
|
|
254
|
+
details?: unknown;
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
/**
|
|
258
|
+
* tool 调用(导出的纯净数据形状,不含内部状态)。
|
|
259
|
+
*
|
|
260
|
+
* tool_start 到达但 tool_end 未到时,调用为进行中;一旦 tool_end 到达,
|
|
261
|
+
* result/isError 填充完成。对外投影(AgentResult.toolCalls / getAllToolCalls)
|
|
262
|
+
* 一律返回此类型——**不泄漏 running/done/failed 内部状态机**。
|
|
263
|
+
*
|
|
264
|
+
* 进行中状态由 execution-record 内部的 `InternalToolCall`(= ToolCall + _status)承载,
|
|
265
|
+
* 只存在于 record.turns[].toolCalls,跨边界导出时由 getAllToolCalls strip _status。
|
|
266
|
+
*/
|
|
267
|
+
export interface ToolCall {
|
|
268
|
+
toolName: string;
|
|
269
|
+
args?: unknown;
|
|
270
|
+
result?: ToolCallResult;
|
|
271
|
+
isError?: boolean;
|
|
272
|
+
}
|
|
273
|
+
|
|
274
|
+
/**
|
|
275
|
+
* 内部 ToolCall:在 ToolCall 基础上追加 _status 进行中状态标记与 startedTs 时间戳。
|
|
276
|
+
*
|
|
277
|
+
* running = tool_start 已收到但 tool_end 未到;
|
|
278
|
+
* done/failed = tool_end 已到。
|
|
279
|
+
*
|
|
280
|
+
* 仅存在于 ExecutionRecord.turns[].toolCalls(Core 内部可变状态)。
|
|
281
|
+
* 跨边界导出(getAllToolCalls → AgentResult.toolCalls / 持久化)由 getAllToolCalls
|
|
282
|
+
* 映射回 ToolCall(丢弃 _status / startedTs),保证导出形状清洁。
|
|
283
|
+
*/
|
|
284
|
+
export interface InternalToolCall extends ToolCall {
|
|
285
|
+
_status: "running" | "done" | "failed";
|
|
286
|
+
/** tool_start 到达时的墙钟时间戳(Date.now(),ms)。getEventLog 派生 tool 条目 ts 用。 */
|
|
287
|
+
startedTs: number;
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
/**
|
|
291
|
+
* 一个 turn 的完整内容(ExecutionRecord.turns[] 的元素)。
|
|
292
|
+
*
|
|
293
|
+
* 收口设计:text/thinking 流式累积**完整内容**(非 100 字切片),
|
|
294
|
+
* toolCalls 存完整 ToolCall(含 result + _status 内部状态)。turn_end 到达后 closed=true,
|
|
295
|
+
* 下次 text/thinking/tool 时开新 turn。
|
|
296
|
+
*
|
|
297
|
+
* eventLog / currentActivity / result 均从 turns[] 派生,不再独立存储。
|
|
298
|
+
*/
|
|
299
|
+
export interface Turn {
|
|
300
|
+
/** 本 turn assistant 正文(text_delta 流式累积,完整)。 */
|
|
301
|
+
text: string;
|
|
302
|
+
/** 本 turn 推理(thinking_delta 流式累积,完整)。 */
|
|
303
|
+
thinking: string;
|
|
304
|
+
/** 本 turn 工具调用(InternalToolCall:含完整 result + _status 进行中标记)。 */
|
|
305
|
+
toolCalls: InternalToolCall[];
|
|
306
|
+
/** 本 turn message_end 的 token 增量(聚合得 totalUsage)。 */
|
|
307
|
+
usageDelta?: AgentUsage;
|
|
308
|
+
/** turn_end 是否已到达。false=正在进行;true=已闭合,下次内容开新 turn。 */
|
|
309
|
+
closed: boolean;
|
|
310
|
+
/** turn_end 到达时的墙钟时间戳(Date.now(),ms)。getEventLog 派生 turn_end 条目 ts 用。 */
|
|
311
|
+
closedTs?: number;
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
/** 一次 session 执行的完整结果。collectResult 产出,写入 Record.outcome。 */
|
|
315
|
+
export interface AgentResult {
|
|
316
|
+
text: string;
|
|
317
|
+
turns: number;
|
|
318
|
+
durationMs: number;
|
|
319
|
+
success: boolean;
|
|
320
|
+
error?: string;
|
|
321
|
+
sessionId: string;
|
|
322
|
+
toolCalls: ToolCall[];
|
|
323
|
+
usage?: AgentUsageTotal;
|
|
324
|
+
/** /resume /fork 可恢复的 session 文件名(不含目录)。 */
|
|
325
|
+
sessionFile?: string;
|
|
326
|
+
/** schema 模式下,structured-output tool 的 result.details(已通过 schema 校验)。 */
|
|
327
|
+
parsedOutput?: unknown;
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
// ============================================================
|
|
331
|
+
// ExecutionRecord —— 唯一状态对象(Core 拥有,Runtime 引用)
|
|
332
|
+
// ============================================================
|
|
333
|
+
|
|
334
|
+
// 本 section 先声明 ExecutionRecord 的组成值对象(WorktreeHandle / AliveMarker /
|
|
335
|
+
// PatchResult 等),ExecutionRecord 本体及其文档注释在 section 末尾。
|
|
336
|
+
|
|
337
|
+
/**
|
|
338
|
+
* worktree handle 值对象。仅 worktree:true 时持有——worktree 是独立维度,
|
|
339
|
+
* 需显式开启,fork alone 不创建 worktree。
|
|
340
|
+
* Object.freeze 守卫保证不可变。
|
|
341
|
+
*/
|
|
342
|
+
export interface WorktreeHandle {
|
|
343
|
+
/** checkout 目录(子 agent 工作目录,tmpdir 下)。 */
|
|
344
|
+
readonly path: string;
|
|
345
|
+
readonly branch: string;
|
|
346
|
+
readonly baseCommit: string;
|
|
347
|
+
/** 主仓库根目录(cleanup/scan 需要,不再靠路径反推)。 */
|
|
348
|
+
readonly mainCwd: string;
|
|
349
|
+
}
|
|
350
|
+
|
|
351
|
+
/** alive marker:子进程存活标记,用于心跳检测和 crash 推断。 */
|
|
352
|
+
export interface AliveMarker {
|
|
353
|
+
readonly pid: number;
|
|
354
|
+
readonly id: string;
|
|
355
|
+
readonly startedAt: number;
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
/** git diff patch 结果。 */
|
|
359
|
+
export interface PatchResult {
|
|
360
|
+
readonly patchFile: string;
|
|
361
|
+
readonly failed: boolean;
|
|
362
|
+
/** patch 是否实际写入 patchFile。true=diff 非空且写盘成功;false=空 diff 或写失败。
|
|
363
|
+
* 调用方据此回填 record.patchFile,避免悬空路径(`git apply` 不存在的文件)。 */
|
|
364
|
+
readonly written: boolean;
|
|
365
|
+
}
|
|
366
|
+
|
|
367
|
+
/** resolveSessionContext 纯函数的入参(#3 SessionContextResolver)。 */
|
|
368
|
+
export interface SessionResolveInput {
|
|
369
|
+
fork?: boolean;
|
|
370
|
+
cwd?: string;
|
|
371
|
+
mainCwd: string;
|
|
372
|
+
mainSessionFile?: string;
|
|
373
|
+
parentForkDepth?: number;
|
|
374
|
+
/** agent 配置目录(getSubagentSessionDir 需要)。 */
|
|
375
|
+
agentDir: string;
|
|
376
|
+
/** worktree checkout 路径(来自 WorktreeHandle.path,作为 effectiveCwd)。 */
|
|
377
|
+
worktreePath?: string;
|
|
378
|
+
}
|
|
379
|
+
|
|
380
|
+
/** resolveSessionContext 纯函数的返回值。 */
|
|
381
|
+
export interface ResolvedSessionContext {
|
|
382
|
+
readonly shouldFork: boolean;
|
|
383
|
+
readonly forkSource: string | undefined;
|
|
384
|
+
readonly effectiveCwd: string;
|
|
385
|
+
readonly sessionDir: string;
|
|
386
|
+
}
|
|
387
|
+
|
|
388
|
+
/** fork depth 超限错误。 */
|
|
389
|
+
export class ForkDepthExceededError extends Error {
|
|
390
|
+
constructor(message: string) {
|
|
391
|
+
super(message);
|
|
392
|
+
this.name = "ForkDepthExceededError";
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
/** worktree 有未提交变更错误。 */
|
|
397
|
+
export class DirtyWorktreeError extends Error {
|
|
398
|
+
constructor(message: string) {
|
|
399
|
+
super(message);
|
|
400
|
+
this.name = "DirtyWorktreeError";
|
|
401
|
+
}
|
|
402
|
+
}
|
|
403
|
+
|
|
404
|
+
/**
|
|
405
|
+
* 所有执行路径的唯一状态源。
|
|
406
|
+
*
|
|
407
|
+
* 收口设计:一次执行的完整内容(text/thinking/toolCalls/usage)按 turn 收口在
|
|
408
|
+
* `turns: Turn[]` 里。eventLog / currentActivity / result 文本均从 turns[] 派生
|
|
409
|
+
* (getEventLog / getCurrentActivity / getFullText),不再独立存储切片或缓冲。
|
|
410
|
+
*
|
|
411
|
+
* 生命周期:createRecord() 创建 → updateFromEvent() 实时更新(累积进 turns)→
|
|
412
|
+
* completeRecord() 冻结 → archive 立即移出内存(读时从 session.jsonl 重建)。
|
|
413
|
+
*
|
|
414
|
+
* TUI 永远拿 RecordSnapshot(.slice() 快照),不直接持此可变对象。
|
|
415
|
+
*/
|
|
416
|
+
export interface ExecutionRecord {
|
|
417
|
+
/** 唯一 ID(sync: "run-N",bg: "bg-N-xxx")。 */
|
|
418
|
+
readonly id: string;
|
|
419
|
+
|
|
420
|
+
// ── 身份(创建时确定,不可变)──
|
|
421
|
+
readonly agent: string;
|
|
422
|
+
readonly model: string;
|
|
423
|
+
readonly thinkingLevel: string | undefined;
|
|
424
|
+
readonly mode: ExecutionMode;
|
|
425
|
+
readonly task: string;
|
|
426
|
+
/**
|
|
427
|
+
* 人类可读的短标签(≤35 字符),简述本次 subagent「在做什么」。
|
|
428
|
+
* 区别于 agent(类型名)/ task(完整 prompt)。旧持久化 record 反序列化时缺失兜底空串。
|
|
429
|
+
*/
|
|
430
|
+
readonly slug: string;
|
|
431
|
+
readonly startedAt: number;
|
|
432
|
+
/** 根 Pi session ID(session 隔离过滤用)。递归链上所有层 record 同值。 */
|
|
433
|
+
readonly rootSessionId: string | undefined;
|
|
434
|
+
/** 直接父 subagent record ID(层级树构建用)。顶层 record 为 undefined。 */
|
|
435
|
+
readonly parentRecordId: string | undefined;
|
|
436
|
+
/** subagent 递归深度。顶层(主 session 直接创建)=0,每层嵌套 +1。 */
|
|
437
|
+
readonly depth: number;
|
|
438
|
+
/**
|
|
439
|
+
* 对话模式标志(可持续对话 subagent)。true = 轮次完成进 idle 态(保留 record +
|
|
440
|
+
* worktree)等待续聊,而非一次性终态化。
|
|
441
|
+
* undefined/false = 一次性模式(默认,行为完全不变)。
|
|
442
|
+
* 向后兼容:旧 record / 旧 session 文件无此字段,按一次性模式处理。
|
|
443
|
+
*/
|
|
444
|
+
readonly chatMode?: boolean;
|
|
445
|
+
/**
|
|
446
|
+
* 执行态信号(residual-fixes 设计):true = 该 record 无活进程驱动(轮终 idle /
|
|
447
|
+
* 重建孤儿兜底),处于「可续聊/等续聊」态——不是后台真在跑。轮终迁移
|
|
448
|
+
* (doFinalizeRoundToIdle)置 true,冷路径续轮(进程启动)清除;GUI 侧
|
|
449
|
+
* streaming/waiting 细分与 hasRunning 判据消费。缺省 falsy = 有进程或旧数据。
|
|
450
|
+
*/
|
|
451
|
+
resumable?: boolean;
|
|
452
|
+
/**
|
|
453
|
+
* 空闲超时毫秒数(仅 chatMode 有意义)。覆盖默认 5min idle timeout。
|
|
454
|
+
* 优先级:参数 > env XYZ_SUBAGENT_IDLE_TIMEOUT_MS > 默认 300000ms。
|
|
455
|
+
* 向后兼容:旧 record 无此字段,按默认值处理。
|
|
456
|
+
*/
|
|
457
|
+
readonly idleTimeoutMs?: number;
|
|
458
|
+
/**
|
|
459
|
+
* 实际执行引擎 id(P4 路由留痕,D9①)。创建时确定不可变;缺省(存量 record)
|
|
460
|
+
* = pi 投影(消费方零迁移)。持久化经 subagent-record entry。
|
|
461
|
+
*/
|
|
462
|
+
readonly engine?: string;
|
|
463
|
+
/**
|
|
464
|
+
* 引擎 fallback 留痕(D9①:probe 失败路由回默认引擎)。GUI 警告条数据源;
|
|
465
|
+
* 缺省 = 无 fallback。持久化经 subagent-record entry。
|
|
466
|
+
*/
|
|
467
|
+
readonly engineFallback?: { from: string; reason: string };
|
|
468
|
+
/**
|
|
469
|
+
* 引擎自描述定位符(U2:非 pi run resolve 后回填、终态迁移落 entry 前——run 前
|
|
470
|
+
* 缺省不可用)。sessionRef 整体透传(失败终态 sessionId 缺失时仍回填已有部分,
|
|
471
|
+
* 读侧①级降②级的防御形态);journalPath 为 retarget 后实际落盘路径。pi 分支不
|
|
472
|
+
* 回填(sessionFile 即定位符)。持久化经 subagent-record entry。
|
|
473
|
+
*/
|
|
474
|
+
engineHandle?: { sessionRef: Record<string, string>; journalPath?: string; poolKey: string };
|
|
475
|
+
|
|
476
|
+
// ── 状态(实时更新)──
|
|
477
|
+
status: ExecutionStatus;
|
|
478
|
+
/** L2 关闭原因子枚举(仅 status="closed" 时有意义)。表达「为什么关闭」。
|
|
479
|
+
* 由 tryTransition(record, "closed", reason) 写入;投影层按需派生对外语义。
|
|
480
|
+
* 向后兼容:旧 record 无此字段,按 gc 处理(通用完成/失败)。 */
|
|
481
|
+
closedReason?: ClosedReason;
|
|
482
|
+
/**
|
|
483
|
+
* 终态三态对外语义(U3 C-outcome)。completeRecord 唯一写入点按 deriveOutcome
|
|
484
|
+
* 一次计算,消费方只读本字段不再自行推导。向后兼容:旧 record / 磁盘重建
|
|
485
|
+
* record 无此字段,投影层按 projectOutcome 兜底(closed-legacy 语义)。
|
|
486
|
+
*/
|
|
487
|
+
outcome?: ExecutionOutcome;
|
|
488
|
+
/** 完整执行内容,按 turn 组织。createRecord 初始化为 [空 turn]。 */
|
|
489
|
+
turns: Turn[];
|
|
490
|
+
/** turn 计数(= turns.filter(closed).length,冗余存储供投影直接读)。 */
|
|
491
|
+
turnCount: number;
|
|
492
|
+
totalTokens: number;
|
|
493
|
+
/** 运行期最近一次 error 事件的消息(getEventLog 派生 error 条目用)。 */
|
|
494
|
+
lastError: string | undefined;
|
|
495
|
+
/**
|
|
496
|
+
* 对话轮次计数(仅 chatMode 有意义)。首轮运行时 = 0;每完成一轮(finalizeRoundToIdle
|
|
497
|
+
* 进 idle)+1。undefined 时视为 0。非 chatMode 不自增。
|
|
498
|
+
*/
|
|
499
|
+
round?: number;
|
|
500
|
+
/**
|
|
501
|
+
* [增量通知] 当前轮次增量的 turns[] 起始下标(仅 chatMode 有意义;内存态记账,D4 不持久化)。
|
|
502
|
+
*
|
|
503
|
+
* - 生命周期:undefined 视为 0(首轮增量 = 全量,与改造前首轮通知逐字节一致,向后兼容旧
|
|
504
|
+
* record);唯一写点 onRoundSettled 第 5 步(notify 之后推进),唯一读点同回调第 2 步
|
|
505
|
+
* (`getFullTextFrom(record, record.roundBaseTurnIndex ?? 0)`)。非 chatMode 恒
|
|
506
|
+
* undefined(onRoundSettled 是 session-runner chatMode 分支专属回调)。
|
|
507
|
+
* - D1 滞后空 turn 防丢文本(防御性):pi 当前事件序下该形态不可达——带 usage 的
|
|
508
|
+
* message_end 恒先于 turn_end(@earendil-works/pi-agent-core dist/agent-loop.js
|
|
509
|
+
* :240/:253/:547 三处 message_end emit 均在 :131 正常路径 turn_end 之前),settle 时
|
|
510
|
+
* turn 全闭合。防 pi 未来事件序变化:若 settle 时刻末 turn 是滞后 message_end 开出的
|
|
511
|
+
* 空 turn(execution-record.ts message_end 分支经 currentTurn,需同时过两层 usage 守卫:
|
|
512
|
+
* session-runner.ts 转发层 `if (msg?.usage)`(bare message_end 不转发)+ execution-record.ts
|
|
513
|
+
* 累积层 `if (event.usage)`(bare message_end 不开 turn)),推进公式
|
|
514
|
+
* nextRoundBaseTurnIndex 把它留在下一轮增量内(新轮首个 text_delta 经 currentTurn 复用该
|
|
515
|
+
* 空 turn,复用累积被 slice 覆盖);直用 turns.length 推进会把下轮首段文本挤出 slice
|
|
516
|
+
* 范围静默丢失。
|
|
517
|
+
* - D4 不持久化:磁盘重建走 createRecord(turns 仅为初始 [emptyTurn()]),base=0 对空 turn
|
|
518
|
+
* 的增量派生等价为空、天然产出仅新轮增量,持久化是死数据。故不写 manifest、不参与重建。
|
|
519
|
+
* - pi 内部序锚定依据(R1 mitigation):@earendil-works/pi-agent-core 0.84.2
|
|
520
|
+
* dist/agent-loop.js :108-111(error/aborted stopReason 也先 emit turn_end 再 agent_end)
|
|
521
|
+
* 与 :131(正常路径 turn_end 收尾);agent_settled 在 agent_end 之后 emit,故未闭合
|
|
522
|
+
* turn 只可能来自滞后事件。pi 升级若改变 turn_end/agent_end 时序,onRoundSettled 推进前
|
|
523
|
+
* 的观测哨(末 turn 未闭合且 text 非空 → logger.warn)会留痕。
|
|
524
|
+
*/
|
|
525
|
+
roundBaseTurnIndex?: number;
|
|
526
|
+
/**
|
|
527
|
+
* record 进入 idle 态的时间戳(ms)。finalizeRoundToIdle 设值;GC 定时器据此计算
|
|
528
|
+
* 剩余 TTL。undefined = 非 idle 态(running/closed/cancelled)或旧 record 缺失字段。
|
|
529
|
+
*/
|
|
530
|
+
idleSince?: number;
|
|
531
|
+
/**
|
|
532
|
+
* close 优雅关闭标志(M2-B3)。chatMode record 运行中调 `close {force:false}` 时置 true;
|
|
533
|
+
* runAndFinalize 的 done 分流检查此标志——true 则终态化为 done(而非进 idle),并清标志。
|
|
534
|
+
* undefined/false = 正常 idle 分流(对话模式轮次完成进 idle 等续聊)。
|
|
535
|
+
* 仅 chatMode + running 时有意义;force:true(立即终止)不走此标志。
|
|
536
|
+
*/
|
|
537
|
+
closeAfterRound?: boolean;
|
|
538
|
+
|
|
539
|
+
// ── 完成 ──
|
|
540
|
+
endedAt: number | undefined;
|
|
541
|
+
result: string | undefined;
|
|
542
|
+
error: string | undefined;
|
|
543
|
+
/** 完整 AgentResult(含 usage/toolCalls,完成时填)。 */
|
|
544
|
+
agentResult: AgentResult | undefined;
|
|
545
|
+
|
|
546
|
+
/** session jsonl 文件名。session 创建成功后由 session-runner.run() 回填(窗口期内 undefined)。 */
|
|
547
|
+
sessionFile?: string;
|
|
548
|
+
|
|
549
|
+
/**
|
|
550
|
+
* [V2 决策 3] 子进程 pid(spawn 后由 session-runner 回填到内存 record)。
|
|
551
|
+
*
|
|
552
|
+
* 用于 lifecycle-manager 孤儿扫描(V2 §5.2 职责 4:父进程重启时按持久化 pid 扫收
|
|
553
|
+
* 上次崩溃遗留的孤儿)。本字段仅在内存记账,持久化留 Step 5(record
|
|
554
|
+
* 文件写入 pid + 启动时 scanOrphanProcesses 消费)。undefined = 尚未 spawn / 已退出。
|
|
555
|
+
* 向后兼容:旧 record 无此字段,按无 pid 处理(孤儿扫描跳过)。
|
|
556
|
+
*/
|
|
557
|
+
pid?: number;
|
|
558
|
+
|
|
559
|
+
/** [MF#3] worktree 模式下子 agent 改动的 patch 文件路径(worktree 外,供调用方应用)。 */
|
|
560
|
+
patchFile?: string;
|
|
561
|
+
|
|
562
|
+
/** worktree 隔离时的 handle(仅 worktree:true 时存在;fork alone 无此字段)。 */
|
|
563
|
+
worktreeHandle?: WorktreeHandle;
|
|
564
|
+
|
|
565
|
+
/**
|
|
566
|
+
* [review round2] 该 record 创建时启用了 worktree 隔离(跨重启磁盘重建时从 session
|
|
567
|
+
* entry 的 worktree 标志恢复)。handle 本体不可序列化——跨重启后 worktreeHandle 恒
|
|
568
|
+
* undefined,续聊(冷路径 resume)须拒绝(防 cwd 静默回落主 repo 破坏隔离)。仅内存
|
|
569
|
+
* record 使用,与持久化无关;execute() 新建 record 不设(有真 handle 时无意义)。
|
|
570
|
+
*/
|
|
571
|
+
hadWorktree?: boolean;
|
|
572
|
+
|
|
573
|
+
// ── 控制(仅 background 持有)──
|
|
574
|
+
controller: AbortController | undefined;
|
|
575
|
+
}
|
|
576
|
+
|
|
577
|
+
// ============================================================
|
|
578
|
+
// Runtime → TUI 的投影契约
|
|
579
|
+
// ============================================================
|
|
580
|
+
|
|
581
|
+
/**
|
|
582
|
+
* Tool 返回的 details(内层扁平结构)。
|
|
583
|
+
* 由 project(record) 唯一产出——sync/bg 两路径字段一致。
|
|
584
|
+
* 含 mode + sessionFile(供外层 SubagentToolResult 分组 + spinner 判断)。
|
|
585
|
+
*
|
|
586
|
+
* 分层(spec FR-3):此为**内层**,不感知 action/外层分组。
|
|
587
|
+
* 外层 SubagentToolResult 由 adapter 包裹产出(加 action/subagentId/sessionFile + 分组)。
|
|
588
|
+
*/
|
|
589
|
+
export interface SubagentToolDetails {
|
|
590
|
+
status: ExecutionStatus;
|
|
591
|
+
/**
|
|
592
|
+
* 终态三态对外语义(U3 C-outcome,projectOutcome 唯一出口)。running → undefined;
|
|
593
|
+
* 历史数据无 outcome 字段时兜底派生(见 ProjectedOutcome)。
|
|
594
|
+
*/
|
|
595
|
+
outcome?: ProjectedOutcome;
|
|
596
|
+
mode: ExecutionMode;
|
|
597
|
+
agent: string;
|
|
598
|
+
model: string;
|
|
599
|
+
thinkingLevel: string | undefined;
|
|
600
|
+
/** 短标签(≤35 字符),来自 record.slug。旧 record 反序列化时为空串。 */
|
|
601
|
+
slug: string;
|
|
602
|
+
turns: number;
|
|
603
|
+
totalTokens: number;
|
|
604
|
+
elapsedSeconds: number;
|
|
605
|
+
eventLog: AgentEventLogEntry[];
|
|
606
|
+
/** [STEP3] 从 turns[] 派生的展示项(对齐 nicobailon getDisplayItems)。 */
|
|
607
|
+
displayItems: DisplayItem[];
|
|
608
|
+
result?: string;
|
|
609
|
+
error?: string;
|
|
610
|
+
/** running 时的当前活动行(tool/thinking/text 优先级)。 */
|
|
611
|
+
currentActivity?: { type: "tool" | "text" | "thinking"; label: string };
|
|
612
|
+
/** schema 模式下,structured-output tool 的 result.details(对齐 workflow agent-pool)。 */
|
|
613
|
+
parsedOutput?: unknown;
|
|
614
|
+
/** session jsonl 文件名(不含目录)。窗口期内可能 undefined(session 尚未创建成功)。 */
|
|
615
|
+
sessionFile?: string;
|
|
616
|
+
/** [MF#3] worktree 模式下子 agent 改动的 patch 文件路径(worktree 外,供调用方应用)。 */
|
|
617
|
+
patchFile?: string;
|
|
618
|
+
}
|
|
619
|
+
|
|
620
|
+
// ============================================================
|
|
621
|
+
// Runtime 公共 API 的入参/出参
|
|
622
|
+
// ============================================================
|
|
623
|
+
|
|
624
|
+
/** Hub.execute 的入参(sync/bg 共用)。mode 由 Hub 内部判定,不暴露给调用方。 */
|
|
625
|
+
export interface ExecuteOptions {
|
|
626
|
+
task: string;
|
|
627
|
+
/**
|
|
628
|
+
* 短标签(≤35 字符),简述本次执行用途,展示在 TUI。必填。
|
|
629
|
+
* workflow 内 agent() 调用时从 AgentCallOpts.description 透传而来。
|
|
630
|
+
*/
|
|
631
|
+
slug: string;
|
|
632
|
+
agent?: string;
|
|
633
|
+
model?: string;
|
|
634
|
+
thinkingLevel?: string;
|
|
635
|
+
skillPath?: string;
|
|
636
|
+
appendSystemPrompt?: string[];
|
|
637
|
+
schema?: Record<string, unknown>;
|
|
638
|
+
/** D-A6 bridge: workflow schemaEnv 经 ExecuteOptions 透传到 runSpawn childEnv。 */
|
|
639
|
+
schemaEnv?: string;
|
|
640
|
+
/**
|
|
641
|
+
* Turn 上限 limiter。显式 0/负 = 显式不限:压过 SPAWN_WATCHDOG_ENV 兑底不挂
|
|
642
|
+
* watchdog(SP-6 参数 > env,U5);undefined 未传才由 env 兑底。
|
|
643
|
+
*/
|
|
644
|
+
maxTurns?: number;
|
|
645
|
+
graceTurns?: number;
|
|
646
|
+
/** sync 模式来自 Pi tool 框架;background 模式 hub 忽略,自建 controller。 */
|
|
647
|
+
signal?: AbortSignal;
|
|
648
|
+
/** 主 agent 当前模型(模型解析第三层兼底)。execute 调用方从 ctx.model 传入。 */
|
|
649
|
+
ctxModel?: ModelInfo;
|
|
650
|
+
/** background 完成回调(sync 不调)。 */
|
|
651
|
+
onComplete?: (record: RecordSnapshot) => void;
|
|
652
|
+
/** 是否继承父会话上下文(fork 模式,只继承上下文)。 */
|
|
653
|
+
fork?: boolean;
|
|
654
|
+
/**
|
|
655
|
+
* [v8.5 B] fork-from 显式指定继承源 session 文件(非主 session)。
|
|
656
|
+
* 与 fork:true 的区别:fork:true 用主 session 作 --fork 源;本字段用任意已有
|
|
657
|
+
* session 文件(断联 subagent 接续场景)作源。优先级高于 fork;传了本字段时
|
|
658
|
+
* fork 取值不影响 spawn 参数。仅 pi 引擎支持(同 fork)。仅 background tool
|
|
659
|
+
* 层 fork-from action 使用;workflow / executeAndAwait 不消费。
|
|
660
|
+
*/
|
|
661
|
+
forkFromSessionFile?: string;
|
|
662
|
+
/** 文件系统隔离:true=创建新 git worktree,WorktreeHandle=复用外部已创建的;undefined=不隔离(parent cwd)。 */
|
|
663
|
+
worktree?: boolean | WorktreeHandle;
|
|
664
|
+
/** 覆盖执行 cwd(默认 mainCwd)。 */
|
|
665
|
+
cwd?: string;
|
|
666
|
+
/**
|
|
667
|
+
* 可持续对话模式(决策 8:独立 chatMode 标志,不扩展 ExecutionMode)。
|
|
668
|
+
* true = record 标记 chatMode,轮次完成进 idle 态(保留 record + worktree,等待 message 续聊);
|
|
669
|
+
* undefined/false = 一次性模式(默认,行为完全不变)。service.execute 透传到 createRecordForMode。
|
|
670
|
+
*/
|
|
671
|
+
conversation?: boolean;
|
|
672
|
+
/**
|
|
673
|
+
* 空闲超时毫秒数(仅 conversation 模式有意义)。覆盖默认 5min idle timeout。
|
|
674
|
+
* 优先级:参数 > env XYZ_SUBAGENT_IDLE_TIMEOUT_MS > 默认 300000ms。
|
|
675
|
+
* 显式传 0/负数 = 禁用 idle GC(不挂 timer;旧实现 0 会落成 setTimeout(0) 立即 kill)。
|
|
676
|
+
*/
|
|
677
|
+
idleTimeoutMs?: number;
|
|
678
|
+
/**
|
|
679
|
+
* 实际执行引擎 id(P4 路由留痕):pi 引擎由 PiEngine.run 在还原 opts 时写入;
|
|
680
|
+
* 缺省(历史调用方不设)= pi 投影。createRecordForMode 读入 record identity。
|
|
681
|
+
*/
|
|
682
|
+
engine?: string;
|
|
683
|
+
/**
|
|
684
|
+
* 引擎 fallback 留痕(D9①:probe 失败路由回默认引擎时由路由层写入)。
|
|
685
|
+
* from = 请求引擎 id,reason 恒 'engine_probe_failed'(GUI 警告条数据源)。
|
|
686
|
+
*/
|
|
687
|
+
engineFallback?: { from: string; reason: string };
|
|
688
|
+
// 注:fork 深度不从外部传入(曾暴露 parentForkDepth,改用 ALS 后 execute 内部从调用链派生,
|
|
689
|
+
// 公开字段成为死字段误导调用方,已移除)。深度限制检查见 session-runner.ts 内部 RunOptions.parentForkDepth
|
|
690
|
+
// (与历史残留的 types.ts RunOptions 同名不同 interface——后者已删除)。
|
|
691
|
+
}
|
|
692
|
+
|
|
693
|
+
/**
|
|
694
|
+
* execute 返回值。
|
|
695
|
+
* background: { mode:"background", subagentId, sessionFile, details } —— 立即返回。
|
|
696
|
+
* subagentId 供后续 cancel/list 用;sessionFile 窗口期可能 undefined。
|
|
697
|
+
*/
|
|
698
|
+
export type ExecutionHandle = {
|
|
699
|
+
mode: "background";
|
|
700
|
+
subagentId: string;
|
|
701
|
+
sessionFile: string | undefined;
|
|
702
|
+
details: SubagentToolDetails;
|
|
703
|
+
};
|
|
704
|
+
|
|
705
|
+
// ============================================================
|
|
706
|
+
// tool action 出参(外层分组,adapter 产出)
|
|
707
|
+
// ============================================================
|
|
708
|
+
|
|
709
|
+
/** list 的 item 结构。 */
|
|
710
|
+
export interface SubagentListItem {
|
|
711
|
+
subagentId: string;
|
|
712
|
+
agent: string;
|
|
713
|
+
/** 短标签(≤35 字符),来自 record.slug。旧 record 反序列化时为空串。 */
|
|
714
|
+
slug: string;
|
|
715
|
+
/** 对外四态(决策 10 细则 3,主字段)。由 mapExternalState(status) 派生。 */
|
|
716
|
+
state: ExternalState;
|
|
717
|
+
/** 原始内部状态(调试用,供 details 展示)。 */
|
|
718
|
+
status: ExecutionStatus;
|
|
719
|
+
mode: ExecutionMode;
|
|
720
|
+
/** 运行秒数(running 态实时计算,终态 endedAt-startedAt)。 */
|
|
721
|
+
duration: number;
|
|
722
|
+
model: string;
|
|
723
|
+
totalTokens: number;
|
|
724
|
+
/** session jsonl 文件名(窗口期内可能 undefined)。 */
|
|
725
|
+
sessionFile?: string;
|
|
726
|
+
/** 直接父 subagent record ID(顶层 record 为 undefined)。[v4 A-6] 从
|
|
727
|
+
* record.parentRecordId 派生,配合 A-5 直接父守卫(message/close 仅作用于直接子)。 */
|
|
728
|
+
parent?: string;
|
|
729
|
+
/** 可冷路径 resume(running 且无活进程句柄)。[v4 A-6] B-1「可续聊」对外表达,
|
|
730
|
+
* agent 据 list 判断哪些 running subagent 实际可续聊(vs 正在忙)。 */
|
|
731
|
+
resumable?: boolean;
|
|
732
|
+
/**
|
|
733
|
+
* 终态三态对外语义(U3 C-outcome 一等披露,projectOutcome 唯一出口):
|
|
734
|
+
* completed / failed / cancelled,历史 record 无 outcome 字段时兜底派生,
|
|
735
|
+
* 不可判读的存量形态为 "closed-legacy"。GUI pane / agent 据此判读成败,
|
|
736
|
+
* 无需翻 error 字段原文(S5)。
|
|
737
|
+
*/
|
|
738
|
+
outcome?: ProjectedOutcome;
|
|
739
|
+
}
|
|
740
|
+
|
|
741
|
+
/** background 启动的内层响应(挂在 SubagentToolResult.bgResponse)。 */
|
|
742
|
+
export interface BgResponse {
|
|
743
|
+
status: "running";
|
|
744
|
+
mode: "background";
|
|
745
|
+
/** 启动提示文案("detached, will notify on completion")。 */
|
|
746
|
+
message: string;
|
|
747
|
+
/**
|
|
748
|
+
* 终态三态语义(U3 C-outcome 对外 JSON 契约完备位)。start 时点 record 尚未终态,
|
|
749
|
+
* 恒 undefined(JSON.stringify 落键省略);终态成败语义经 list items[].outcome
|
|
750
|
+
* 披露。旧字段 status/mode/message 原样保留(向后兼容)。
|
|
751
|
+
*/
|
|
752
|
+
outcome?: ProjectedOutcome;
|
|
753
|
+
/**
|
|
754
|
+
* 通知投递契约回显位(U1 预置,U2 通知账本的契约声明)。恒值
|
|
755
|
+
* "ledger+at-least-once":主 agent 在当前 run 结束或有限延迟内收到完成通知,
|
|
756
|
+
* 送达保证为 at-least-once + notifyId 幂等可识别。字段与填充由 U1 负责,
|
|
757
|
+
* 值语义由 U2(execution/notify-ledger.ts)兑现。
|
|
758
|
+
*/
|
|
759
|
+
notifyContract: "ledger+at-least-once";
|
|
760
|
+
}
|
|
761
|
+
|
|
762
|
+
/** list 的内层响应(挂在 SubagentToolResult.listResponse)。 */
|
|
763
|
+
export interface ListResponse {
|
|
764
|
+
/** items 中 status==="running" 的计数(受 limit 截断如实反映,非全局总数)。 */
|
|
765
|
+
running: number;
|
|
766
|
+
items: SubagentListItem[];
|
|
767
|
+
}
|
|
768
|
+
|
|
769
|
+
/** cancel 的内层响应(挂在 SubagentToolResult.cancelResponse)。 */
|
|
770
|
+
export interface CancelResponse {
|
|
771
|
+
cancelled: true;
|
|
772
|
+
}
|
|
773
|
+
|
|
774
|
+
/**
|
|
775
|
+
* message 的内层响应(挂在 SubagentToolResult.messageResponse,决策 10 瘦身)。
|
|
776
|
+
*
|
|
777
|
+
* [R1 删除记录] 旧 PendingMessage(在途消息缓存条目,消费确认制,设计决策 6 状态×
|
|
778
|
+
* interrupt 映射)已随 deliverToRunning 一并删除——SP-5 upgrade 后无生产调用方,
|
|
779
|
+
* 配套三段消费链(push / message_start shift / redeliverPending 补投)全部不可达。
|
|
780
|
+
* 详见 subagent-service.ts 的删除记录注释。
|
|
781
|
+
*/
|
|
782
|
+
export interface MessageResponse {
|
|
783
|
+
delivered: true;
|
|
784
|
+
}
|
|
785
|
+
|
|
786
|
+
/** close 的内层响应(挂在 SubagentToolResult.closeResponse,决策 10 瘦身)。 */
|
|
787
|
+
export interface CloseResponse {
|
|
788
|
+
closed: true;
|
|
789
|
+
}
|
|
790
|
+
|
|
791
|
+
/**
|
|
792
|
+
* Tool 外层出参(renderResult + LLM content JSON 同源)。
|
|
793
|
+
* adapter 唯一产出:领域对象(bg/list/cancel/message/close 五选一)+ action/subagentId/sessionFile。
|
|
794
|
+
*
|
|
795
|
+
* - background 启动 → bgResponse(subagentId 有值;sessionFile 窗口期可能 undefined)
|
|
796
|
+
* - list → listResponse(最外层 subagentId/sessionFile 为 null,sessionFile 在各 item 内)
|
|
797
|
+
* - cancel → cancelResponse(subagentId 有值;sessionFile 无意义,可为 null)
|
|
798
|
+
* - message → messageResponse(subagentId 有值;sessionFile 无意义,可为 null)
|
|
799
|
+
* - close → closeResponse(subagentId 有值;sessionFile 无意义,可为 null)
|
|
800
|
+
*/
|
|
801
|
+
export type SubagentToolResult =
|
|
802
|
+
| { action: "start"; subagentId: string; sessionFile: string | null; slug: string; /** registry 全等回显(U1):放行即与 registry 条目全等,"provider/id" 形态。 */ model: string; bgResponse: BgResponse; __gui__?: GuiRenderResult }
|
|
803
|
+
| { action: "list"; subagentId: null; sessionFile: null; listResponse: ListResponse; __gui__?: GuiRenderResult }
|
|
804
|
+
| { action: "cancel"; subagentId: string; sessionFile: null; cancelResponse: CancelResponse; __gui__?: GuiRenderResult }
|
|
805
|
+
| { action: "message"; subagentId: string; sessionFile: null; messageResponse: MessageResponse; __gui__?: GuiRenderResult }
|
|
806
|
+
| { action: "close"; subagentId: string; sessionFile: null; closeResponse: CloseResponse; __gui__?: GuiRenderResult }
|
|
807
|
+
| { action: "fork-from"; subagentId: string; sessionFile: string | null; forkFromResponse: ForkFromResponse; __gui__?: GuiRenderResult };
|
|
808
|
+
|
|
809
|
+
/** fork-from 的内层响应:新 subagent id + 作为继承源的旧记录 session 文件。
|
|
810
|
+
* [v8.5 B] 断联恢复通道——新 subagent 以 --fork 方式继承旧会话历史,源文件只读
|
|
811
|
+
* 不续写(pi fork 建 branched session,copy-on-write)。 */
|
|
812
|
+
export interface ForkFromResponse {
|
|
813
|
+
/** 新 subagent record id(接续对话用 action:'message')。 */
|
|
814
|
+
newSubagentId: string;
|
|
815
|
+
/** 作为继承源的旧 subagent session jsonl 绝对路径。 */
|
|
816
|
+
sourceSessionFile: string;
|
|
817
|
+
}
|
|
818
|
+
|
|
819
|
+
// ============================================================
|
|
820
|
+
// TUI list 视图的合并 record(4 源 merge 后的形状)
|
|
821
|
+
// ============================================================
|
|
822
|
+
|
|
823
|
+
/** /subagents list 左列展示单元。来自内存(running) 或 session.jsonl 重建(终态)。 */
|
|
824
|
+
export interface SubagentRecord {
|
|
825
|
+
id: string;
|
|
826
|
+
agent: string;
|
|
827
|
+
/** 任务提示词(详情面板置顶展示)。磁盘/内存源均有。 */
|
|
828
|
+
task: string;
|
|
829
|
+
/** 短标签(≤35 字符)。磁盘重建源旧文件可能缺失→兜底空串。 */
|
|
830
|
+
slug: string;
|
|
831
|
+
status: ExecutionStatus;
|
|
832
|
+
/** L2 关闭原因子枚举(仅 status="closed" 时有意义)。SP-1 新增。 */
|
|
833
|
+
closedReason?: ClosedReason;
|
|
834
|
+
mode: ExecutionMode;
|
|
835
|
+
startedAt: number;
|
|
836
|
+
/** 根 Pi session ID(session 隔离过滤用)。递归链上所有层 record 同值。 */
|
|
837
|
+
rootSessionId: string | undefined;
|
|
838
|
+
/** 直接父 subagent record ID(层级树构建用)。顶层 record 为 undefined。 */
|
|
839
|
+
parentRecordId: string | undefined;
|
|
840
|
+
/** subagent 递归深度。顶层 =0,每层嵌套 +1。 */
|
|
841
|
+
depth: number;
|
|
842
|
+
endedAt: number | undefined;
|
|
843
|
+
turns: number;
|
|
844
|
+
totalTokens: number;
|
|
845
|
+
model: string;
|
|
846
|
+
thinkingLevel: string | undefined;
|
|
847
|
+
eventLog: AgentEventLogEntry[];
|
|
848
|
+
/** [STEP3] 从 turns[] 派生的展示项(对齐 nicobailon getDisplayItems)。 */
|
|
849
|
+
displayItems: DisplayItem[];
|
|
850
|
+
/** running 时的当前活动行(仅内存源;磁盘重建无此数据)。streaming 可观测性用。 */
|
|
851
|
+
currentActivity?: { type: "tool" | "text" | "thinking"; label: string };
|
|
852
|
+
result?: string;
|
|
853
|
+
error?: string;
|
|
854
|
+
sessionFile?: string;
|
|
855
|
+
/** [MF#3] worktree 模式下子 agent 改动的 patch 文件路径(worktree 外,供调用方应用)。 */
|
|
856
|
+
patchFile?: string;
|
|
857
|
+
/**
|
|
858
|
+
* [review round2] 创建时启用 worktree 隔离(磁盘重建源从 session entry 恢复;内存源由
|
|
859
|
+
* recordToSubagent 从 worktreeHandle 投影)。getRecordForAction 跨重启重建时据此拒绝续聊。
|
|
860
|
+
*/
|
|
861
|
+
worktree?: boolean;
|
|
862
|
+
/**
|
|
863
|
+
* 对话轮次计数(仅 chatMode idle record 有意义)。round 仅在内存维护(doFinalizeRoundToIdle
|
|
864
|
+
* 递增),跨重启不恢复(round 无磁盘持久化);非对话模式 / 非 idle record 为 undefined。内存源由 recordToSubagent 从
|
|
865
|
+
* ExecutionRecord.round 投影。
|
|
866
|
+
*/
|
|
867
|
+
round?: number;
|
|
868
|
+
/**
|
|
869
|
+
* 对话模式标志(与 ExecutionRecord.chatMode 同义;投影给 GUI 侧 streaming/waiting/done
|
|
870
|
+
* 细分判据——one-shot 轮终(chatMode 非 true + result 有值)显示完成态,chat 轮终显示
|
|
871
|
+
* 等续聊。内存源由 recordToSubagent 投影,磁盘源经 subagent-record entry 重建)。
|
|
872
|
+
*/
|
|
873
|
+
chatMode?: boolean;
|
|
874
|
+
/**
|
|
875
|
+
* 执行态信号(与 ExecutionRecord.resumable 同义):true = 无活进程驱动的 running
|
|
876
|
+
* (轮终 idle / 重建孤儿兜底),GUI 侧据此排除「真在跑」判定。
|
|
877
|
+
*/
|
|
878
|
+
resumable?: boolean;
|
|
879
|
+
/** 外部 Pi 实例(进程隔离模式下由外部启动的子进程)。 */
|
|
880
|
+
externalInstance?: AliveMarker;
|
|
881
|
+
/** fork 模式下的 worktree handle。 */
|
|
882
|
+
worktreeHandle?: WorktreeHandle;
|
|
883
|
+
/**
|
|
884
|
+
* 实际执行引擎 id(P4 路由留痕)。缺省 = pi 投影(存量 record 零迁移);
|
|
885
|
+
* GUI 警告条/引擎标记的数据源之一。
|
|
886
|
+
*/
|
|
887
|
+
engine?: string;
|
|
888
|
+
/** 引擎 fallback 留痕(D9①:probe 失败路由回默认引擎)。GUI 警告条数据源。 */
|
|
889
|
+
engineFallback?: { from: string; reason: string };
|
|
890
|
+
/**
|
|
891
|
+
* 引擎自描述定位符(U1:EngineHandleData 的持久化消费面子集,引擎无关——
|
|
892
|
+
* sessionRef 整体透传不枚举内部键)。read 降级链①②级的数据源(runtime
|
|
893
|
+
* subagent-engine-history);缺省 = pi(走 JSONL 直读链)。
|
|
894
|
+
*/
|
|
895
|
+
engineHandle?: { sessionRef: Record<string, string>; journalPath?: string; poolKey: string };
|
|
896
|
+
}
|
|
897
|
+
|
|
898
|
+
// ============================================================
|
|
899
|
+
// 配置(global + session)
|
|
900
|
+
// ============================================================
|
|
901
|
+
|
|
902
|
+
/**
|
|
903
|
+
* 全局配置(~/.pi/agent/subagents/config.json)。
|
|
904
|
+
*
|
|
905
|
+
* 模型解析已退化为「主 agent model 优先,仅 override 时查 registry」——
|
|
906
|
+
* 不再有 category/fallback/yolo 字段。config.json 只保留 maxConcurrent
|
|
907
|
+
* (pool 大小)。旧 config.json 中的 categories/fallback 等字段读取时忽略。
|
|
908
|
+
*/
|
|
909
|
+
export interface SubagentsGlobalConfig {
|
|
910
|
+
version: number;
|
|
911
|
+
maxConcurrent: number;
|
|
912
|
+
/**
|
|
913
|
+
* 全局默认执行引擎(D9 三层优先级的最底层:调用参数 > agent frontmatter > 本值)。
|
|
914
|
+
* 缺省 'pi'(P4 路由层 DEFAULT_ENGINE_ID)。加载期只做类型校验,注册表校验归路由层。
|
|
915
|
+
*/
|
|
916
|
+
defaultEngine?: string;
|
|
917
|
+
/** 引擎路由策略(D9①):strict=true 时一切 probe 失败直接报错(不 fallback)。 */
|
|
918
|
+
engineRouting?: { strict: boolean };
|
|
919
|
+
}
|
|
920
|
+
|
|
921
|
+
// ============================================================
|
|
922
|
+
// 只读快照(TUI 消费,永不 mutate)
|
|
923
|
+
// ============================================================
|
|
924
|
+
|
|
925
|
+
/**
|
|
926
|
+
* Record 的只读视图。store.snapshot() 返回。
|
|
927
|
+
* TUI 拿到此类型,保证不会回写 Core 状态。
|
|
928
|
+
*
|
|
929
|
+
* 不含 eventLog——snapshot 的消费点(cancel 判 mode/status、hasRunning 判 mode、
|
|
930
|
+
* toNotifyRecord 取 result/error)均不读 eventLog。需要 eventLog 的场景用 project()
|
|
931
|
+
* 投影的 SubagentToolDetails。需要完整内容用 record.turns[](Core 内部)。
|
|
932
|
+
*/
|
|
933
|
+
export interface RecordSnapshot {
|
|
934
|
+
readonly id: string;
|
|
935
|
+
readonly agent: string;
|
|
936
|
+
readonly model: string;
|
|
937
|
+
readonly thinkingLevel: string | undefined;
|
|
938
|
+
readonly mode: ExecutionMode;
|
|
939
|
+
readonly task: string;
|
|
940
|
+
/** 短标签(≤35 字符)。来自 record.slug。 */
|
|
941
|
+
readonly slug: string;
|
|
942
|
+
readonly status: ExecutionStatus;
|
|
943
|
+
/** 对话模式标志(与 ExecutionRecord.chatMode 同源)。cancel 别名判定用。 */
|
|
944
|
+
readonly chatMode?: boolean;
|
|
945
|
+
readonly turns: number;
|
|
946
|
+
readonly totalTokens: number;
|
|
947
|
+
readonly startedAt: number;
|
|
948
|
+
readonly endedAt: number | undefined;
|
|
949
|
+
readonly result: string | undefined;
|
|
950
|
+
readonly error: string | undefined;
|
|
951
|
+
readonly sessionFile: string | undefined;
|
|
952
|
+
}
|
|
953
|
+
|
|
954
|
+
// Re-export 用于 ExecuteOptions 的 agent/model 契约
|
|
955
|
+
// ============================================================
|
|
956
|
+
// SDK duck-typed 接口(测试可 mock,session-runner 消费)
|
|
957
|
+
// ============================================================
|
|
958
|
+
|
|
959
|
+
/** AgentSession 的最小可用接口(duck-typed,与 SDK AgentSession 结构兼容)。 */
|
|
960
|
+
export interface AgentSessionLike {
|
|
961
|
+
prompt(task: string, options?: unknown): Promise<void>;
|
|
962
|
+
steer(message: string): Promise<void>;
|
|
963
|
+
abort(): Promise<void>;
|
|
964
|
+
dispose(): void;
|
|
965
|
+
subscribe(fn: (event: unknown) => void): () => void;
|
|
966
|
+
sessionId: string;
|
|
967
|
+
readonly sessionManager: {
|
|
968
|
+
getSessionFile(): string | undefined;
|
|
969
|
+
getSessionId(): string;
|
|
970
|
+
/** 写 custom entry(subagent-identity 持久化用)。SDK SessionManager.appendCustomEntry 的 duck-type。 */
|
|
971
|
+
appendCustomEntry(customType: string, data?: unknown): string;
|
|
972
|
+
};
|
|
973
|
+
messages: ReadonlyArray<{
|
|
974
|
+
role: string;
|
|
975
|
+
content?: ReadonlyArray<{ type: string; text?: string }>;
|
|
976
|
+
}>;
|
|
977
|
+
getAllTools(): Array<{ name: string }>;
|
|
978
|
+
setActiveToolsByName(names: string[]): void;
|
|
979
|
+
}
|
|
980
|
+
|
|
981
|
+
/** DefaultResourceLoader 的最小可用接口(duck-typed)。 */
|
|
982
|
+
export interface ResourceLoaderLike {
|
|
983
|
+
reload(): Promise<void>;
|
|
984
|
+
}
|
|
985
|
+
|
|
986
|
+
/** createAgentSession 入参的类型化子集(对应 SDK CreateAgentSessionOptions)。 */
|
|
987
|
+
export interface CreateAgentSessionArgs {
|
|
988
|
+
model: unknown;
|
|
989
|
+
thinkingLevel?: string;
|
|
990
|
+
cwd: string;
|
|
991
|
+
resourceLoader: ResourceLoaderLike;
|
|
992
|
+
modelRegistry: ModelRegistryLike;
|
|
993
|
+
sessionManager: unknown;
|
|
994
|
+
}
|
|
995
|
+
|
|
996
|
+
/** DefaultResourceLoader 构造参数的类型化子集。 */
|
|
997
|
+
export interface ResourceLoaderOptions {
|
|
998
|
+
cwd: string;
|
|
999
|
+
agentDir: string;
|
|
1000
|
+
appendSystemPrompt: string[];
|
|
1001
|
+
additionalSkillPaths?: string[];
|
|
1002
|
+
}
|
|
1003
|
+
|
|
1004
|
+
/** SessionManager 实例的最小接口(duck-typed,fork 路径消费 SDK 静态方法的返回值)。 */
|
|
1005
|
+
export interface SessionManagerLike {
|
|
1006
|
+
getLeafId(): string | null;
|
|
1007
|
+
createBranchedSession(leafId: string): string | undefined;
|
|
1008
|
+
getSessionFile(): string | undefined;
|
|
1009
|
+
getSessionId(): string;
|
|
1010
|
+
}
|
|
1011
|
+
|
|
1012
|
+
/** Pi SDK 动态 import 的形状(getSdk() 获取)。 */
|
|
1013
|
+
export interface SdkLike {
|
|
1014
|
+
DefaultResourceLoader: new (opts: ResourceLoaderOptions) => ResourceLoaderLike;
|
|
1015
|
+
SessionManager: {
|
|
1016
|
+
inMemory(cwd?: string): SessionManagerLike;
|
|
1017
|
+
create(cwd: string, sessionDir?: string): SessionManagerLike;
|
|
1018
|
+
open(sessionFile: string, sessionDir?: string, cwdOverride?: string): SessionManagerLike;
|
|
1019
|
+
/** [MF#1] fork 静态方法:从源 session 文件 fork 到目标 cwd,返回 SessionManager。 */
|
|
1020
|
+
forkFrom(sourcePath: string, targetCwd: string, sessionDir?: string): SessionManagerLike;
|
|
1021
|
+
};
|
|
1022
|
+
createAgentSession: (opts: CreateAgentSessionArgs) => Promise<{ session: AgentSessionLike }>;
|
|
1023
|
+
}
|