@agent-compose/sdk 0.7.0 → 0.8.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 +66 -39
- package/dist/agent/__tests__/runtime-json-schema.test.d.ts +10 -0
- package/dist/agent/agent-context.d.ts +21 -1
- package/dist/agent/agent-loop.d.ts +24 -1
- package/dist/client.d.ts +338 -534
- package/dist/directives.d.ts +112 -0
- package/dist/display.d.ts +242 -0
- package/dist/errors.d.ts +24 -1
- package/dist/index.d.ts +24 -12
- package/dist/index.js +3545 -1667
- package/dist/pause/wrappers.d.ts +31 -9
- package/dist/runtimes/_acp-client.d.ts +46 -1
- package/dist/runtimes/_cli-agent.d.ts +49 -4
- package/dist/runtimes/_jsonl-guard.d.ts +103 -0
- package/dist/runtimes/amp.d.ts +2 -2
- package/dist/runtimes/claude-code.d.ts +59 -0
- package/dist/runtimes/claude-code.test.d.ts +14 -0
- package/dist/runtimes/claude.d.ts +16 -0
- package/dist/runtimes/claude.test.d.ts +8 -0
- package/dist/runtimes/codex.d.ts +9 -3
- package/dist/runtimes/cursor.d.ts +2 -2
- package/dist/runtimes/droid.d.ts +2 -2
- package/dist/runtimes/jsonl-guard.test.d.ts +19 -0
- package/dist/runtimes/openai-desktop.js +2691 -864
- package/dist/runtimes/opencode.d.ts +2 -2
- package/dist/runtimes/vercel.js +12 -1
- package/dist/sandbox/devbox.d.ts +42 -0
- package/dist/sandbox/exec-stream.d.ts +14 -0
- package/dist/sandbox/network-policy.d.ts +100 -0
- package/dist/sandbox/provider-def.d.ts +79 -0
- package/dist/sandbox/providers/desktop.d.ts +10 -0
- package/dist/sandbox/providers/e2b.d.ts +17 -0
- package/dist/sandbox/providers/local.d.ts +11 -0
- package/dist/sandbox/providers/vercel.d.ts +18 -0
- package/dist/sandbox/registry.d.ts +45 -0
- package/dist/sandbox/sizes.d.ts +68 -0
- package/dist/sandbox.d.ts +24 -299
- package/dist/step-invocation/__tests__/foreground-recovery.test.d.ts +1 -0
- package/dist/step-invocation/invoker.d.ts +10 -0
- package/dist/step-invocation/protocol.d.ts +5 -0
- package/dist/types/api-compliance.d.ts +71 -0
- package/dist/types/api-conversations.d.ts +492 -0
- package/dist/types/api-factory.d.ts +309 -0
- package/dist/types/api-projects.d.ts +131 -0
- package/dist/types/api-runs.d.ts +377 -0
- package/dist/types/api-scopes.d.ts +102 -0
- package/dist/types/conversation-stream.d.ts +191 -0
- package/dist/types/execution-context.d.ts +12 -2
- package/dist/types/protocol.d.ts +30 -1
- package/dist/types/sandbox-environment.d.ts +8 -5
- package/dist/types/sandbox.d.ts +74 -4
- package/dist/types/workflow-metadata.d.ts +33 -8
- package/dist/types/workflow-plan.d.ts +10 -0
- package/dist/types/workflow.d.ts +18 -205
- package/dist/utils/bundler.d.ts +12 -1
- package/dist/workflow-steps/index.d.ts +1 -1
- package/dist/workflow-steps/observability.d.ts +8 -1
- package/dist/workflow-steps/runner.d.ts +3 -3
- package/dist/workflow-steps/step.d.ts +15 -1
- package/dist/workflow-steps/types.d.ts +19 -5
- package/dist/workflow-steps/workflow.d.ts +22 -1
- package/dist/workflows/engine.d.ts +3 -2
- package/dist/workflows/invoke-child.d.ts +2 -2
- package/package.json +1 -1
- package/src/agent/agent-context.ts +186 -3
- package/src/agent/agent-loop.ts +31 -2
- package/src/client.ts +909 -621
- package/src/directives.ts +184 -0
- package/src/display.ts +788 -0
- package/src/errors.ts +39 -0
- package/src/index.ts +104 -10
- package/src/pause/wrappers.ts +44 -9
- package/src/runtimes/_acp-client.ts +72 -3
- package/src/runtimes/_cli-agent.ts +159 -36
- package/src/runtimes/_jsonl-guard.ts +219 -0
- package/src/runtimes/claude-code.ts +246 -0
- package/src/runtimes/claude.ts +32 -2
- package/src/runtimes/codex.ts +55 -3
- package/src/runtimes/openai-desktop.ts +59 -14
- package/src/sandbox/devbox.ts +48 -0
- package/src/sandbox/exec-stream.ts +48 -0
- package/src/sandbox/network-policy.ts +181 -0
- package/src/sandbox/provider-def.ts +94 -0
- package/src/sandbox/providers/desktop.ts +57 -0
- package/src/sandbox/providers/e2b.ts +354 -0
- package/src/sandbox/providers/local.ts +106 -0
- package/src/sandbox/providers/vercel.ts +331 -0
- package/src/sandbox/registry.ts +198 -0
- package/src/sandbox/sizes.ts +95 -0
- package/src/sandbox.ts +59 -1275
- package/src/step-invocation/invoker.ts +151 -28
- package/src/step-invocation/protocol.ts +8 -0
- package/src/types/api-compliance.ts +79 -0
- package/src/types/api-conversations.ts +522 -0
- package/src/types/api-factory.ts +336 -0
- package/src/types/api-projects.ts +140 -0
- package/src/types/api-runs.ts +412 -0
- package/src/types/api-scopes.ts +102 -0
- package/src/types/conversation-stream.ts +231 -0
- package/src/types/execution-context.ts +10 -2
- package/src/types/protocol.ts +33 -0
- package/src/types/sandbox-environment.ts +28 -9
- package/src/types/sandbox.ts +73 -4
- package/src/types/workflow-metadata.ts +35 -8
- package/src/types/workflow-plan.ts +11 -0
- package/src/types/workflow.ts +25 -292
- package/src/utils/bundler.ts +32 -5
- package/src/utils/errors.ts +16 -1
- package/src/workflow-steps/index.ts +1 -0
- package/src/workflow-steps/observability.ts +19 -8
- package/src/workflow-steps/runner.ts +4 -4
- package/src/workflow-steps/step.ts +49 -1
- package/src/workflow-steps/types.ts +20 -5
- package/src/workflow-steps/workflow.ts +22 -1
- package/src/workflows/engine.ts +3 -2
- package/src/workflows/invoke-child.ts +2 -2
package/src/errors.ts
CHANGED
|
@@ -1,10 +1,49 @@
|
|
|
1
|
+
/** Stable machine-readable denial codes on membership/capability-gated
|
|
2
|
+
* mutations (ADR-0045). Reads never carry a code — a visibility denial is
|
|
3
|
+
* a plain 404, indistinguishable from a missing id. */
|
|
4
|
+
export type AuthzErrorCode =
|
|
5
|
+
| "role_read_only"
|
|
6
|
+
| "owner_required"
|
|
7
|
+
| "capability_required"
|
|
8
|
+
| "membership_required"
|
|
9
|
+
| "last_owner"
|
|
10
|
+
| "approver_only";
|
|
11
|
+
|
|
1
12
|
/** Thrown by AgentComposeClient when the server returns a non-2xx response. */
|
|
2
13
|
export class AgentComposeError extends Error {
|
|
14
|
+
/** Parsed `Retry-After` response header, in milliseconds, when the server
|
|
15
|
+
* sent one (rate-limit 429s do). Pollers use it to honor the server's own
|
|
16
|
+
* estimate of when the limit window clears instead of guessing. */
|
|
17
|
+
readonly retryAfterMs?: number;
|
|
18
|
+
/** Stable error code on gated-mutation 403s (ADR-0045) — one of
|
|
19
|
+
* `AuthzErrorCode` when the denial is a membership/capability gate;
|
|
20
|
+
* undefined otherwise. */
|
|
21
|
+
readonly code?: string;
|
|
22
|
+
/** The missing capability on a `capability_required` denial
|
|
23
|
+
* (e.g. "write", "invoke", "see_runs"). */
|
|
24
|
+
readonly capability?: string;
|
|
25
|
+
|
|
3
26
|
constructor(
|
|
4
27
|
public readonly status: number,
|
|
5
28
|
message: string,
|
|
29
|
+
opts?: { retryAfterMs?: number; code?: string; capability?: string },
|
|
6
30
|
) {
|
|
7
31
|
super(message);
|
|
8
32
|
this.name = "AgentComposeError";
|
|
33
|
+
if (opts?.retryAfterMs !== undefined) this.retryAfterMs = opts.retryAfterMs;
|
|
34
|
+
if (opts?.code !== undefined) this.code = opts.code;
|
|
35
|
+
if (opts?.capability !== undefined) this.capability = opts.capability;
|
|
9
36
|
}
|
|
10
37
|
}
|
|
38
|
+
|
|
39
|
+
/** Parse a `Retry-After` header into milliseconds. Accepts both RFC 9110
|
|
40
|
+
* forms — delta-seconds (`"120"`) and HTTP-date — and returns `undefined`
|
|
41
|
+
* for anything unparseable so callers fall back to their own backoff. */
|
|
42
|
+
export function parseRetryAfterMs(header: string | null | undefined): number | undefined {
|
|
43
|
+
if (!header) return undefined;
|
|
44
|
+
const seconds = Number(header);
|
|
45
|
+
if (Number.isFinite(seconds)) return Math.max(0, seconds * 1000);
|
|
46
|
+
const date = Date.parse(header);
|
|
47
|
+
if (!Number.isNaN(date)) return Math.max(0, date - Date.now());
|
|
48
|
+
return undefined;
|
|
49
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -16,7 +16,6 @@
|
|
|
16
16
|
// Factory functions
|
|
17
17
|
export { defineRuntime } from "./types/runtime.js";
|
|
18
18
|
export { defineWorkflow } from "./types/workflow.js";
|
|
19
|
-
export type { WorkflowDefinition } from "./types/workflow.js";
|
|
20
19
|
export { defineSandboxEnvironment } from "./types/sandbox-environment.js";
|
|
21
20
|
export type { SandboxEnvironmentDefinition } from "./types/sandbox-environment.js";
|
|
22
21
|
|
|
@@ -31,8 +30,6 @@ export type {
|
|
|
31
30
|
|
|
32
31
|
// Workflow types and runtime utilities
|
|
33
32
|
export type {
|
|
34
|
-
WorkflowFn,
|
|
35
|
-
WorkflowCtx,
|
|
36
33
|
WorkflowRun,
|
|
37
34
|
AgentBudget,
|
|
38
35
|
WorkflowHooks,
|
|
@@ -46,7 +43,7 @@ export type { ConnectorRequestRules } from "./types/workflow-metadata.js";
|
|
|
46
43
|
|
|
47
44
|
// Snapshot entry type re-exported for consumers (dashboard, CLI).
|
|
48
45
|
export type { RunSnapshotEntry } from "./client.js";
|
|
49
|
-
export type { WorkflowPlan, WorkflowStepPlan } from "./types/workflow-plan.js";
|
|
46
|
+
export type { WorkflowPlan, WorkflowStepPlan, WorkflowStepDeliverable } from "./types/workflow-plan.js";
|
|
50
47
|
export type { BaseExecutionContext, InvokeChild } from "./types/execution-context.js";
|
|
51
48
|
|
|
52
49
|
// Request context — per-run typed bag (tenant identity + freeform).
|
|
@@ -108,6 +105,8 @@ export type {
|
|
|
108
105
|
export type {
|
|
109
106
|
SandboxProvider,
|
|
110
107
|
DesktopSandboxProvider,
|
|
108
|
+
SandboxPtyOpts,
|
|
109
|
+
SandboxPtyHandle,
|
|
111
110
|
} from "./types/sandbox.js";
|
|
112
111
|
|
|
113
112
|
// HTTP client
|
|
@@ -122,6 +121,8 @@ export type {
|
|
|
122
121
|
TeamMember, Mention, CreateMentionsInput,
|
|
123
122
|
EventSubjectType, EventRow, ReportEventInput, ListEventsOptions, ListEventsResult,
|
|
124
123
|
RunLogLine, ListRunLogsOptions,
|
|
124
|
+
RunListEntry, ListRunsOptions, RunDetail,
|
|
125
|
+
FundingLane, RunFundingStamp, RunFundingUsageRow, RunFundingResponse,
|
|
125
126
|
RegisteredRuntime, RunState, RunStatus, FactoryRow, SnapshotListEntry, SnapshotListResponse,
|
|
126
127
|
ApiKey, ApiKeyCreated,
|
|
127
128
|
UsageRollupRow, UsageResponse,
|
|
@@ -130,13 +131,73 @@ export type {
|
|
|
130
131
|
SendAgentMessageOptions, SendAgentMessageResponse,
|
|
131
132
|
AnswerSteerOptions,
|
|
132
133
|
ResumePauseOptions, ResumePauseResponse, ResumePauseSuccess, ResumePausePending, ResumePauseActor,
|
|
134
|
+
ConversationMessagePart, ConversationRow, ConversationMessageRow,
|
|
135
|
+
ConversationsPage, ConversationDetail, ConversationThread,
|
|
136
|
+
ConversationPageContext, SendConversationMessageInput, SendConversationMessageResult,
|
|
137
|
+
ConversationTurnState, ConversationPresenceSnapshot, StreamConversationOptions, AgentListRow,
|
|
138
|
+
CreateCloudSessionInput, CloudSessionCreated,
|
|
139
|
+
// Cloud-session developer surface (ADR-0052)
|
|
140
|
+
SessionPreview, PreviewOpened, OpenPreviewInput, SessionForked,
|
|
141
|
+
// Session branch proposals (ADR-0053)
|
|
142
|
+
SessionFileChange, SessionChangeSet,
|
|
143
|
+
SessionMergeReportDetail, SessionMergeReport, SessionDiscardReport,
|
|
144
|
+
// Channel-attached sessions (ADR-0057)
|
|
145
|
+
ChannelSessionStatus, ChannelSessionRow, ChannelSessionsResponse, SessionChannelMessagePosted,
|
|
146
|
+
FactoryFileSearchRow, FactoryFolderSearchRow, SearchFactoryFilesOptions, FactoryFileSearchResult, PublicFileLinkState,
|
|
147
|
+
// Membership-scoped authorization (ADR-0045)
|
|
148
|
+
ConversationMemberRole, ConversationMember,
|
|
149
|
+
DocumentCapability, TemplateCapability, ScopeGrant, ArtifactScope,
|
|
150
|
+
RunContext, SetScopeGrantsInput, SetTemplateScopeInput, TemplateDetail,
|
|
151
|
+
// Projects (ADR-0045 projects extension)
|
|
152
|
+
Project, ProjectsPage, ProjectRole, ProjectMember,
|
|
153
|
+
ProjectObject, ProjectObjectsPage, ProjectSkippedFile, ProjectPreviewFile,
|
|
154
|
+
ProjectAddPreview, AddProjectObjectInput, AddProjectObjectResult,
|
|
155
|
+
RefreshProjectObjectResult,
|
|
156
|
+
// Break-glass compliance sessions (ADR-0051)
|
|
157
|
+
ComplianceScopeKind, ComplianceStatus, ComplianceSession, ComplianceAccess,
|
|
158
|
+
RequestComplianceSessionInput, ListComplianceSessionsOptions, ComplianceSessionsPage,
|
|
159
|
+
ListComplianceAccessesOptions, ComplianceAccessesPage,
|
|
133
160
|
} from "./client.js";
|
|
134
161
|
|
|
135
162
|
// SSE parser — exposed so tests and downstream callers can reuse it.
|
|
136
163
|
export { parseSseStream } from "./sse.js";
|
|
137
164
|
|
|
165
|
+
// Cloud-session UI directives — the marker contract between the in-sandbox
|
|
166
|
+
// `agentc` CLI and the server's cloud executor.
|
|
167
|
+
export {
|
|
168
|
+
renderDirectiveMarker, parseDirectiveMarkers,
|
|
169
|
+
DIRECTIVE_MARKER_PREFIX, DIRECTIVE_MARKER_SUFFIX, MAX_DIRECTIVES_PER_OUTPUT,
|
|
170
|
+
REVISION_SELECTOR_RE,
|
|
171
|
+
ASK_DIRECTIVE_PROMPT_MAX, ASK_DIRECTIVE_MAX_OPTIONS,
|
|
172
|
+
ASK_DIRECTIVE_OPTION_ID_MAX, ASK_DIRECTIVE_OPTION_LABEL_MAX,
|
|
173
|
+
ASK_APPROVER_MIN, ASK_APPROVER_MAX,
|
|
174
|
+
} from "./directives.js";
|
|
175
|
+
export type { CloudDirective } from "./directives.js";
|
|
176
|
+
|
|
177
|
+
// Conversation stream — typed wire events + the frame normalizer, shared by
|
|
178
|
+
// `streamConversation` and clients that run their own SSE loop (the CLI's
|
|
179
|
+
// `agentc session` terminal driver reuses its bridge parser + normalizes
|
|
180
|
+
// through this, so every surface holds the same durable-vs-live invariant).
|
|
181
|
+
export { normalizeConversationStreamEvent } from "./types/conversation-stream.js";
|
|
182
|
+
export type {
|
|
183
|
+
ConversationStreamEvent, ConversationStreamAuthor,
|
|
184
|
+
ConversationPartEvent, ConversationPartPartialEvent, ConversationMessageDoneEvent,
|
|
185
|
+
ConversationErrorEvent, ConversationReactionEvent, ConversationMessageDeletedEvent,
|
|
186
|
+
ConversationReplayContinueEvent, ConversationTurnStateEvent, ConversationPresenceEvent,
|
|
187
|
+
ConversationSessionStatusEvent,
|
|
188
|
+
ConversationPresenceClient, ConversationAgentPresence,
|
|
189
|
+
} from "./types/conversation-stream.js";
|
|
190
|
+
|
|
191
|
+
// ACP client peer — the JSON-RPC client half of ADR-0020. Re-exported for the
|
|
192
|
+
// CLI's local-agent bridge daemon (`agentc bridge`), which is an ACP client
|
|
193
|
+
// over a locally spawned agent process and reuses the exact same peer +
|
|
194
|
+
// session/update normaliser as the sandbox CLI-agent runtimes.
|
|
195
|
+
export { AcpClientPeer, normalizeSessionUpdate, ACP_PROTOCOL_VERSION } from "./runtimes/_acp-client.js";
|
|
196
|
+
export type { AcpAvailableCommand, AcpClientPeerDeps, AcpSessionCaps } from "./runtimes/_acp-client.js";
|
|
197
|
+
|
|
138
198
|
// Errors and utilities
|
|
139
199
|
export { AgentComposeError } from "./errors.js";
|
|
200
|
+
export type { AuthzErrorCode } from "./errors.js";
|
|
140
201
|
export { formatError } from "./utils/errors.js";
|
|
141
202
|
|
|
142
203
|
// Bundling utilities
|
|
@@ -170,9 +231,11 @@ export type { GatewayModelId } from "ai";
|
|
|
170
231
|
// CLI-agent runtimes — drive an external agentic CLI (codex / amp) inside the
|
|
171
232
|
// sandbox and stream-parse its JSONL. No heavy npm deps (the CLI lives in the
|
|
172
233
|
// sandbox image), so these are root-exported like claudeRuntime.
|
|
173
|
-
export { createCodexRuntime } from "./runtimes/codex.js";
|
|
234
|
+
export { createCodexRuntime, codexSpec } from "./runtimes/codex.js";
|
|
174
235
|
export type { CodexRuntimeConfig } from "./runtimes/codex.js";
|
|
175
236
|
export { default as codexRuntime } from "./runtimes/codex.js";
|
|
237
|
+
// Reasoning-effort level a CLI runtime turn may carry (claude-code / codex).
|
|
238
|
+
export type { CliReasoningEffort } from "./runtimes/_cli-agent.js";
|
|
176
239
|
export { createAmpRuntime } from "./runtimes/amp.js";
|
|
177
240
|
export type { AmpRuntimeConfig } from "./runtimes/amp.js";
|
|
178
241
|
export { default as ampRuntime } from "./runtimes/amp.js";
|
|
@@ -188,6 +251,14 @@ export { createDroidRuntime, droidSpec } from "./runtimes/droid.js";
|
|
|
188
251
|
export type { DroidRuntimeConfig } from "./runtimes/droid.js";
|
|
189
252
|
export { default as droidRuntime } from "./runtimes/droid.js";
|
|
190
253
|
|
|
254
|
+
// Claude Code as a CLI-agent runtime (in-sandbox `claude -p` / the Zed ACP
|
|
255
|
+
// adapter) — the cloud-hostable counterpart of `claudeRuntime` (claude.ts,
|
|
256
|
+
// which drives the Agent SDK in the calling process and so can never run a
|
|
257
|
+
// server-driven cloud-session turn).
|
|
258
|
+
export { createClaudeCodeRuntime, claudeCodeSpec, CLAUDE_CODE_ACP_ADAPTER, CLAUDE_CODE_THINKING_TOKENS } from "./runtimes/claude-code.js";
|
|
259
|
+
export type { ClaudeCodeRuntimeConfig } from "./runtimes/claude-code.js";
|
|
260
|
+
export { default as claudeCodeRuntime } from "./runtimes/claude-code.js";
|
|
261
|
+
|
|
191
262
|
// Built-in coding tools for Vercel AI SDK runtime.
|
|
192
263
|
export { bashTool, codingTools, editTool, readTool, writeTool } from "./tools/index.js";
|
|
193
264
|
export type { CodingTool } from "./tools/index.js";
|
|
@@ -202,7 +273,10 @@ export { createSandbox, reconnectSandbox, killAllSandboxes, killSandboxById,
|
|
|
202
273
|
parseSseExecStream, AGENT_COMPOSE_TAG,
|
|
203
274
|
SANDBOX_VCPUS, DEFAULT_SANDBOX_SIZE, E2B_TEMPLATE_SIZES,
|
|
204
275
|
isE2bSupportedSize, e2bMachineSpec, e2bBaseTemplate, e2bAgentEnvTemplate,
|
|
205
|
-
isPlatformE2bTemplateAlias
|
|
276
|
+
isPlatformE2bTemplateAlias,
|
|
277
|
+
// ADR-0038 "Computer" — the per-member persistent desktop machine template.
|
|
278
|
+
E2B_DEVBOX_TEMPLATE, E2B_DEVBOX_SPEC, E2B_DEVBOX_RECIPE_VERSION,
|
|
279
|
+
e2bDevboxTemplateRef } from "./sandbox.js";
|
|
206
280
|
export { SandboxUnavailableError, SANDBOX_UNAVAILABLE_PREFIX } from "./sandbox-errors.js";
|
|
207
281
|
export type {
|
|
208
282
|
SandboxCreateOpts, SandboxNetworkPolicy, SandboxNetworkHeaderTransform,
|
|
@@ -210,7 +284,7 @@ export type {
|
|
|
210
284
|
SandboxQuotaResult, OwnedSandboxResult, OwnedSandbox, SandboxSize,
|
|
211
285
|
ParseSseExecStreamOptions, SandboxCommandRunOptions, SandboxCommandResult,
|
|
212
286
|
} from "./sandbox.js";
|
|
213
|
-
export type { SandboxResources } from "./types/workflow-metadata.js";
|
|
287
|
+
export type { SandboxResources, DriveMergePolicy } from "./types/workflow-metadata.js";
|
|
214
288
|
|
|
215
289
|
// Workflow engine
|
|
216
290
|
export { runWorkflow, WorkflowError, EngineError, classifyError, parseNameVersion } from "./workflows/engine.js";
|
|
@@ -231,6 +305,7 @@ export {
|
|
|
231
305
|
export type {
|
|
232
306
|
Step,
|
|
233
307
|
StepContext,
|
|
308
|
+
StepDeliverable,
|
|
234
309
|
StepRunResult,
|
|
235
310
|
Workflow,
|
|
236
311
|
DefineStepOpts,
|
|
@@ -274,7 +349,7 @@ export {
|
|
|
274
349
|
} from "./pause/errors.js";
|
|
275
350
|
export type { PauseErrorCode } from "./pause/errors.js";
|
|
276
351
|
export type { PauseRequest } from "./pause/pause-core.js";
|
|
277
|
-
export type { WaitForEventRequest } from "./pause/wrappers.js";
|
|
352
|
+
export type { WaitForEventRequest, DecisionRequest } from "./pause/wrappers.js";
|
|
278
353
|
// ADR-0028 — the in-sandbox pause client. `agentc pause` and the gate-pause
|
|
279
354
|
// processor both pause their OWN run through the server pause API and block
|
|
280
355
|
// until a human answers (create-then-poll; the VM suspends in place while
|
|
@@ -298,7 +373,26 @@ export { agentLoop, parseAgentStatus, DEFAULT_CLAUDE_MODEL } from "./agent/agent
|
|
|
298
373
|
export type { AgentLifecycleEvent, AgentLoopOpts, AgentLoopResult } from "./agent/agent-loop.js";
|
|
299
374
|
export { agent } from "./agent/run-agent.js";
|
|
300
375
|
export type { AgentOpts } from "./agent/run-agent.js";
|
|
301
|
-
export { AGENT_COMPOSE_MANUAL, buildAgentContextDoc, writeAgentContext } from "./agent/agent-context.js";
|
|
302
|
-
export type { AgentConnectorInfo } from "./agent/agent-context.js";
|
|
376
|
+
export { AGENT_COMPOSE_MANUAL, buildAgentContextDoc, writeAgentContext, buildAddedSessionBrief } from "./agent/agent-context.js";
|
|
377
|
+
export type { AgentConnectorInfo, AddedSessionBriefParams } from "./agent/agent-context.js";
|
|
303
378
|
export { AgentMessageSchema, parseAgentResponse } from "./agent/protocol.js";
|
|
304
379
|
export { importSourceModule, TMP_DIR, LATEST_VERSION } from "./utils/source-loader.js";
|
|
380
|
+
|
|
381
|
+
// The display palette (ADR-0040 §7) — the typed marker contract between
|
|
382
|
+
// `agentc display` and the session executors, plus the promoter that maps
|
|
383
|
+
// native-harness tool traffic onto the platform's rich-card part shapes.
|
|
384
|
+
export {
|
|
385
|
+
DISPLAY_MARKER_KEY, DISPLAY_MARKER_VERSION, PLAN_MAX_ENTRIES, PLAN_ENTRY_MAX_CHARS,
|
|
386
|
+
TABLE_MAX_COLUMNS, TABLE_MAX_ROWS, TABLE_CELL_MAX_CHARS,
|
|
387
|
+
CHART_MAX_SERIES, CHART_MAX_POINTS_PER_SERIES, CHART_LABEL_MAX_CHARS,
|
|
388
|
+
ASK_PROMPT_MAX_CHARS, ASK_MAX_OPTIONS, ASK_OPTION_ID_MAX_CHARS, ASK_OPTION_LABEL_MAX_CHARS,
|
|
389
|
+
serializeDisplayMarker, parseDisplayMarker, findDisplayMarker, clampPlanEntries,
|
|
390
|
+
clampTableData, clampChartSeries, clampChartAxisLabel, clampAskOptions,
|
|
391
|
+
detectAgentcInvocation, shellWords, createDisplayPromoter,
|
|
392
|
+
} from "./display.js";
|
|
393
|
+
export type {
|
|
394
|
+
DisplayMarker, DisplayPlanEntry, DisplayPlanStatus,
|
|
395
|
+
DisplayTableCell, DisplayTableColumn, DisplayTableData,
|
|
396
|
+
DisplayChartKind, DisplayChartPoint, DisplayChartSeries, DisplayAskOption,
|
|
397
|
+
AgentcInvocation, PromotedPart, DisplayPromoter, DisplayPromoterContext,
|
|
398
|
+
} from "./display.js";
|
package/src/pause/wrappers.ts
CHANGED
|
@@ -1,21 +1,24 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* The
|
|
3
|
-
* closure over `ctx.pause`:
|
|
2
|
+
* The three opinionated pause wrappers (ADR-0006 §"SDK surface", ADR-0042),
|
|
3
|
+
* each a thin closure over `ctx.pause`:
|
|
4
4
|
*
|
|
5
5
|
* - `sleep` — a lightweight timed pause; resolves on its own TTL,
|
|
6
6
|
* skips the snapshot, returns void.
|
|
7
7
|
* - `waitForEvent` — pause until an event resumes by correlation key.
|
|
8
|
-
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
*
|
|
12
|
-
*
|
|
8
|
+
* - `requestDecision` — a typed human/agent decision (wire `kind:
|
|
9
|
+
* "decision"`): the prompt/options/approvers ride
|
|
10
|
+
* `payload` for the dashboard's answer UI, and the
|
|
11
|
+
* resume value is the frozen `{ decision: string }`
|
|
12
|
+
* convention. `approvers` travel as RAW member refs
|
|
13
|
+
* (user ids or emails) — the SERVER resolves them
|
|
14
|
+
* against the team roster at pause-insert time and
|
|
15
|
+
* stamps the gate-bearing snapshots (ADR-0042 §2).
|
|
13
16
|
*
|
|
14
17
|
* Built from a `PauseFn` so the wrapper logic lives in one place and the step
|
|
15
18
|
* runner just spreads them onto the context next to `pause`.
|
|
16
19
|
*/
|
|
17
20
|
|
|
18
|
-
import
|
|
21
|
+
import { z } from "zod";
|
|
19
22
|
import type { StepPauseRequest } from "../step-invocation/types.js";
|
|
20
23
|
import type { PauseRequest } from "./pause-core.js";
|
|
21
24
|
|
|
@@ -23,7 +26,7 @@ import type { PauseRequest } from "./pause-core.js";
|
|
|
23
26
|
export type PauseFn = <T = unknown>(req: PauseRequest<T>) => Promise<T>;
|
|
24
27
|
|
|
25
28
|
/** Internal: pause with an explicit wire `kind`. The wrappers stamp
|
|
26
|
-
* `sleep`/`event` through this; the public `ctx.pause` is always
|
|
29
|
+
* `decision`/`sleep`/`event` through this; the public `ctx.pause` is always
|
|
27
30
|
* `custom` and never exposes it. */
|
|
28
31
|
export type KindedPauseFn = <T = unknown>(req: PauseRequest<T>, kind: StepPauseRequest["kind"]) => Promise<T>;
|
|
29
32
|
|
|
@@ -35,9 +38,26 @@ export interface WaitForEventRequest<T> {
|
|
|
35
38
|
ttlMs?: number;
|
|
36
39
|
}
|
|
37
40
|
|
|
41
|
+
export interface DecisionRequest {
|
|
42
|
+
prompt: string;
|
|
43
|
+
/** Choices the decision UI offers as buttons; free text is always open. */
|
|
44
|
+
options?: Array<string | { label: string; value: string }>;
|
|
45
|
+
/** Team member refs (user ids or emails, ≤ 10) — with any named, ONLY a
|
|
46
|
+
* named approver may resolve the decision, and each gets an Activity
|
|
47
|
+
* ping. Resolution is server-side at pause creation. */
|
|
48
|
+
approvers?: string[];
|
|
49
|
+
/** DecisionDraft artifact rendered alongside the prompt. */
|
|
50
|
+
draft?: Record<string, unknown>;
|
|
51
|
+
ttlMs?: number;
|
|
52
|
+
correlationKey?: string;
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
const DecisionResultSchema = z.object({ decision: z.string() });
|
|
56
|
+
|
|
38
57
|
export interface PauseWrappers {
|
|
39
58
|
sleep(durationMs: number): Promise<void>;
|
|
40
59
|
waitForEvent<T = unknown>(req: WaitForEventRequest<T>): Promise<T>;
|
|
60
|
+
requestDecision(req: DecisionRequest): Promise<{ decision: string }>;
|
|
41
61
|
}
|
|
42
62
|
|
|
43
63
|
export function buildPauseWrappers(pause: KindedPauseFn): PauseWrappers {
|
|
@@ -61,5 +81,20 @@ export function buildPauseWrappers(pause: KindedPauseFn): PauseWrappers {
|
|
|
61
81
|
...(req.ttlMs !== undefined ? { ttlMs: req.ttlMs } : {}),
|
|
62
82
|
}, "event");
|
|
63
83
|
},
|
|
84
|
+
|
|
85
|
+
requestDecision(req: DecisionRequest): Promise<{ decision: string }> {
|
|
86
|
+
return pause<{ decision: string }>({
|
|
87
|
+
reason: req.prompt,
|
|
88
|
+
payload: {
|
|
89
|
+
prompt: req.prompt,
|
|
90
|
+
...(req.options !== undefined ? { options: req.options } : {}),
|
|
91
|
+
...(req.approvers !== undefined ? { approvers: req.approvers } : {}),
|
|
92
|
+
...(req.draft !== undefined ? { draft: req.draft } : {}),
|
|
93
|
+
},
|
|
94
|
+
schema: DecisionResultSchema,
|
|
95
|
+
...(req.ttlMs !== undefined ? { ttlMs: req.ttlMs } : {}),
|
|
96
|
+
...(req.correlationKey !== undefined ? { correlationKey: req.correlationKey } : {}),
|
|
97
|
+
}, "decision");
|
|
98
|
+
},
|
|
64
99
|
};
|
|
65
100
|
}
|
|
@@ -60,6 +60,28 @@ const OPTION_KIND_FOR_VERDICT = {
|
|
|
60
60
|
deny: ["reject_once", "reject_always"],
|
|
61
61
|
} as const;
|
|
62
62
|
|
|
63
|
+
/** Session-lifecycle capabilities the agent advertised at `initialize`,
|
|
64
|
+
* surfaced (not discarded) so callers can pick a resume strategy
|
|
65
|
+
* (ADR-0037 §3). The in-sandbox CLI-agent runtimes ignore both — they
|
|
66
|
+
* resume via the CLI's own on-disk rollout (ADR-0020 Q4); the bridge
|
|
67
|
+
* daemon attempts `session/resume` only when `resume` is true. */
|
|
68
|
+
export interface AcpSessionCaps {
|
|
69
|
+
/** Agent supports `session/load` — full-history replay as
|
|
70
|
+
* `agent_message_chunk`s. Deliberately NOT used for resume: replaying
|
|
71
|
+
* history would re-emit the transcript as new parts and duplicate the
|
|
72
|
+
* conversation (ADR-0037 alternative D). */
|
|
73
|
+
loadSession: boolean;
|
|
74
|
+
/** Agent supports `session/resume` — context restore with NO replay. */
|
|
75
|
+
resume: boolean;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/** One entry of the agent's slash-command palette, as announced by the ACP
|
|
79
|
+
* `available_commands_update` session notification. */
|
|
80
|
+
export interface AcpAvailableCommand {
|
|
81
|
+
name: string;
|
|
82
|
+
description: string;
|
|
83
|
+
}
|
|
84
|
+
|
|
63
85
|
/** Collaborators `AcpClientPeer` needs from `CliAgentRunner`, kept as a small
|
|
64
86
|
* injected surface so the peer stays transport-agnostic and unit-testable. */
|
|
65
87
|
export interface AcpClientPeerDeps {
|
|
@@ -80,6 +102,14 @@ export interface AcpClientPeerDeps {
|
|
|
80
102
|
/** Turn-scoped abort signal from `sendMessage`. On abort the peer sends
|
|
81
103
|
* `session/cancel` for the live session. */
|
|
82
104
|
signal?: AbortSignal;
|
|
105
|
+
/** The agent announced (or changed) its slash-command palette — an ACP
|
|
106
|
+
* `available_commands_update` session NOTIFICATION, which can arrive at
|
|
107
|
+
* any time (typically right after session/new, outside any prompt), so
|
|
108
|
+
* it rides a callback rather than the per-turn message stream. Each call
|
|
109
|
+
* carries the ENTIRE palette (replace semantics). Optional: the
|
|
110
|
+
* in-sandbox runtimes ignore it; the bridge daemon reports it to the
|
|
111
|
+
* server for composer autocomplete. */
|
|
112
|
+
onAvailableCommands?: (commands: AcpAvailableCommand[]) => void;
|
|
83
113
|
}
|
|
84
114
|
|
|
85
115
|
// ── The single session/update → AgentMessage normaliser ───────────────────────
|
|
@@ -270,6 +300,17 @@ export class AcpClientPeer {
|
|
|
270
300
|
// answers method-not-found.
|
|
271
301
|
const handler: Client = {
|
|
272
302
|
sessionUpdate: (params: acp.SessionNotification): void => {
|
|
303
|
+
// The slash-command palette is session state, not turn content —
|
|
304
|
+
// it can land OUTSIDE any prompt (right after session/new), when
|
|
305
|
+
// no turn queue is being drained, so it goes to its own callback
|
|
306
|
+
// instead of the AgentMessage stream (which drops it).
|
|
307
|
+
if (params.update.sessionUpdate === "available_commands_update") {
|
|
308
|
+
this.deps.onAvailableCommands?.(params.update.availableCommands.map((c) => ({
|
|
309
|
+
name: c.name,
|
|
310
|
+
description: c.description,
|
|
311
|
+
})));
|
|
312
|
+
return;
|
|
313
|
+
}
|
|
273
314
|
// Push mapped messages onto the queue. Tolerate updates that race in
|
|
274
315
|
// after cancel (the agent may flush a few before unwinding) — the
|
|
275
316
|
// normaliser handles them the same way.
|
|
@@ -290,9 +331,12 @@ export class AcpClientPeer {
|
|
|
290
331
|
* Negotiate the wire protocol at `initialize`. Pins `protocolVersion` to
|
|
291
332
|
* integer 1 and advertises NO fs / terminal capabilities. Returns the
|
|
292
333
|
* version the agent negotiated — `CliAgentRunner` compares it to
|
|
293
|
-
* `ACP_PROTOCOL_VERSION` to decide ACP-path vs. legacy-JSONL fallback
|
|
334
|
+
* `ACP_PROTOCOL_VERSION` to decide ACP-path vs. legacy-JSONL fallback —
|
|
335
|
+
* plus the agent's advertised session-lifecycle capabilities (`caps`),
|
|
336
|
+
* which the bridge daemon caches as `agent_sessions.resume_supported`
|
|
337
|
+
* (ADR-0037 §3). Absent capability blocks mean "not supported".
|
|
294
338
|
*/
|
|
295
|
-
async initialize(): Promise<{ protocolVersion: number }> {
|
|
339
|
+
async initialize(): Promise<{ protocolVersion: number; caps: AcpSessionCaps }> {
|
|
296
340
|
const res = await this.conn.initialize({
|
|
297
341
|
protocolVersion: ACP_PROTOCOL_VERSION,
|
|
298
342
|
clientCapabilities: {
|
|
@@ -300,7 +344,15 @@ export class AcpClientPeer {
|
|
|
300
344
|
terminal: false,
|
|
301
345
|
},
|
|
302
346
|
});
|
|
303
|
-
return {
|
|
347
|
+
return {
|
|
348
|
+
protocolVersion: res.protocolVersion,
|
|
349
|
+
caps: {
|
|
350
|
+
loadSession: res.agentCapabilities?.loadSession ?? false,
|
|
351
|
+
// Per the ACP schema, `resume` is a capability OBJECT (`{}` =
|
|
352
|
+
// supported), not a boolean — presence is the signal.
|
|
353
|
+
resume: res.agentCapabilities?.sessionCapabilities?.resume != null,
|
|
354
|
+
},
|
|
355
|
+
};
|
|
304
356
|
}
|
|
305
357
|
|
|
306
358
|
/**
|
|
@@ -316,6 +368,23 @@ export class AcpClientPeer {
|
|
|
316
368
|
return res.sessionId;
|
|
317
369
|
}
|
|
318
370
|
|
|
371
|
+
/**
|
|
372
|
+
* Resume an existing session by id — ACP `session/resume` (ADR-0037 §3).
|
|
373
|
+
* ADDITIVE and opt-in: the in-sandbox CLI-agent runtimes never call this
|
|
374
|
+
* (their resume path is the CLI's own persisted rollout, see
|
|
375
|
+
* `startSession`); the bridge daemon calls it only when `initialize`
|
|
376
|
+
* advertised `caps.resume`. Unlike `session/load` there is NO history
|
|
377
|
+
* replay — the agent restores its internal context and returns nothing,
|
|
378
|
+
* so nothing is re-emitted through the caller's part sink. Throws on an
|
|
379
|
+
* unknown/expired session id (JSON-RPC error from the agent) — the caller
|
|
380
|
+
* marks the durable row stale and falls back to `startSession` + full
|
|
381
|
+
* re-render. `this.sessionId` is only adopted on success.
|
|
382
|
+
*/
|
|
383
|
+
async resumeSession(cwd: string, acpSessionId: string): Promise<void> {
|
|
384
|
+
await this.conn.resumeSession({ sessionId: acpSessionId, cwd, mcpServers: [] });
|
|
385
|
+
this.sessionId = acpSessionId;
|
|
386
|
+
}
|
|
387
|
+
|
|
319
388
|
/**
|
|
320
389
|
* Drive one `session/prompt` turn, yielding `AgentMessage`s as the agent
|
|
321
390
|
* streams `session/update` notifications. Resolves the generator when the
|