qlogicagent 2.20.2 → 2.20.4

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 (197) hide show
  1. package/dist/agent-contract.js +1 -1
  2. package/dist/agent.js +39 -35
  3. package/dist/cli.js +1 -1
  4. package/dist/host-contract.js +1 -1
  5. package/dist/host-session-collection-contract.js +1 -1
  6. package/dist/index.js +624 -549
  7. package/dist/memory-category-contract.js +1 -0
  8. package/dist/orchestration.js +1 -1
  9. package/dist/project-memory-host.js +21 -21
  10. package/dist/protocol.js +1 -1
  11. package/dist/skill-category-contract.js +1 -0
  12. package/dist/skills/builtin/web-research/SKILL.md +37 -0
  13. package/dist/skills/mcp/astraclaw-native-mcp-server.js +1 -1
  14. package/dist/tunables.js +1 -1
  15. package/dist/types/agent/memory-recall-context.d.ts +6 -9
  16. package/dist/types/agent/memory-recall-injection.d.ts +1 -6
  17. package/dist/types/agent/tool-loop/agent-argument-normalizer.d.ts +12 -0
  18. package/dist/types/agent/tool-loop/artifact-final-contract.d.ts +8 -0
  19. package/dist/types/agent/tool-loop.d.ts +5 -0
  20. package/dist/types/agent/types.d.ts +5 -0
  21. package/dist/types/cli/acp-extended-handlers.d.ts +11 -9
  22. package/dist/types/cli/acp-session-handlers.d.ts +1 -1
  23. package/dist/types/cli/acp-session-host.d.ts +8 -0
  24. package/dist/types/cli/agent-runtime-bootstrap.d.ts +7 -1
  25. package/dist/types/cli/agent-runtime-session-state.d.ts +23 -6
  26. package/dist/types/cli/atomic-text-file.d.ts +31 -0
  27. package/dist/types/cli/background-context-capsule.d.ts +12 -0
  28. package/dist/types/cli/base-tool-bootstrap.d.ts +1 -0
  29. package/dist/types/cli/cli-acp-request-handler.d.ts +3 -1
  30. package/dist/types/cli/community-workflow-installer.d.ts +1 -1
  31. package/dist/types/cli/core-tool-coordinator.d.ts +1 -0
  32. package/dist/types/cli/core-tools/agent-tool-service.d.ts +17 -1
  33. package/dist/types/cli/dev-tool-bootstrap.d.ts +3 -2
  34. package/dist/types/cli/dev-tools/dev-tool-bootstrap-service.d.ts +1 -0
  35. package/dist/types/cli/dev-tools/dev-tool-registry.d.ts +3 -1
  36. package/dist/types/cli/dev-tools/incremental-repo-map.d.ts +81 -0
  37. package/dist/types/cli/dev-tools/lsp-supervisor.d.ts +59 -0
  38. package/dist/types/cli/dev-tools/lsp-tool-service.d.ts +2 -0
  39. package/dist/types/cli/handlers/community-handler.d.ts +2 -0
  40. package/dist/types/cli/handlers/dream-handler.d.ts +1 -1
  41. package/dist/types/cli/handlers/memory-handler.d.ts +2 -14
  42. package/dist/types/cli/handlers/product-handler.d.ts +6 -24
  43. package/dist/types/cli/handlers/turn-handler.d.ts +1 -0
  44. package/dist/types/cli/idle-dream-coordinator.d.ts +9 -5
  45. package/dist/types/cli/memory-background-coordinator.d.ts +26 -0
  46. package/dist/types/cli/memory-candidate-service.d.ts +2 -3
  47. package/dist/types/cli/memory-coordinator.d.ts +12 -8
  48. package/dist/types/cli/permission-bootstrap.d.ts +10 -1
  49. package/dist/types/cli/product-acp-params.d.ts +29 -0
  50. package/dist/types/cli/resolved-agent-cache.d.ts +18 -7
  51. package/dist/types/cli/rpc-registry.d.ts +2 -1
  52. package/dist/types/cli/runtime-hook-bootstrap.d.ts +2 -0
  53. package/dist/types/cli/stdio-acp-request-host.d.ts +7 -4
  54. package/dist/types/cli/stdio-agent-session-bootstrap.d.ts +8 -2
  55. package/dist/types/cli/stdio-rpc-handler-hosts.d.ts +4 -2
  56. package/dist/types/cli/stdio-runtime-bootstrap.d.ts +1 -0
  57. package/dist/types/cli/stdio-server.d.ts +53 -16
  58. package/dist/types/cli/stdio-session-runtime-coordinator.d.ts +0 -2
  59. package/dist/types/cli/task-distillation-coordinator.d.ts +42 -14
  60. package/dist/types/cli/tool-bootstrap-core-registration.d.ts +14 -4
  61. package/dist/types/cli/tool-bootstrap.d.ts +2 -1
  62. package/dist/types/cli/turn-core.d.ts +4 -0
  63. package/dist/types/cli/turn-lifecycle.d.ts +1 -0
  64. package/dist/types/contracts/hooks.d.ts +3 -2
  65. package/dist/types/contracts/turn-event.d.ts +7 -0
  66. package/dist/types/host-contract/index.d.ts +144 -14
  67. package/dist/types/host-contract/memory-category.d.ts +8 -0
  68. package/dist/types/host-contract/skill-category.d.ts +5 -0
  69. package/dist/types/host-session-collection-contract.d.ts +1 -0
  70. package/dist/types/orchestration/agent-instance.d.ts +15 -0
  71. package/dist/types/orchestration/dag-scheduler.d.ts +18 -0
  72. package/dist/types/orchestration/delegate-approval-policy.d.ts +8 -0
  73. package/dist/types/orchestration/goal-acceptance.d.ts +2 -5
  74. package/dist/types/orchestration/goal-loop-coordinator.d.ts +4 -2
  75. package/dist/types/orchestration/goal-mode-adapters.d.ts +16 -0
  76. package/dist/types/orchestration/goal-run-types.d.ts +6 -1
  77. package/dist/types/orchestration/product-budget.d.ts +35 -16
  78. package/dist/types/orchestration/product-persistence.d.ts +5 -14
  79. package/dist/types/orchestration/product-planner.d.ts +38 -0
  80. package/dist/types/orchestration/product-worktree.d.ts +4 -2
  81. package/dist/types/orchestration/solo-evaluator.d.ts +42 -2
  82. package/dist/types/orchestration/solo-spec-builder.d.ts +3 -0
  83. package/dist/types/orchestration/testing/delegate-test-bridge.d.ts +6 -0
  84. package/dist/types/orchestration/testing/run-state-client-double.d.ts +13 -0
  85. package/dist/types/orchestration/workflow/builtin-capabilities.d.ts +3 -0
  86. package/dist/types/orchestration/workflow/capability-catalog.d.ts +31 -0
  87. package/dist/types/orchestration/workflow/cron-schedule.d.ts +3 -4
  88. package/dist/types/orchestration/workflow/expression.d.ts +2 -1
  89. package/dist/types/orchestration/workflow/n8n-import.d.ts +3 -0
  90. package/dist/types/orchestration/workflow/node-registry.d.ts +2 -2
  91. package/dist/types/orchestration/workflow/node-schema.d.ts +20 -4
  92. package/dist/types/orchestration/workflow/params-schema.d.ts +7 -6
  93. package/dist/types/orchestration/workflow/qla-executor-host.d.ts +4 -1
  94. package/dist/types/orchestration/workflow/run-history-store.d.ts +33 -3
  95. package/dist/types/orchestration/workflow/semantic-acceptance.d.ts +65 -0
  96. package/dist/types/orchestration/workflow/workflow-authoring.d.ts +74 -0
  97. package/dist/types/orchestration/workflow/workflow-bundle.d.ts +4 -0
  98. package/dist/types/orchestration/workflow/workflow-controller.d.ts +16 -4
  99. package/dist/types/orchestration/workflow/workflow-edit-context.d.ts +46 -0
  100. package/dist/types/orchestration/workflow/workflow-intent-contract.d.ts +56 -0
  101. package/dist/types/orchestration/workflow/workflow-patch.d.ts +7 -0
  102. package/dist/types/orchestration/workflow/workflow-runtime.d.ts +5 -0
  103. package/dist/types/orchestration/workflow/workflow-scheduler.d.ts +11 -0
  104. package/dist/types/orchestration/workflow/workflow-store.d.ts +5 -0
  105. package/dist/types/orchestration/workflow/workflow-template-setup.d.ts +65 -0
  106. package/dist/types/orchestration/workflow/workflow-trigger.d.ts +4 -0
  107. package/dist/types/orchestration/workflow-chat-builder.d.ts +105 -20
  108. package/dist/types/orchestration/worktree-task-prompt.d.ts +1 -0
  109. package/dist/types/protocol/agent-contract.d.ts +49 -8
  110. package/dist/types/protocol/notifications.d.ts +1 -1
  111. package/dist/types/protocol/wire/acp-agent-management.d.ts +97 -9
  112. package/dist/types/protocol/wire/acp-protocol.d.ts +7 -1
  113. package/dist/types/protocol/wire/agent-methods.d.ts +15 -1
  114. package/dist/types/protocol/wire/index.d.ts +2 -4
  115. package/dist/types/protocol/wire/memory-provider-lifecycle.d.ts +1 -39
  116. package/dist/types/protocol/wire/notification-payloads.d.ts +96 -1
  117. package/dist/types/protocol/wire/web-capability.d.ts +2 -2
  118. package/dist/types/runtime/community/community-consent-client.d.ts +3 -0
  119. package/dist/types/runtime/config/tunable-defaults.d.ts +0 -6
  120. package/dist/types/runtime/execution/bounded-output-tail.d.ts +7 -0
  121. package/dist/types/runtime/execution/dream-agent.d.ts +8 -5
  122. package/dist/types/runtime/execution/dream-category-context.d.ts +3 -3
  123. package/dist/types/runtime/execution/structured-tool-progress.d.ts +21 -0
  124. package/dist/types/runtime/hooks/memory-hooks.d.ts +20 -8
  125. package/dist/types/runtime/infra/background-tasks.d.ts +5 -1
  126. package/dist/types/runtime/infra/cloud-auth-host-authority.d.ts +4 -0
  127. package/dist/types/runtime/infra/llmrouter-access-token.d.ts +0 -1
  128. package/dist/types/runtime/infra/subagent-turn-snapshot.d.ts +32 -0
  129. package/dist/types/runtime/infra/turn-telemetry-store.d.ts +22 -0
  130. package/dist/types/runtime/memory/implicit-extraction.d.ts +23 -7
  131. package/dist/types/runtime/ports/agent-runtime-ports.d.ts +0 -5
  132. package/dist/types/runtime/ports/index.d.ts +2 -3
  133. package/dist/types/runtime/ports/memory-provider.d.ts +31 -16
  134. package/dist/types/runtime/ports/memory-writer.d.ts +55 -6
  135. package/dist/types/runtime/ports/permission-contracts.d.ts +2 -0
  136. package/dist/types/runtime/ports/tool-contracts.d.ts +3 -1
  137. package/dist/types/runtime/prompt/identity-section.d.ts +2 -0
  138. package/dist/types/runtime/session/session-permission-store.d.ts +6 -0
  139. package/dist/types/runtime/tasks/task-types.d.ts +2 -0
  140. package/dist/types/skills/memory/host-memory-provider.d.ts +59 -9
  141. package/dist/types/skills/memory/memory-tool.d.ts +3 -1
  142. package/dist/types/skills/memory/task-distillation.d.ts +22 -3
  143. package/dist/types/skills/permissions/hook-runner.d.ts +8 -0
  144. package/dist/types/skills/permissions/operation-classifier.d.ts +7 -0
  145. package/dist/types/skills/skill-system/skill-category.d.ts +10 -0
  146. package/dist/types/skills/tools/agent-tool.d.ts +13 -21
  147. package/dist/types/skills/tools/edit-tool.d.ts +10 -2
  148. package/dist/types/skills/tools/exec-tool.d.ts +2 -2
  149. package/dist/types/skills/tools/file-text-snapshot.d.ts +24 -0
  150. package/dist/types/skills/tools/lsp-tool.d.ts +1 -1
  151. package/dist/types/skills/tools/patch-tool.d.ts +10 -3
  152. package/dist/types/skills/tools/read-tool.d.ts +23 -1
  153. package/dist/types/skills/tools/repo-map-tool.d.ts +52 -0
  154. package/dist/types/skills/tools/search-tool.d.ts +10 -1
  155. package/dist/types/skills/tools/shell/index.d.ts +1 -2
  156. package/dist/types/skills/tools/shell/shell-command.d.ts +1 -1
  157. package/dist/types/skills/tools/shell/shell-exec.d.ts +2 -2
  158. package/dist/types/skills/tools/shell/task-output.d.ts +12 -3
  159. package/dist/types/skills/tools/subagent-decision-tool.d.ts +15 -0
  160. package/dist/types/skills/tools/task-tool.d.ts +16 -2
  161. package/dist/types/skills/tools/write-tool.d.ts +2 -1
  162. package/dist/types/transport/acp-server.d.ts +1 -0
  163. package/dist/types/transport/host-cloud-auth-client.d.ts +10 -0
  164. package/dist/types/transport/host-community-client.d.ts +8 -0
  165. package/dist/types/transport/host-run-state-client.d.ts +6 -0
  166. package/dist/types/workflow-host.d.ts +8 -1
  167. package/dist/workflow-host.js +9 -9
  168. package/package.json +25 -6
  169. package/dist/types/cli/tool-bootstrap-web-registration.d.ts +0 -14
  170. package/dist/types/orchestration/tool-cascade.d.ts +0 -49
  171. package/dist/types/protocol/wire/channel-ingress.d.ts +0 -29
  172. package/dist/types/protocol/wire/channel.d.ts +0 -89
  173. package/dist/types/runtime/infra/native-mcp-config-sync.d.ts +0 -16
  174. package/dist/types/runtime/memory/categories.d.ts +0 -5
  175. package/dist/types/runtime/memory/recall-category-filter.d.ts +0 -42
  176. package/dist/types/runtime/ports/source-provider.d.ts +0 -39
  177. package/dist/types/runtime/ports/web-search-contracts.d.ts +0 -21
  178. package/dist/types/server/search-svc.d.ts +0 -1
  179. package/dist/types/skills/memory/local-embedding.d.ts +0 -80
  180. package/dist/types/skills/memory/memory-config-resolver.d.ts +0 -4
  181. package/dist/types/skills/memory/memory-embedding-config.d.ts +0 -31
  182. package/dist/types/skills/tools/web-answer-tool.d.ts +0 -27
  183. package/dist/types/skills/tools/web-fetch-tool.d.ts +0 -80
  184. package/dist/types/skills/tools/web-research-tool.d.ts +0 -48
  185. package/dist/types/skills/tools/web-search-tool.d.ts +0 -46
  186. package/dist/types/skills/web-search/brave-source.d.ts +0 -3
  187. package/dist/types/skills/web-search/crawl4ai-extractor.d.ts +0 -16
  188. package/dist/types/skills/web-search/embedding-rerank.d.ts +0 -13
  189. package/dist/types/skills/web-search/exa-source.d.ts +0 -3
  190. package/dist/types/skills/web-search/multi-source-backend.d.ts +0 -23
  191. package/dist/types/skills/web-search/redis-source-cache.d.ts +0 -6
  192. package/dist/types/skills/web-search/search-svc-source.d.ts +0 -5
  193. package/dist/types/skills/web-search/searxng-source.d.ts +0 -4
  194. package/dist/types/skills/web-search/serper-source.d.ts +0 -3
  195. package/dist/types/skills/web-search/source-factory.d.ts +0 -6
  196. package/dist/types/skills/web-search/stability.d.ts +0 -26
  197. package/dist/types/skills/web-search/web-tunable-resolver.d.ts +0 -16
@@ -5,6 +5,18 @@ import type { ProductOrchestrator } from "./agent-instance.js";
5
5
  import type { HostRunStateAuthority } from "./run-state-host-authority.js";
6
6
  import type { LeaderPort, PhaseRunnerPort } from "./goal-loop-coordinator.js";
7
7
  import { type AcceptanceCriterion, type AcceptanceDelta, type PhaseSpec } from "./goal-run-types.js";
8
+ export type GoalVerifyCommandValidation = {
9
+ valid: true;
10
+ } | {
11
+ valid: false;
12
+ reason: string;
13
+ };
14
+ /**
15
+ * Persisted Goal verifiers are unattended acceptance contracts, not general-purpose shell scripts.
16
+ * Reject known stdin, interactive, host-specific and nondeterministic constructs before persistence;
17
+ * runVerifyDeltas repeats the check for old snapshots and defense in depth.
18
+ */
19
+ export declare function validateGoalVerifyCommand(command: string): GoalVerifyCommandValidation;
8
20
  /**
9
21
  * #2 verify 输出的头尾截断:测试/构建命令的失败摘要通常在输出**末尾**(框架的 summary 行),裸
10
22
  * slice(0,N) 保头丢尾会把真正的失败原因截掉,判官只能看到无关的开头。超限时保留头尾各半,并在
@@ -110,6 +122,10 @@ export declare function parsePhaseSpec(reply: string, availableAgentIds: string[
110
122
  */
111
123
  export declare function validateAssessDeltas(rawDeltas: AcceptanceDelta[], changedFiles: string[], log?: {
112
124
  warn(msg: string): void;
125
+ }, context?: {
126
+ criteria?: AcceptanceCriterion[];
127
+ outputTexts?: string[];
128
+ assignmentReceiptLines?: string[];
113
129
  }): AcceptanceDelta[];
114
130
  /**
115
131
  * #1②: the judge-prompt view of this phase's project changed files. The PROMPT is windowed to stay
@@ -20,6 +20,9 @@ export interface AcceptanceCriterion {
20
20
  id: string;
21
21
  criterion: string;
22
22
  status: AcceptanceStatus;
23
+ /** Output-only criteria (reply/copy/summary/etc.) are accepted from the Product task result text,
24
+ * never by inventing a shell verifier or citing an unrelated file. */
25
+ evidenceSource?: "output" | "host.product.assignment";
23
26
  evidence?: AcceptanceEvidence[];
24
27
  reason?: string;
25
28
  verify?: string;
@@ -71,7 +74,7 @@ export interface GoalQueuedMessage {
71
74
  export interface GoalRunEvent {
72
75
  seq: number;
73
76
  ts: string;
74
- type: "goal_started" | "phase_planned" | "phase_started" | "task_settled" | "phase_assessed" | "progress_compacted" | "goal_edited" | "message_queued" | "paused" | "resumed" | "stopped" | "phase_boundary" | "ended";
77
+ type: "goal_started" | "checklist_initialized" | "phase_planned" | "phase_started" | "task_settled" | "phase_assessed" | "progress_compacted" | "goal_edited" | "message_queued" | "paused" | "resumed" | "stopped" | "phase_boundary" | "round_message" | "ended";
75
78
  payload: Record<string, unknown>;
76
79
  }
77
80
  /** Derived Goal checkpoint stored by Gateway RunState, rebuildable by replaying events. */
@@ -83,6 +86,8 @@ export interface PersistedGoalRunState {
83
86
  currentGoal: string;
84
87
  goalUpdatedAt?: string;
85
88
  checklistVersion: number;
89
+ /** False only between the durable start acknowledgement and the detached leader initialization. */
90
+ checklistInitialized?: boolean;
86
91
  status: GoalRunStatus;
87
92
  pauseState: GoalPauseState;
88
93
  phaseIndex: number;
@@ -16,6 +16,27 @@ export interface BudgetCheck {
16
16
  elapsed: number;
17
17
  maxDuration?: number;
18
18
  }
19
+ /**
20
+ * The persisted budget shape — SINGLE source of truth, owned here and consumed by
21
+ * product-persistence's execution and planning snapshots.
22
+ *
23
+ * It must stay round-trippable: `serialize()` is the only writer and `resume()` rebuilds the tracker
24
+ * from these exact fields. The ceilings are live state (raiseBudget mutates them), not construction
25
+ * config, so dropping them from the snapshot silently removes every guard from a resumed run.
26
+ */
27
+ export interface PersistedBudgetState {
28
+ maxTotalTokens?: number;
29
+ maxDuration?: number;
30
+ usedTokens: number;
31
+ startedAt: number;
32
+ warningEmitted: boolean;
33
+ /**
34
+ * Absent on a planning snapshot: a planning session carries only the ceilings, and nothing has run
35
+ * yet, so there is no in/out split to record. Present on every execution snapshot.
36
+ */
37
+ inputTokens?: number;
38
+ outputTokens?: number;
39
+ }
19
40
  export declare class ProductBudgetTracker {
20
41
  private maxTotalTokens?;
21
42
  private maxDuration?;
@@ -56,20 +77,18 @@ export declare class ProductBudgetTracker {
56
77
  maxTotalTokens?: number;
57
78
  maxDuration?: number;
58
79
  }): void;
59
- /** Restore from persisted budget data. (input/output optional for back-compat with older snapshots.) */
60
- restore(data: {
61
- usedTokens: number;
62
- startedAt: number;
63
- warningEmitted: boolean;
64
- inputTokens?: number;
65
- outputTokens?: number;
66
- }): void;
67
- /** Serialize for persistence. */
68
- serialize(): {
69
- usedTokens: number;
70
- startedAt: number;
71
- warningEmitted: boolean;
72
- inputTokens: number;
73
- outputTokens: number;
74
- };
80
+ /**
81
+ * Restore from persisted budget data. Also re-applies the persisted ceilings so a single
82
+ * `restore()` fully rebuilds the tracker — callers that already passed them to the constructor
83
+ * are unaffected (same values), and callers that forget can no longer end up unbounded.
84
+ * A planning snapshot has no in/out split yet, so those default to 0 rather than being required.
85
+ */
86
+ restore(data: PersistedBudgetState): void;
87
+ /**
88
+ * Serialize for persistence. MUST emit the ceilings: they are live state (raiseBudget mutates
89
+ * them) and resume() rebuilds the tracker from this snapshot alone. Omitting them made every
90
+ * resumed or rolled-back run unbounded, because check() short-circuits on a falsy ceiling.
91
+ * Absent ceilings stay absent so an unbudgeted run is not accidentally given one.
92
+ */
93
+ serialize(): PersistedBudgetState;
75
94
  }
@@ -2,6 +2,7 @@
2
2
  * Product persistence facade over the Gateway-owned RunStateStore.
3
3
  */
4
4
  import type { ProductPhase, ProductInstanceDef } from "../protocol/wire/acp-agent-management.js";
5
+ import type { PersistedBudgetState } from "./product-budget.js";
5
6
  import type { SerializedNode } from "./dag-scheduler.js";
6
7
  import type { PlanningSession } from "./product-planner.js";
7
8
  import { type HostRunStateAuthority } from "./run-state-host-authority.js";
@@ -13,13 +14,8 @@ export interface PersistedProductState {
13
14
  cwd: string;
14
15
  instances: ProductInstanceDef[];
15
16
  tasks: SerializedNode[];
16
- budget: {
17
- maxTotalTokens?: number;
18
- maxDuration?: number;
19
- usedTokens: number;
20
- startedAt: number;
21
- warningEmitted: boolean;
22
- };
17
+ /** Owned by ProductBudgetTracker — see PersistedBudgetState for the round-trip contract. */
18
+ budget: PersistedBudgetState;
23
19
  createdAt: string;
24
20
  lastCheckpointAt: string;
25
21
  /** Last durably announced attempt number for each stable task id. */
@@ -42,13 +38,8 @@ export interface PersistedProductPlanningState {
42
38
  cwd: string;
43
39
  instances: ProductInstanceDef[];
44
40
  tasks: SerializedNode[];
45
- budget: {
46
- maxTotalTokens?: number;
47
- maxDuration?: number;
48
- usedTokens: number;
49
- startedAt: number;
50
- warningEmitted: boolean;
51
- };
41
+ /** Owned by ProductBudgetTracker — see PersistedBudgetState for the round-trip contract. */
42
+ budget: PersistedBudgetState;
52
43
  createdAt: string;
53
44
  lastCheckpointAt: string;
54
45
  planningSession: PlanningSession;
@@ -115,15 +115,43 @@ export interface DagMutation {
115
115
  taskId: string;
116
116
  details?: Record<string, unknown>;
117
117
  }
118
+ /**
119
+ * Human-readable form of an execution-phase leader reply.
120
+ *
121
+ * The raw reply is prose plus a JSON mutation array. Showing it verbatim puts machine payload in the
122
+ * conversation; showing nothing leaves the user's question unanswered. So: prose without the JSON
123
+ * block, and when the leader answered only in JSON, a line naming what it actually changed.
124
+ */
125
+ export declare function describeExecutionReply(response: string, mutations: DagMutation[]): string;
118
126
  export declare class ProductPlanner {
119
127
  private providerDirectory;
120
128
  private callbacks;
121
129
  private sessions;
122
130
  private sessionAuthorities;
131
+ /** Issues from the most recent plan semantic check, quoted back in the reprompt (empty = passed). */
132
+ private lastPlanIssues;
123
133
  constructor(providerDirectory: HostAgentProviderDirectory, callbacks?: PlannerCallbacks);
124
134
  private resolveOwnerAuthority;
125
135
  private assertSessionOwner;
126
136
  private getOrRestoreSession;
137
+ /**
138
+ * Phases where the ORCHESTRATOR owns this run's RunState key. The planner and the orchestrator write
139
+ * the SAME key for the same productId; ownership hands over at markExecuting() and never comes back
140
+ * (markAwaitingConfirmation only rolls back a create() that never started executing).
141
+ */
142
+ private static readonly EXECUTION_OWNED_PHASES;
143
+ /** True once execution owns the checkpoint — the planner must neither write it nor mutate phase. */
144
+ private executionHasTakenOver;
145
+ /**
146
+ * Persist the planning snapshot — unless execution has taken the key over.
147
+ *
148
+ * A leader turn is dispatched detached (`void runLeaderTurn`) with a 10-minute ceiling, so it can land
149
+ * long after the user confirmed and the DAG started. It used to write unconditionally, stamping a
150
+ * `stateKind:"planning"` snapshot over the live execution checkpoint — after which loadProductState()
151
+ * returns undefined for that run (it rejects planning snapshots), so a crash in that window made the
152
+ * executing run unresumable and reset usedTokens/task states. Dropping the stale write is correct:
153
+ * the planning dialogue it carried is no longer the authority for this run.
154
+ */
127
155
  private checkpointPlanningSession;
128
156
  private publishNotification;
129
157
  /**
@@ -229,6 +257,16 @@ export declare class ProductPlanner {
229
257
  restoreSession(data: PlanningSession, authority?: HostRunStateAuthority): void;
230
258
  private handlePlanningMessage;
231
259
  private handleExecutionMessage;
260
+ /**
261
+ * One leader turn over the Gateway delegate.
262
+ *
263
+ * `stream` opts INTO product.planningDelta and defaults to off. Only turns the user actually asked
264
+ * for belong in the conversation: the planning turn and a run-time steering message. The acceptance
265
+ * judge and the automatic failure consultation are internal machinery — they used to stream too, so
266
+ * every task acceptance pushed `VERDICT: PASS FEEDBACK: -` into the leader conversation. Nothing
267
+ * rendered that channel during a run, so the pollution stayed invisible until the run window
268
+ * surfaced it. Defaulting to silent means a future internal call site cannot leak by omission.
269
+ */
232
270
  private sendToLeader;
233
271
  /**
234
272
  * Extract a JSON object from the leader's reply. The leader (an LLM) formats the block
@@ -11,7 +11,9 @@ export declare function getWorktreeDiff(worktreePath: string): Promise<string>;
11
11
  export declare function listWorktreeChangedFiles(worktreePath: string): Promise<string[]>;
12
12
  /** Copy the changed files from a task worktree back into the product workspace. */
13
13
  export declare function materializeWorktreeChanges(worktreePath: string, targetRoot: string): Promise<void>;
14
- /** Remove a git worktree. */
15
- export declare function removeWorktree(gitRoot: string, path: string): Promise<void>;
14
+ /** Remove a git worktree. When `branch` is given, also delete the worktree's throwaway branch
15
+ * (created by createWorktree's `-B solo/<name>`); best effort — the branch never carries commits
16
+ * of its own, but leaving it behind litters the user's repo with one `solo/*` ref per racer. */
17
+ export declare function removeWorktree(gitRoot: string, path: string, branch?: string): Promise<void>;
16
18
  /** Merge a worktree branch into the current branch. */
17
19
  export declare function mergeWorktree(gitRoot: string, worktreeBranch: string): Promise<string>;
@@ -8,7 +8,8 @@
8
8
  * 3. On completion of initial task, agents enter "idle" state (process kept alive)
9
9
  * 4. User can send follow-up messages to individual agents via solo.message
10
10
  * 5. User triggers evaluation via solo.evaluate (or skips directly to solo.select)
11
- * 6. solo.select → merge winning worktree, clean up others
11
+ * 6. solo.select → materialize the winner's worktree changes into the workspace, clean up all
12
+ * worktrees + solo/* branches
12
13
  *
13
14
  * Key design:
14
15
  * - Solo = special project type persisted by the Gateway RunState authority
@@ -34,8 +35,16 @@ export interface SoloCallbacks {
34
35
  onAgentActivity?: (soloId: string, agentId: string, toolName: string) => void;
35
36
  /** Token usage report after agent completes. */
36
37
  onAgentUsage?: (soloId: string, agentId: string, inputTokens: number, outputTokens: number) => void;
38
+ /** Full (capped) unified diff of a competitor's worktree once a turn settles — the same diff the
39
+ * judge scores, so the user can inspect actual changes instead of only the agent's self-report. */
40
+ onAgentDiff?: (soloId: string, agentId: string, diff: string) => void;
41
+ /** Run-level state transition (running/evaluating/…): lets the UI narrate the auto-judge phase. */
42
+ onState?: (soloId: string, state: SoloState, projectId: string) => void;
37
43
  /** Required Gateway delegate access; Solo fails loud when the Host rail is unavailable. */
38
44
  getDelegateBridge?: () => DelegateBridge | undefined;
45
+ /** Ready (launchable) agent provider ids — used to prefer an INDEPENDENT judge over a competitor
46
+ * scoring its own race. Best effort: absent/failing falls back to a participant judge. */
47
+ listReadyAgentIds?: () => Promise<string[]>;
39
48
  /**
40
49
  * Race reached a terminal state WITHOUT an evaluation winner (all agents failed, or cancelled).
41
50
  * The success path uses onEvaluation; this lets the host write back the plan project's planStatus
@@ -78,6 +87,18 @@ export declare class SoloEvaluator {
78
87
  private snapshotSession;
79
88
  private queuePersistSession;
80
89
  private publishNotification;
90
+ /** Announce the run-level state so the UI can narrate phases (esp. the auto-judge window). */
91
+ private publishState;
92
+ /**
93
+ * Resolve a session, lazily rehydrating from the Host RunState checkpoint after an engine
94
+ * restart — without this, every restart turned live races into zombies (uncancellable,
95
+ * unadoptable, undeletable, forever "运行中" in history).
96
+ *
97
+ * A restart killed the racer processes, so a checkpointed "running"/"pending" agent can never
98
+ * settle: mark it failed to make the run actionable. Same for a mid-flight "evaluating" run —
99
+ * the judge turn is gone; drop back to "running" so select/cancel/evaluate stay available.
100
+ */
101
+ private requireSession;
81
102
  /**
82
103
  * Start a Solo Mode PK session.
83
104
  * Creates worktrees, spawns agents in parallel, waits for completion, then evaluates.
@@ -119,16 +140,35 @@ export declare class SoloEvaluator {
119
140
  soloId: string;
120
141
  displayId: string;
121
142
  } | null;
143
+ /**
144
+ * Replay each in-flight agent's already-streamed turn text (reconnect/refresh resume). The status
145
+ * snapshot only carries SETTLED turn text; this hands back what the current turn has produced so
146
+ * far, so a refresh mid-race doesn't blank the streaming columns until the next delta.
147
+ */
148
+ replayLiveText(soloId: string, emit: (agentDisplayId: string, text: string) => void): Promise<void>;
122
149
  /** Get the current status of a solo session. */
123
150
  getStatus(soloId: string): SoloStatus | null;
124
151
  /** Cancel a running solo session. Kill all agents and clean up worktrees. */
125
152
  cancel(soloId: string): Promise<void>;
126
153
  /**
127
- * Select a winner and merge their worktree into the main branch.
154
+ * Select a winner and adopt their worktree changes into the workspace.
155
+ *
156
+ * Racers never commit on their `solo/*` branch, so the old `git merge --no-ff` here was a no-op
157
+ * ("Already up to date") and the follow-up cleanup then deleted every uncommitted产物. Adoption
158
+ * now COPIES the winner's staged/untracked changes back (same materialize path Product mode uses)
159
+ * and only cleans up after the copy succeeded — a materialize failure keeps all worktrees intact.
128
160
  */
129
161
  select(params: SoloSelectParams): Promise<string>;
130
162
  /** Delete a solo session, killing agents and cleaning up worktrees if still active. */
131
163
  delete(soloId: string): Promise<void>;
164
+ /**
165
+ * Pick a ready agent that is NOT racing to act as an independent judge (小智优先). Returns a
166
+ * synthetic member on the same supervised delegate rail: unique seq (= agents.length) keeps its
167
+ * memberKey distinct, cwd = the project workspace (the judge only reads the prompt; evaluation
168
+ * turns are stream-suppressed and its memberId is unknown to getMemberContext, so nothing leaks
169
+ * into competitor columns). Best effort — any failure falls back to a participant judge.
170
+ */
171
+ private resolveExternalJudge;
132
172
  /**
133
173
  * Build an evaluation prompt and send to the user-chosen evaluator agent.
134
174
  * Returns evaluation result.
@@ -35,6 +35,9 @@ export interface SpecChatDeps {
35
35
  /** (a) Owner global memory cheat-sheet — the spec moderator must honor standing
36
36
  * preferences/boundaries (language, style, hard limits) when drafting the spec. */
37
37
  globalMemoryIndex?: string | null;
38
+ /** 上一轮已形成的规格草稿。多轮打磨必须在它的基础上增量更新——不回传会导致第二轮起模型
39
+ * 凭对话重写整份规格,用户此前敲定的约束/验收被静默丢弃。 */
40
+ previousSpec?: SoloSpec | null;
38
41
  }
39
42
  /** R3 多轮对话式 spec:agent 通过此工具产出/更新结构化规格(类比 plan_mode 的 plan 入参)。 */
40
43
  export declare const SET_SPEC_TOOL_NAME = "set_spec";
@@ -10,6 +10,12 @@ interface LegacyTurnFixture {
10
10
  outputTokens: number;
11
11
  };
12
12
  } | null;
13
+ /**
14
+ * Optional streamed chunks for this turn, replayed through the caller's sink before the result
15
+ * resolves. The bridge used to drop the sink entirely, so no test could observe which turns stream —
16
+ * which is how every acceptance verdict reached the leader conversation unnoticed.
17
+ */
18
+ streamDeltas?(memberId: string, prompt: string): string[];
13
19
  }
14
20
  /** Test-only adapter for migrating orchestration fixtures from the retired local spawn lane. */
15
21
  export declare function makeDelegateTestBridge(processManager: LegacyTurnFixture): DelegateBridge;
@@ -0,0 +1,13 @@
1
+ /**
2
+ * Test double helper for HostRunStateClient.
3
+ *
4
+ * The RunState client contract is hand-rolled into ~19 inline object literals across the orchestration
5
+ * tests, each cast with `as never`. That cast means TypeScript cannot tell a double from a real client,
6
+ * so adding a method to the contract breaks every one of them at RUNTIME instead of at compile time —
7
+ * which is exactly what happened when `openWithCheckpoint` was introduced.
8
+ *
9
+ * This wrapper derives the atomic method from whatever `open`/`checkpoint` the double already provides,
10
+ * so existing spies and their assertions keep working unchanged: `openWithCheckpoint` still routes
11
+ * through the double's own `checkpoint` spy, preserving every "checkpoint was called with X" assertion.
12
+ */
13
+ export declare function runStateClientDouble<T extends Record<string, unknown>>(partial: T): never;
@@ -0,0 +1,3 @@
1
+ import type { CapabilityEntry } from "./capability-catalog.js";
2
+ /** Fresh copies prevent Host/UI consumers from mutating the shared contract. */
3
+ export declare function builtinWorkflowCapabilities(): CapabilityEntry[];
@@ -16,9 +16,40 @@ export interface CapabilityEntry {
16
16
  toolName?: string;
17
17
  server?: string;
18
18
  tool?: string;
19
+ /** Machine-readable planning hints owned by Runtime, not prose invented by the Agent. */
20
+ useWhen?: string[];
21
+ avoidWhen?: string[];
22
+ keywords?: string[];
23
+ inputSchema?: Record<string, unknown>;
24
+ outputSchema?: Record<string, unknown>;
25
+ inputPorts?: Array<{
26
+ name: string;
27
+ type: string;
28
+ required?: boolean;
29
+ }>;
30
+ outputPorts?: Array<{
31
+ name: string;
32
+ type: string;
33
+ }>;
34
+ requiredParams?: string[];
35
+ sideEffectLevel?: "none" | "local" | "external";
36
+ permissionHints?: string[];
37
+ constraints?: string[];
38
+ examples?: Array<{
39
+ intent: string;
40
+ params?: Record<string, unknown>;
41
+ }>;
19
42
  }
20
43
  /** Render the Host-owned catalog for the AI graph builder prompt. */
21
44
  export declare function renderCatalogForPrompt(entries: CapabilityEntry[], perCategoryCap?: number): string;
45
+ /**
46
+ * Select a compact, deterministic capability working set before the Agent turn.
47
+ * The full catalog remains available through list_capabilities for long-tail discovery.
48
+ */
49
+ export declare function selectRelevantCapabilities(entries: CapabilityEntry[], intent: string, options?: {
50
+ limit?: number;
51
+ preferredIds?: string[];
52
+ }): CapabilityEntry[];
22
53
  /** Extract canonical references for anti-hallucination validation. */
23
54
  export declare function collectCapabilityRefs(def: {
24
55
  nodes: {
@@ -3,9 +3,8 @@
3
3
  *
4
4
  * `validateCron` (trigger-validation.ts) guarantees a stored schedule is structurally valid; this
5
5
  * module turns a validated cron string into a concrete "next fire time" so the in-process
6
- * WorkflowScheduler can arm a timer. Pure, side-effect-free, and UTC-based for determinism — the
7
- * scheduler injects its own clock, and tests pin time exactly. (A future local-timezone offset is a
8
- * caller concern; the engine itself is UTC so the same input always yields the same output.)
6
+ * WorkflowScheduler can arm a timer. Pure, side-effect-free, and deterministic for an explicit
7
+ * IANA timezone. Legacy callers that omit a timezone retain UTC semantics.
9
8
  *
10
9
  * Grammar matches validateCron exactly: 5-field (min hour dom month dow) or 6-field (+ leading
11
10
  * seconds); each field is a comma-list of star / star-step / value / range / stepped-range, with
@@ -34,4 +33,4 @@ export declare function parseCron(cron: string): ParsedCron;
34
33
  * exists within a ~5-year horizon (e.g. an impossible date like "0 0 30 2 *"). Deterministic: the
35
34
  * same (cron, afterMs) always returns the same value.
36
35
  */
37
- export declare function nextCronTime(cron: string, afterMs: number): number;
36
+ export declare function nextCronTime(cron: string, afterMs: number, timezone?: string): number;
@@ -10,7 +10,8 @@
10
10
  * - context roots: $input · $json · $node("name") · $now · $vars · $trigger
11
11
  * - accessors: `.prop` and `[index]` / `["key"]`
12
12
  * - literals: string ('..' / ".."), number, true/false/null
13
- * - whitelist functions: len, upper, lower, default, jsonpath, date
13
+ * - whitelist functions: len, upper, lower, default, jsonpath, date,
14
+ * eq, ne, gt, gte, lt, lte, not, and, or, contains
14
15
  *
15
16
  * fail-loud: unknown roots/functions, reads through null/undefined, and prototype-escape keys
16
17
  * all throw. Absent *leaf* keys evaluate to undefined (so `default(x, fb)` works).
@@ -1,4 +1,5 @@
1
1
  import type { WorkflowDef } from "./node-schema.js";
2
+ import type { WorkflowTemplateSetupManifest } from "./workflow-template-setup.js";
2
3
  export interface N8nImportOptions {
3
4
  strictTemplates?: boolean;
4
5
  }
@@ -54,6 +55,8 @@ export interface N8nImportResult {
54
55
  def: WorkflowDef;
55
56
  report: N8nConversionReport;
56
57
  }
58
+ /** Turn imported n8n credential references into one centralized Host-owned connection form. */
59
+ export declare function n8nConnectionSetupManifest(report: N8nConversionReport): WorkflowTemplateSetupManifest | undefined;
57
60
  export declare class N8nImportError extends Error {
58
61
  readonly errors: string[];
59
62
  constructor(errors: string[]);
@@ -8,7 +8,7 @@
8
8
  */
9
9
  import type { NodeExecutor } from "./node-schema.js";
10
10
  /**
11
- * Node kinds whose builtin executor is an import-only stub a host is meant to replace.
11
+ * Node kinds whose builtin executor is a Host-binding placeholder.
12
12
  * installHostExecutors overrides ONLY these when already present; any other
13
13
  * pre-registered kind is kept. Single source of the "rebindable kind" rule.
14
14
  */
@@ -22,7 +22,7 @@ export declare class NodeRegistry {
22
22
  /**
23
23
  * Wire host-backed executors — the single source of the host-wiring rule used by the
24
24
  * runtime, the gateway handler, and tests. Absent kinds are registered; an already-present
25
- * rebindable kind (agentBinding/modelBinding, whose builtin is an import-only stub) is
25
+ * rebindable kind (whose builtin is a Host-binding placeholder) is
26
26
  * overridden; any other already-present kind is kept (caller's pre-registration wins).
27
27
  */
28
28
  installHostExecutors(executors: Record<string, NodeExecutor>): void;
@@ -89,6 +89,8 @@ export interface ExecutorContext {
89
89
  kind: string;
90
90
  /** Owning workflow id (def.id) — lets host-backed nodes (approval) tag outbound notifications. */
91
91
  workflowId?: string;
92
+ /** Durable run identity used by Host-backed observability and recovery projections. */
93
+ runId?: string;
92
94
  /** This run's trigger kind (manual/schedule/…) — drives fine-grained unattended audits (IT-7b). */
93
95
  triggerKind?: string;
94
96
  /** 0-based; increments per loop iteration (drives the cache key, spec §A5). */
@@ -120,6 +122,8 @@ export interface ExecutorHost {
120
122
  httpRequest(req: HttpHostRequest): Promise<DataItem[]>;
121
123
  /** Invoke an MCP server tool. */
122
124
  invokeMcp(req: McpHostRequest): Promise<DataItem[]>;
125
+ /** Execute an installed n8n ecosystem node in the Host-owned compatibility worker. */
126
+ runN8nNode?(req: N8nNodeHostRequest): Promise<Record<string, DataItem[]>>;
123
127
  /** Send a message out through a channel (飞书/微信/…) via the xiaozhiclaw channel layer. */
124
128
  sendChannel(req: ChannelHostRequest): Promise<DataItem[]>;
125
129
  /** Project-scoped memory (memdir) read/write/search for the `memory` kind (spec D25). */
@@ -128,8 +132,8 @@ export interface ExecutorHost {
128
132
  runSubworkflow?(req: SubworkflowHostRequest): Promise<DataItem[]>;
129
133
  /**
130
134
  * Human-in-the-loop approval (D34): notify the owner and AWAIT the decision in-memory
131
- * (the run stays "running"; the node shows pending). A restart loses pending approvals —
132
- * the run then fails loud (durable suspended-run resumption is a tracked follow-up).
135
+ * (the run stays "running"; the node shows pending). The Runtime Host persists suspended-run
136
+ * state and reconstructs the approval wait after restart.
133
137
  */
134
138
  approval?(req: ApprovalHostRequest): Promise<{
135
139
  approved: boolean;
@@ -138,8 +142,8 @@ export interface ExecutorHost {
138
142
  }>;
139
143
  /**
140
144
  * D34 wait-until-webhook: suspend the branch until the given webhook path is called
141
- * (await-in-memory, same posture as approval the run stays "running"; a restart loses the
142
- * wait and the run fails loud; checkpoint replay recovers prior steps on re-run).
145
+ * (same posture as approval). The Runtime Host persists the checkpoint and re-registers the
146
+ * webhook wait after restart.
143
147
  */
144
148
  waitWebhook?(req: WebhookWaitHostRequest): Promise<Record<string, unknown>>;
145
149
  }
@@ -163,6 +167,8 @@ export interface HttpHostRequest {
163
167
  url: string;
164
168
  headers?: Record<string, string>;
165
169
  body?: unknown;
170
+ /** Stable across retries/recovery for downstream de-duplication. */
171
+ idempotencyKey?: string;
166
172
  signal?: AbortSignal;
167
173
  }
168
174
  export interface McpHostRequest {
@@ -171,11 +177,21 @@ export interface McpHostRequest {
171
177
  args: Record<string, unknown>;
172
178
  signal?: AbortSignal;
173
179
  }
180
+ export interface N8nNodeHostRequest {
181
+ n8nType: string;
182
+ version?: number;
183
+ parameters: Record<string, unknown>;
184
+ connectionIds?: Record<string, string>;
185
+ input: DataItem[];
186
+ idempotencyKey?: string;
187
+ signal?: AbortSignal;
188
+ }
174
189
  export interface ChannelHostRequest {
175
190
  channel: string;
176
191
  target?: string;
177
192
  payload: unknown;
178
193
  input: DataItem[];
194
+ idempotencyKey?: string;
179
195
  signal?: AbortSignal;
180
196
  }
181
197
  export interface SubworkflowHostRequest {
@@ -13,7 +13,8 @@
13
13
  * - a value that is a `{{ }}` template is skipped for type checks (resolved at runtime).
14
14
  * - an `__ASK__: 问题` sentinel (brace-less ON PURPOSE so it bypasses the {{ }} expression gate in
15
15
  * validateDefExpressions) counts as "present but pending" (the agent honestly marking an unknown,
16
- * not a hallucination) — surfaced by collectClarifications for the 待补 badge + activation gate.
16
+ * not a hallucination) — surfaced by collectClarifications for the pending-field badge and
17
+ * execution-readiness validation.
17
18
  */
18
19
  import type { CapabilityEntry } from "./capability-catalog.js";
19
20
  /** Per-kind params schemas. `trigger` (workflow-level trigger def) and
@@ -30,7 +31,7 @@ type NodeLike = {
30
31
  /**
31
32
  * Resolve the schema governing a canonical node's params.
32
33
  */
33
- export declare function resolveNodeParamsSchema(node: NodeLike, _entries: CapabilityEntry[]): Record<string, unknown> | undefined;
34
+ export declare function resolveNodeParamsSchema(node: NodeLike, entries: CapabilityEntry[]): Record<string, unknown> | undefined;
34
35
  /**
35
36
  * Validate every node's params against its resolved schema. Returns human-readable Chinese errors
36
37
  * (empty = clean). Skips `trigger` (trigger def is validated elsewhere) and `manual` (placeholder).
@@ -38,11 +39,11 @@ export declare function resolveNodeParamsSchema(node: NodeLike, _entries: Capabi
38
39
  */
39
40
  export declare function validateParamsAgainstSchema(def: {
40
41
  nodes: NodeLike[];
41
- }, _entries: CapabilityEntry[]): string[];
42
+ }, entries: CapabilityEntry[]): string[];
42
43
  /**
43
- * Collect every `{{ __ASK__ }}` placeholder in a def (top-level params + one level into `args`).
44
- * Drives the canvas "待补" badge and the activation gate (a workflow with pending asks cannot be
45
- * activated). Empty = nothing pending.
44
+ * Collect every brace-less `__ASK__` placeholder in a def (top-level params + one level into
45
+ * `args`). Drives the canvas pending-field badge and execution-readiness validation. Empty =
46
+ * nothing pending.
46
47
  */
47
48
  export declare function collectAskPlaceholders(def: {
48
49
  nodes: NodeLike[];
@@ -7,7 +7,7 @@
7
7
  */
8
8
  import type { LLMTransport } from "../../runtime/ports/index.js";
9
9
  import { type DataItem } from "./data-item.js";
10
- import type { ExecutorHost, MemoryHostRequest, SubworkflowHostRequest, ApprovalHostRequest, WebhookWaitHostRequest } from "./node-schema.js";
10
+ import type { ExecutorHost, N8nNodeHostRequest, MemoryHostRequest, SubworkflowHostRequest, ApprovalHostRequest, WebhookWaitHostRequest } from "./node-schema.js";
11
11
  /** Injected boundary capabilities — supplied by the handler host that owns the real runners. */
12
12
  export interface QlaExecutorHostDeps {
13
13
  /** Run one agent turn (spawn external ACP agent + sendTask). Returns the agent's text output. */
@@ -29,6 +29,8 @@ export interface QlaExecutorHostDeps {
29
29
  args: Record<string, unknown>;
30
30
  signal?: AbortSignal;
31
31
  }) => Promise<unknown>;
32
+ /** Execute an installed n8n ecosystem node through the embedding Host. */
33
+ runN8nNode?: (req: N8nNodeHostRequest) => Promise<Record<string, DataItem[]>>;
32
34
  /**
33
35
  * Send a message out through a channel via the xiaozhiclaw channel layer.
34
36
  * Undefined in standalone qlogicagent (no gateway) → channel nodes fail-loud (D12/D13).
@@ -37,6 +39,7 @@ export interface QlaExecutorHostDeps {
37
39
  channel: string;
38
40
  target?: string;
39
41
  payload: unknown;
42
+ idempotencyKey?: string;
40
43
  signal?: AbortSignal;
41
44
  }) => Promise<unknown>;
42
45
  /**