@robota-sdk/agent-subagent-runner 3.0.0-beta.82 → 3.0.0-beta.83

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/CHANGELOG.md ADDED
@@ -0,0 +1,629 @@
1
+ # @robota-sdk/agent-subagent-runner
2
+
3
+ ## 3.0.0-beta.83
4
+
5
+ ### Minor Changes
6
+
7
+ - e8779c9: A subagent consults the sandbox its shell tools run under, as its parent does. With
8
+ `autoAllowBashIfSandboxed` on, a confined command the subagent's gate leaves to the mode now runs
9
+ without a prompt. Before, a `context: fork` skill asked for approval, and a print run refused it.
10
+ An Agent-tool subagent in `auto` mode sent a command allowed by a broad rule like `Bash(npm *)` to
11
+ its classifier instead. A background policy's ceiling is still checked first: nothing outside it
12
+ runs.
13
+
14
+ - `agent-framework` (minor): `createSubagentSession` takes a `commandSandbox` option. The fork and the
15
+ in-process runner derive it from the parent's sandbox, the instance their inherited tools run
16
+ under. `sandboxApprovalFor` is exported.
17
+ - `agent-subagent-runner` (minor): `ISubagentWorkerComposition` takes an optional `createSandbox`. The
18
+ worker builds that sandbox once and hands the same instance to `createTools` and to the session.
19
+ - `agent-cli` (patch): robota's worker composition builds the OS sandbox through `createSandbox`, so
20
+ a child-process subagent approves what its parent approves.
21
+
22
+ - 122e82b: A child-process subagent confines and approves commands with its parent's sandbox settings as they
23
+ stand when it starts. Before, it read its root's settings files, so a `/sandbox` change made in the
24
+ session did not reach it. `/sandbox` changes the live sandbox and only the user settings file, which
25
+ project settings outrank. A worktree child also missed the parent's untracked local settings.
26
+
27
+ - `agent-subagent-runner` (minor): the runner factory takes `parentSandboxSettings`, read at each
28
+ spawn. The start payload carries it, the IPC guard checks it is a record, and the worker hands it to
29
+ `createSandbox` as `parentSettings`.
30
+ - `agent-cli` (patch): robota sends its live sandbox's settings, and a child builds its sandbox from
31
+ them. It refuses settings it cannot read rather than falling back to the files.
32
+
33
+ - 0368058: A running child-process subagent follows a `/sandbox` change made in its parent session. Before, it
34
+ kept the settings it started with until it ended, so a long-running `auto`-mode subagent went on
35
+ auto-approving confined commands after the user turned auto-allow off.
36
+
37
+ - `agent-tools` (minor): `OsSandboxClient.watchSettings(watcher)` reports each `configure`, until
38
+ its returned function is called.
39
+ - `agent-subagent-runner` (minor): the runner factory takes `watchParentSandboxSettings`, and
40
+ forwards each change to every running child as a `sandbox_settings` message. It watches before
41
+ reading the start payload, so no change is lost while a child starts, and stops when the child
42
+ exits or fails to start. A composed sandbox may define `applyParentSettings`. The worker applies
43
+ each change through it. On settings it cannot take, it aborts the run, lets a running command
44
+ finish, and ends the run with that error.
45
+ - `agent-cli` (patch): robota watches its live sandbox, and a child applies each change to the
46
+ instance its tools and approval read.
47
+
48
+ ### Patch Changes
49
+
50
+ - 57280bf: Every published package now declares `"engines": { "node": ">=22.12.0" }`. Before, 27 of the 38
51
+ packages declared no floor (`agent-core`, `agent-tools` and every provider among them),
52
+ `agent-session` and `agent-file-authority` declared `>=20.19.0`, and the other nine declared
53
+ `>=22.0.0`, so a consumer on Node 20 saw at most a warning from a transitive dependency.
54
+
55
+ Why 22.12: `agent-cli` and `agent-ui-terminal` need Node 22 through `ink` 7, and the CommonJS entries
56
+ of `agent-tools` and its dependents, `agent-transport`/`node` and its dependents, and
57
+ `agent-ui-terminal` `require()` ESM-only dependencies (`p-limit`, `jose`, `chalk`), which Node 22
58
+ supports unflagged only from 22.12. `engines` is advisory unless the consumer enables `engine-strict`.
59
+
60
+ No code changes: `tsdown` now reads `node22.12.0` as its build target from the field.
61
+
62
+ - 18c0d5c: Every published package now exports `./package.json`, so `require('<package>/package.json')` and
63
+ `import('<package>/package.json', { with: { type: 'json' } })` work instead of failing with
64
+ `ERR_PACKAGE_PATH_NOT_EXPORTED`, and each tarball now ships the package's `CHANGELOG.md`.
65
+ - Updated dependencies [3c81769]
66
+ - Updated dependencies [724fabb]
67
+ - Updated dependencies [997f2fb]
68
+ - Updated dependencies [bfe8ed5]
69
+ - Updated dependencies [e689c8e]
70
+ - Updated dependencies [4241fc5]
71
+ - Updated dependencies [4f49d14]
72
+ - Updated dependencies [7b72344]
73
+ - Updated dependencies [6ae3f28]
74
+ - Updated dependencies [9721162]
75
+ - Updated dependencies [be0e53c]
76
+ - Updated dependencies [57f57f5]
77
+ - Updated dependencies [ba822c1]
78
+ - Updated dependencies [9721162]
79
+ - Updated dependencies [6e6b06b]
80
+ - Updated dependencies [7d77ce4]
81
+ - Updated dependencies [8bd5fac]
82
+ - Updated dependencies [57280bf]
83
+ - Updated dependencies [5033dd9]
84
+ - Updated dependencies [18c0d5c]
85
+ - Updated dependencies [dbd888d]
86
+ - Updated dependencies [1887e54]
87
+ - Updated dependencies [caaab20]
88
+ - Updated dependencies [f01868f]
89
+ - Updated dependencies [e8779c9]
90
+ - Updated dependencies [5a0ee96]
91
+ - @robota-sdk/agent-framework@3.0.0-beta.83
92
+ - @robota-sdk/agent-core@3.0.0-beta.83
93
+ - @robota-sdk/agent-executor@3.0.0-beta.83
94
+ - @robota-sdk/agent-interface-execution@3.0.0-beta.83
95
+ - @robota-sdk/agent-process@3.0.0-beta.83
96
+
97
+ ## 3.0.0-beta.82
98
+
99
+ ### Patch Changes
100
+
101
+ - Updated dependencies [c7f9203]
102
+ - @robota-sdk/agent-core@3.0.0-beta.82
103
+ - @robota-sdk/agent-framework@3.0.0-beta.82
104
+ - @robota-sdk/agent-executor@3.0.0-beta.82
105
+ - @robota-sdk/agent-interface-execution@3.0.0-beta.82
106
+ - @robota-sdk/agent-process@3.0.0-beta.82
107
+
108
+ ## 3.0.0-beta.81
109
+
110
+ ### Patch Changes
111
+
112
+ - Updated dependencies [3038eb7]
113
+ - Updated dependencies [02b7452]
114
+ - Updated dependencies [ec5e477]
115
+ - Updated dependencies [007fd90]
116
+ - Updated dependencies [18b52cc]
117
+ - Updated dependencies [9843fe6]
118
+ - @robota-sdk/agent-core@3.0.0-beta.81
119
+ - @robota-sdk/agent-framework@3.0.0-beta.81
120
+ - @robota-sdk/agent-executor@3.0.0-beta.81
121
+ - @robota-sdk/agent-interface-execution@3.0.0-beta.81
122
+ - @robota-sdk/agent-process@3.0.0-beta.81
123
+
124
+ ## 3.0.0-beta.80
125
+
126
+ ### Major Changes
127
+
128
+ - 807d161: **BREAKING — ARCH-010: the execution root is a required contract field, and the containment guard now fails closed.**
129
+
130
+ The file-tool containment guard was fail-open: with no root configured it answered "allowed". A tool
131
+ built with no `cwd` therefore had no boundary — measured, a `Read` constructed that way returned the
132
+ contents of `/etc/hostname` — and the child-process subagent worker called `createDefaultTools()` with
133
+ no argument at all, so subagents got exactly that. Three independent auditors found three different
134
+ symptoms of this one missing field.
135
+
136
+ **Removed — seven context-free tool singletons.** `readTool`, `writeTool`, `editTool`, `globTool`,
137
+ `grepTool`, `shellTool`, `bashTool` are gone from `@robota-sdk/agent-tools`. A module-level instance is
138
+ bound at import time and can carry no containment root, so after the guard was inverted they could only
139
+ refuse everything.
140
+
141
+ Migrate to the factory of the same name, passing the directory the tool is allowed to work in:
142
+
143
+ ```ts
144
+ // before
145
+ import { readTool, globTool } from '@robota-sdk/agent-tools';
146
+ const tools = [readTool, globTool];
147
+
148
+ // after
149
+ import { createReadTool, createGlobTool } from '@robota-sdk/agent-tools';
150
+ const cwd = process.cwd(); // or the workspace this agent is scoped to
151
+ const tools = [createReadTool({ cwd }), createGlobTool({ cwd })];
152
+ ```
153
+
154
+ `webFetchTool`, `webSearchTool` and `askUserQuestionTool` are unchanged — they touch no filesystem, so
155
+ there is no root to contain them by.
156
+
157
+ **`cwd` is now REQUIRED** on `ISandboxToolOptions`, `IContainedBuiltinToolOptions` (and everything
158
+ extending them), `ICreateDefaultToolsOptions`, `ISessionOptions` and `ISubagentOptions`. The `= {}`
159
+ default parameter was removed from every builtin factory — that default was the mechanism by which
160
+ "forgot the root" was legal. `new Session({...})` without `cwd` no longer compiles, and also throws at
161
+ construction, because a required field is only required to a TypeScript caller.
162
+
163
+ **`Session` no longer reads `process.cwd()`.** It uses the root it was given, and `getCwd()` exposes it
164
+ so a fork or subagent asks the session instead of re-deriving a root that can disagree with it.
165
+
166
+ **Behavioural change even for callers that already passed a root**: a tool that somehow reaches the
167
+ guard with no root now REFUSES with an explicit error ("no containment root is configured … this is an
168
+ assembly bug, not a path problem") instead of allowing the access.
169
+
170
+ - 0c07176: **BREAKING — ARCH-021: child-process subagents compose the PRODUCT's surface, not imported defaults.**
171
+
172
+ The child-process worker built its surface from `createDefaultProviderDefinitions()` and `createDefaultTools()` — a fixed six-vendor registry and the framework's default tool tier — while the composition root had already handed the runner the fully composed surface and the runner dropped it. So a product's custom providers and pack-contributed tools reached an **in-process** subagent and not a **child-process** one, and ARCH-006's landed invariant "every tool robota runs comes from a pack" was **false in the child**: dropping a pack did not drop its tools.
173
+
174
+ This is the second finding at that line. ARCH-010 — judged BLOCKER, a subagent `Read` returning `/etc/hostname` — patched one argument there and left the reconstruction standing.
175
+
176
+ ```ts
177
+ // the port: what the product composes, stated by the composition root
178
+ export interface ISubagentWorkerComposition {
179
+ createTools(context: { readonly cwd: string }): IToolWithEventService[];
180
+ readonly providerDefinitions: readonly IProviderDefinition[];
181
+ }
182
+
183
+ export function runSubagentWorkerMain(composition: ISubagentWorkerComposition): void;
184
+ ```
185
+
186
+ **Why a recipe and not a broker.** A composition cannot be projected across a process boundary because it is _code_: `createProvider` is a function and a tool carries `execute`. The two sound answers are to proxy the instances or to stop expressing the contract as instances. Proxying loses on containment — a proxied tool executes in the **parent**, bound to the parent's checkout, while a worktree-isolated child's execution root is a different directory — and a prior-art sweep found **no specification that defines a per-call working root for a proxied tool invocation** (MCP roots are session-scoped and pull-based). So the recipe crosses and the child builds an equivalent surface at its own root, which is what every comparable product does.
187
+
188
+ **Per package, classified against each barrel:**
189
+
190
+ - **`agent-subagent-runner` (major)** — `runSubagentWorkerMain` gains a **required** parameter; `ISubagentWorkerComposition` is added to the barrel; `ISubagentWorkerReadyMessage` gains `composedToolNames?`; and the `@robota-sdk/agent-provider-defaults` **dependency edge is removed**.
191
+ - **`agent-cli` (patch)** — composition-root wiring plus one new internal `product/` module; no barrel change.
192
+
193
+ **The structural guarantee reaches one axis, and the document says so.** Deleting the manifest edge makes the **provider** axis a compile error, because that package solely owns `createDefaultProviderDefinitions`. The **tool** axis cannot be cut the same way: `createDefaultTools` is barrel-exported by `agent-framework`, which this package must keep for `createSubagentSession`. That axis is held by a new `harness:scan` check instead — and it is the axis with the failure history, so claiming compile-time enforcement across both would have been an overclaim exactly where it matters. The cause (no defaults-aggregator leaf for the tool surface) is tracked as ARCH-035.
194
+
195
+ **Fail closed on what a recipe cannot reproduce.** A recipe carries anything that is a pure function of (execution root, serialized payload, ambient durable state) — not a live, unrepeatable handle. Today that is `sandboxClient`, and it is reachable with public code (`E2BSandboxClient` and `InMemorySandboxClient` are both on `agent-tools`' barrel). The composition root now **refuses** to select the child-process runner in that case, naming the capability, rather than yielding a sandboxed parent with a host-tool child. Projection is tracked as ARCH-033.
196
+
197
+ **Verified per run, not by construction.** The child declares its composed tool names in `ready`, so the built binary can be asked what it actually composed. Measured on the real artifact: `["Shell","Bash","Read","Write","Edit","Glob","Grep","WebFetch","WebSearch","AskUserQuestion"]` — `pack-coding`'s surface, from the product's own packs.
198
+
199
+ **Also filed rather than folded in:** ARCH-034 (in-process and child-process subagents get different tool surfaces), ARCH-036 (`deps.builtInAgents` is dropped by the child-process path), SEC-009 (`apiKey` rides in the IPC start payload; comparable products use the child's environment).
200
+
201
+ - 4772067: **BREAKING — ARCH-031: the subagent seam is derived from its transport SSOT instead of copied.**
202
+
203
+ One field family — what a subagent job IS — was declared three times as independent shapes and carried
204
+ between them by six hand-written object literals that nothing checked for totality. A field added to
205
+ either side had to be hand-copied at every hop, and a miss compiled clean as a silent no-op. TYPE-003
206
+ named this cause and derived one hop; the next two changes each dropped a field at a hop it had skipped
207
+ (CORE-025's permission policy, and ANALYTICS-001's `usage`, dropped in the very commit that added it).
208
+
209
+ ```ts
210
+ // now, in @robota-sdk/agent-interface-transport
211
+ export type ISubagentSpawnRequest = Omit<IAgentBackgroundTaskRequest, 'kind'>;
212
+ export type ISubagentJobResult = Omit<IBackgroundTaskResult, 'kind' | 'exitCode' | 'signalCode'>;
213
+ ```
214
+
215
+ All four projections collapse to spreads. `parentTaskId` and `providerProfile` now reach the runner
216
+ because they exist on the source, not because someone remembered them.
217
+
218
+ **Per package, classified against each barrel:**
219
+
220
+ - **`agent-executor` (major)** — the barrel loses `ISubagentSpawnRequest` and `ISubagentJobResult` (they
221
+ moved to their owner; re-publishing them here would be a pass-through re-export). `ISubagentJobStart`
222
+ and `ISubagentJobHandle` rename `jobId` → `taskId`, `ISubagentJobStart` gains `worktree?`, and
223
+ `ISubagentWorktreePrepareRequest` renames `jobId` → `taskId`.
224
+ - **`agent-framework` (major)** — the barrel loses eleven type-only re-exports of `agent-executor`-owned
225
+ types. They carried zero runtime values, so they bought none of the assembly convenience a runtime
226
+ facade exists for, while making one field family look like it had three owners. Separately,
227
+ `ISpawnAgentTaskRequest.permissionPolicy` goes optional → **required**.
228
+ - **`agent-subagent-runner` (major)** — `ISubagentWorkerStartPayload` renames `jobId` → `taskId` and gains
229
+ `worktree?`. This package is not in the item's declared `area:`; the audit that caught it is the reason
230
+ it is here.
231
+ - **`agent-interface-transport` (minor)** — two new barrel exports; nothing removed or renamed.
232
+ - **`agent-core` (minor)** — **two** new barrel exports. `DEFAULT_BACKGROUND_PERMISSION_POLICY` is the
233
+ intended one; collapsing the hand-listed permissions block to `export *` also surfaced
234
+ `clearRegisteredToolArgumentKeys`, which the old list had omitted. It is documented as public rather
235
+ than re-narrowed — a barrel that cannot fall out of step with its owner is the point of the collapse.
236
+ Nothing was removed: all nine previously-listed permission types remain on the barrel.
237
+ - **`agent-cli` (patch)** — migrated as the only in-repo implementer of `ISubagentWorktreeAdapter`; no
238
+ barrel change.
239
+
240
+ **`permissionPolicy` is now required at the spawn boundary**, and its default is one exported constant
241
+ owned by the permission SSOT. It was previously applied as `?? 'inherit-allowlist'` in the middle of a
242
+ projection, in **two** packages independently, with nothing keeping them equal — a security-relevant value
243
+ whose default was declared twice. Every spawn site now states its own policy.
244
+
245
+ **The worktree identity moved to the runner envelope.** It is runner-produced — the worktree does not
246
+ exist when a caller builds a request — so it rides on `ISubagentJobStart.worktree` and crosses the IPC
247
+ boundary there. The runner no longer also rewrites `request.cwd`, which had given ARCH-010's execution-root
248
+ rule two carriers that could disagree. `branchName` **relocated rather than being deleted**: it has no
249
+ reader in this repository today, and for a library that is not a reason to drop a legitimate contract.
250
+
251
+ **Renames are consistent across the SPI** (`type` → `agentType`, `jobId` → `taskId`) rather than applied to
252
+ one shape, which would have left two names for one identifier in a single file. The IPC validator's
253
+ string-literal keys are now typed against the contract, so the next rename is a compile error instead of a
254
+ runtime rejection of every start payload.
255
+
256
+ - 6fab98f: **BREAKING — DIST-006: the built `robota` binary could not spawn a subagent at all.**
257
+
258
+ `/agent run` failed on every distributed build with `Subagent worker exited before result: exit code 1`. The child's real stderr was `Cannot find module '…/agent-cli/dist/node/child-process-subagent-worker.js'`. `getDefaultSubagentWorkerPath()` resolved the worker relative to its own `import.meta.url`; INFRA-028 bundles every workspace package into `agent-cli/dist/node/bin.js`, so at runtime that directory is **agent-cli's** dist, where the worker was never emitted. It worked from source, which is why nothing caught it.
259
+
260
+ **Second occurrence of one cause.** `agent-subagent-runner/tsdown.config.ts` already carried a comment naming this exact failure: _"Without this entry the file never existed, so the child-process subagent silently failed from any dist build."_ That fix put the worker next to its OWN package's bundle; bundling then moved the resolver's notion of "next to me" one package along.
261
+
262
+ **The defect was the function, not the missing file.** `getDefaultSubagentWorkerPath()` answered _"where is my worker file on disk?"_ from a library that cannot know — the answer is a property of the packaging step. Emitting the file where the resolver looks would have fixed **one of three shipped artifacts**: the npm bundle, but not the Bun single-file binaries published on every tag, nor the Electron desktop sidecar that embeds them. A compiled single-file executable has no sibling directory to emit into.
263
+
264
+ ```ts
265
+ // removed — a question no library can answer
266
+ export function getDefaultSubagentWorkerPath(): string;
267
+
268
+ // now: the composition root states how to start a copy of ITSELF
269
+ export interface ISubagentWorkerEntry {
270
+ readonly execPath: string;
271
+ readonly args: readonly string[];
272
+ readonly execArgv?: readonly string[];
273
+ }
274
+ ```
275
+
276
+ `IChildProcessSubagentRunnerOptions.workerPath` → **`workerEntry`**, and the runner `spawn`s `execPath args… --__robota-subagent-worker` instead of forking a module path. `robota`'s own entry enters worker mode through the new `runSubagentWorkerMain()`, so **there is no second artifact and no path to get wrong**. The one seam satisfies all three shapes: a bundled Node build names the file it is executing, a `tsx` source run names the same and adds `--import tsx`, and a compiled binary names _nothing_ — `process.execPath` is the binary, and re-executing it re-enters its embedded entry.
277
+
278
+ **Per package, classified against each barrel:**
279
+
280
+ - **`agent-subagent-runner` (major)** — the barrel loses `getDefaultSubagentWorkerPath` (deleted, not renamed) and gains `SUBAGENT_WORKER_MODE_FLAG`, `isSubagentWorkerModeArgv`, `runSubagentWorkerMain`, `ISubagentWorkerEntry`. `IChildProcessSubagentRunnerOptions` renames `workerPath` → `workerEntry` and drops `execArgv` — it now has exactly one owner, on the entry descriptor. The separate `child-process-subagent-worker` bundle entry is gone.
281
+ - **`agent-cli` (patch)** — composition-root wiring only; no barrel change.
282
+
283
+ **Two things this also repairs, both found in review:**
284
+
285
+ - **The child's stderr was discarded** (`stdio: [..., 'ignore', 'ipc']`), so a worker that died before its first IPC message reported only an exit code. That is why occurrence #2 had to be diagnosed by hand. It is now captured, bounded, and appended to the error, making the next occurrence self-reporting.
286
+ - **A source run executed the BUILT worker, not the source worker**, because package `exports` resolve to `dist`. `resolveExecArgv`'s `--import tsx` branch was therefore dead code. Self-fork names the entry actually running, so source runs finally run source.
287
+
288
+ **Verified against the artifacts, not from source:** the built `dist/node/bin.js` and a real `bun --compile` single-file binary each complete the worker IPC handshake (`{type:'ready'}`), each refuse a hand-typed flag with no IPC channel (exit 2, "Silence is not success" — measured on both), and the shipped bundle no longer contains the string `child-process-subagent-worker.js` — there is nothing left to look for.
289
+
290
+ ### Minor Changes
291
+
292
+ - 9c19c50: `/fork [name] [--same-dir]` copies the live conversation into a background session.
293
+
294
+ The session writes a copy of its own record under a fresh id — messages, system prompt, tool schemas
295
+ and full history, and deliberately not the sandbox snapshot, goal, plan or branch — then spawns a
296
+ background job carrying only `resumeSessionId`. The child restores that record itself, so no
297
+ conversation crosses the child-process boundary and the worker start payload's key set is unchanged.
298
+ The background panel gains an `attach` control that switches the terminal onto the forked session; it
299
+ is a view switch, never a merge, and a missing record or a terminal task is refused with the task's
300
+ own status.
301
+
302
+ **`@robota-sdk/agent-framework` is `major` for one reason: `ICommandHostSessionAccess` gains a
303
+ required member.** `forkSession({ name? })` is not optional, so an external implementation of that
304
+ role port stops compiling until it adds the method. Every other change in this set is additive:
305
+
306
+ - `agent-interface-execution` — `TExecutionControl` gains `'attach'`.
307
+ - `agent-interface-command` — `TCommandUiIntent` gains `{ type: 'switch-session'; sessionId }`.
308
+ - `agent-subagent-runner` — `ISubagentWorkerComposition` gains the optional `openSessionStore`, and
309
+ the worker resumes a record when the job names one. A composition that registers no store and
310
+ receives no `resumeSessionId` behaves exactly as before.
311
+ - `agent-framework` also gains the fork-record builder, `SessionTurnMemory`, and
312
+ `IAgentBackgroundTaskRequest.resumeSessionId?`; `loadSessionRecord` now returns
313
+ `restoredSystemPrompt`, which makes a record field that was written and never read take effect on
314
+ restore.
315
+ - `agent-executor`, `agent-command`, `agent-transport-tui`, `agent-cli` — the spawn input, the
316
+ `/fork` module and the attach control that carry it to the surface.
317
+
318
+ - 1698be4: A child-process subagent can no longer send the parent's provider credential to a different
319
+ endpoint.
320
+
321
+ - **Before spawning a child**, the parent compares every environment variable that decides where
322
+ the provider connects or which credential it sends. If the child's environment differs, the job
323
+ is refused before the credential leaves the parent. The error names the variable, never its
324
+ value. The variables compared are:
325
+ - the proxy and TLS variables;
326
+ - the variables the provider's SDK reads, such as `OPENAI_BASE_URL`, `ANTHROPIC_AUTH_TOKEN` and
327
+ the Vertex settings;
328
+ - the credential's own variable.
329
+ - **The child** repeats the check before it builds its provider. It builds that provider from the
330
+ parent's effective connection exactly: it no longer fills in a base URL, options or a default
331
+ credential from its own registry, and a credential reference that resolves to nothing is refused.
332
+ - **Where the effective connection comes from:** the parent applies its own definition defaults
333
+ (base URL, options). `profileName` is sent only when it names the connection actually sent.
334
+ - **New contracts:**
335
+ - `IProviderDefinition.destinationEnvironment`, declared by every built-in provider.
336
+ - `createProviderFromExactProfile`, `connectionEnvironmentNames`,
337
+ `findConnectionEnvironmentDivergence`, `sealConnectionEnvironment`,
338
+ `verifyConnectionEnvironment` and `TRANSPORT_ENVIRONMENT`.
339
+ - The start payload's `connectionCheck`.
340
+ - The child-process runner's `providerDefinitions` option, now required: a provider with no
341
+ definition there is refused, because its connection cannot be checked.
342
+
343
+ - 7937c19: Split the `@robota-sdk/agent-provider` monolith into SDK-aligned leaf packages (ARCH-PROVIDER-002 Stage A). The single package that hard-bundled all three vendor SDKs (`@anthropic-ai/sdk`, `openai`, `@google/genai`) is **removed** and replaced by per-vendor leaves, each depending only on `@robota-sdk/agent-core` + its one SDK: `@robota-sdk/agent-provider-anthropic`, `@robota-sdk/agent-provider-openai`, `@robota-sdk/agent-provider-openai-compatible` (DeepSeek/Qwen/Gemma over the shared OpenAI-compatible base), `@robota-sdk/agent-provider-gemini` (+ a `./google` entry), and `@robota-sdk/agent-provider-bytedance` (media/video `IVideoGenerationProvider`). The aggregated `createDefaultProviderDefinitions()` now lives in the new `@robota-sdk/agent-builtin-providers` leaf.
344
+
345
+ Migration: replace `@robota-sdk/agent-provider/<vendor>` imports with the corresponding `@robota-sdk/agent-provider-<vendor>` package (`/deepseek`, `/qwen`, `/gemma` → `@robota-sdk/agent-provider-openai-compatible`; `/google` → `@robota-sdk/agent-provider-gemini/google`), and import `createDefaultProviderDefinitions` from `@robota-sdk/agent-builtin-providers`. Consumers now pull only the vendor SDK(s) they actually use.
346
+
347
+ - c6c56a6: Move the concrete `GitWorktreeIsolationAdapter` (git CLI + filesystem I/O) out of the reusable
348
+ `@robota-sdk/agent-executor` runtime-primitives package into the `@robota-sdk/agent-cli` composition
349
+ root, restoring the executor's "creates no Git worktrees" boundary (ARL-02 / ARCH-FIX-024, INFRA-031).
350
+
351
+ **Breaking (`@robota-sdk/agent-subagent-runner`):** `worktreeAdapter` is now a **required** option on
352
+ `createChildProcessSubagentRunnerFactory` / `IChildProcessSubagentRunnerOptions`. The concrete git
353
+ default (`createGitWorktreeIsolationAdapter()`) has been removed — inject the adapter at the composition
354
+ root. `@robota-sdk/agent-executor` no longer exports `GitWorktreeIsolationAdapter`,
355
+ `createGitWorktreeIsolationAdapter`, or `IGitWorktreeIsolationAdapterOptions` (the
356
+ `ISubagentWorktreeAdapter` port and `WorktreeSubagentRunner` remain). CLI runtime behavior is unchanged.
357
+
358
+ ### Patch Changes
359
+
360
+ - f336838: One permission evaluation order for every caller. The interactive session, background tasks and
361
+ subagents used to run two different resolvers, so the same call could be decided differently
362
+ depending on who made it. They now share `evaluatePermission`, and a background policy only adds a
363
+ ceiling, an ask-everything flag and the task's own lists to it:
364
+
365
+ deny → caller ceiling → unevaluable deny (ask) → never-auto-approve set (ask) → ask-everything →
366
+ bypassPermissions → allow → mode.
367
+
368
+ - **`ask` rules.** `permissions.ask` patterns always ask, in every mode including
369
+ `bypassPermissions`. They are matched per command like a deny rule, and are validated at
370
+ construction alongside `allow` and `deny`.
371
+ - **Never auto-approved, bypass included:** removing a critical path with `rm`/`rmdir` (the root, a
372
+ top-level directory, home, the working directory or a parent), and a modify-class write into
373
+ `.git`, `.robota`, `.claude`, `.agents`, `.mcp.json`, `.gitconfig`, `.npmrc` or a shell rc file.
374
+ Files inside an isolated worktree (`.robota/worktrees/<name>/…`) are ordinary files. With no
375
+ approver attached, an ask is a denial.
376
+ - **A ceiling is checked before bypass and before any ask.** A subagent's `inherit-allowlist` ceiling
377
+ is now the parent's _effective_ rules, read live at spawn: settings, preset lists and command
378
+ auto-allows. It used to be the raw settings file. An unevaluable deny under a policy now asks,
379
+ like everywhere else, where it used to deny outright; with no approver it is still a denial.
380
+ - **Settings layers union `permissions.allow`**, as they already did `deny`. A checked-in project
381
+ file no longer silently discards the user's allow list.
382
+ - **Print mode, `createQuery()` and headless sessions default to `default` mode**, not
383
+ `bypassPermissions`. They have no approver, so a call that would ask is denied. Pass
384
+ `--permission-mode` / `permissionMode: 'bypassPermissions'` explicitly for unattended runs.
385
+
386
+ **Breaking:**
387
+ - `@robota-sdk/agent-core` removes `resolvePermissionByPolicy` and `TPermissionPolicyDecision` in
388
+ favour of `projectPermissionPolicy` plus `evaluatePermission`'s new `context` argument.
389
+ - `@robota-sdk/agent-framework` changes the settings merge rule for `permissions.allow`, and the
390
+ default permission mode of `createQuery()` and headless sessions.
391
+
392
+ - 4f3c075: Assemble complete, verified package generations before switching build output; preserve the previous generation on build failure and pack only verified regular-file images. Include copied CLI web assets in affected-build ordering and artifact transfer. Preserve the CLI version in managed build paths. Public runtime contracts remain compatible (patch).
393
+ - Updated dependencies [9c19c50]
394
+ - Updated dependencies [7b6234c]
395
+ - Updated dependencies [5307f8a]
396
+ - Updated dependencies [b462ee7]
397
+ - Updated dependencies [08a9bd6]
398
+ - Updated dependencies [818f0c8]
399
+ - Updated dependencies [4eea54b]
400
+ - Updated dependencies [30e5e50]
401
+ - Updated dependencies [bb4696a]
402
+ - Updated dependencies [1698be4]
403
+ - Updated dependencies [9368d00]
404
+ - Updated dependencies [d4189b9]
405
+ - Updated dependencies [9edae52]
406
+ - Updated dependencies [4078a72]
407
+ - Updated dependencies [4c73a0b]
408
+ - Updated dependencies [af2f2ad]
409
+ - Updated dependencies [267af5f]
410
+ - Updated dependencies [196a900]
411
+ - Updated dependencies [f336838]
412
+ - Updated dependencies [34e50f0]
413
+ - Updated dependencies [722e88a]
414
+ - Updated dependencies [a5cc36e]
415
+ - Updated dependencies [d23c848]
416
+ - Updated dependencies [b70fa3d]
417
+ - Updated dependencies [2711ec6]
418
+ - Updated dependencies [4dd45cc]
419
+ - Updated dependencies [4c5148e]
420
+ - Updated dependencies [37af5dc]
421
+ - Updated dependencies [807d161]
422
+ - Updated dependencies [fec722f]
423
+ - Updated dependencies [e82215f]
424
+ - Updated dependencies [52b7346]
425
+ - Updated dependencies [2ebff01]
426
+ - Updated dependencies [2ebff01]
427
+ - Updated dependencies [2d3b2c0]
428
+ - Updated dependencies [b078afa]
429
+ - Updated dependencies [2d3b2c0]
430
+ - Updated dependencies [baa6863]
431
+ - Updated dependencies [2d3b2c0]
432
+ - Updated dependencies [3a8876b]
433
+ - Updated dependencies [4772067]
434
+ - Updated dependencies [7b85767]
435
+ - Updated dependencies [0f98419]
436
+ - Updated dependencies [64ba748]
437
+ - Updated dependencies [9fbab1b]
438
+ - Updated dependencies [d312755]
439
+ - Updated dependencies [a009f5b]
440
+ - Updated dependencies [1e3f91a]
441
+ - Updated dependencies [4f3c075]
442
+ - Updated dependencies [475e085]
443
+ - Updated dependencies [e477440]
444
+ - Updated dependencies [9dcb5da]
445
+ - Updated dependencies [a95ca85]
446
+ - Updated dependencies [b6d14ce]
447
+ - Updated dependencies [0382a51]
448
+ - Updated dependencies [93d061d]
449
+ - Updated dependencies [39554a1]
450
+ - Updated dependencies [d28430a]
451
+ - Updated dependencies [bed26ea]
452
+ - Updated dependencies [fe48835]
453
+ - Updated dependencies [1e40b5b]
454
+ - Updated dependencies [c6c56a6]
455
+ - Updated dependencies [4b76cfa]
456
+ - Updated dependencies [d9bd9ec]
457
+ - Updated dependencies [8865acf]
458
+ - Updated dependencies [90e7a10]
459
+ - Updated dependencies [fcb0da3]
460
+ - Updated dependencies [07b627f]
461
+ - Updated dependencies [d0de5b2]
462
+ - Updated dependencies [9665c6e]
463
+ - Updated dependencies [44393be]
464
+ - Updated dependencies [c7fa299]
465
+ - Updated dependencies [5134b3b]
466
+ - Updated dependencies [dd444c1]
467
+ - Updated dependencies [1f57e7f]
468
+ - Updated dependencies [833afe1]
469
+ - Updated dependencies [d6b9404]
470
+ - Updated dependencies [7863b16]
471
+ - Updated dependencies [fde558e]
472
+ - Updated dependencies [db5c439]
473
+ - Updated dependencies [4a01a87]
474
+ - Updated dependencies [cbee54e]
475
+ - Updated dependencies [9814afc]
476
+ - Updated dependencies [242a644]
477
+ - @robota-sdk/agent-interface-execution@3.0.0-beta.80
478
+ - @robota-sdk/agent-framework@3.0.0-beta.80
479
+ - @robota-sdk/agent-executor@3.0.0-beta.80
480
+ - @robota-sdk/agent-core@3.0.0-beta.80
481
+ - @robota-sdk/agent-process@3.0.0-beta.80
482
+
483
+ ## 3.0.0-beta.79
484
+
485
+ ### Patch Changes
486
+
487
+ - @robota-sdk/agent-core@3.0.0-beta.79
488
+ - @robota-sdk/agent-executor@3.0.0-beta.79
489
+ - @robota-sdk/agent-framework@3.0.0-beta.79
490
+ - @robota-sdk/agent-interface-transport@3.0.0-beta.79
491
+ - @robota-sdk/agent-provider@3.0.0-beta.79
492
+
493
+ ## 3.0.0-beta.78
494
+
495
+ ### Patch Changes
496
+
497
+ - Updated dependencies [6f308d1]
498
+ - @robota-sdk/agent-core@3.0.0-beta.78
499
+ - @robota-sdk/agent-provider@3.0.0-beta.78
500
+ - @robota-sdk/agent-executor@3.0.0-beta.78
501
+ - @robota-sdk/agent-framework@3.0.0-beta.78
502
+ - @robota-sdk/agent-interface-transport@3.0.0-beta.78
503
+
504
+ ## 3.0.0-beta.77
505
+
506
+ ### Patch Changes
507
+
508
+ - Updated dependencies
509
+ - @robota-sdk/agent-core@3.0.0-beta.77
510
+ - @robota-sdk/agent-process@3.0.0-beta.77
511
+ - @robota-sdk/agent-executor@3.0.0-beta.77
512
+ - @robota-sdk/agent-framework@3.0.0-beta.77
513
+ - @robota-sdk/agent-interface-transport@3.0.0-beta.77
514
+ - @robota-sdk/agent-provider@3.0.0-beta.77
515
+
516
+ ## 3.0.0-beta.76
517
+
518
+ ### Patch Changes
519
+
520
+ - Updated dependencies
521
+ - Updated dependencies [c0a6287]
522
+ - Updated dependencies [9df3a88]
523
+ - Updated dependencies
524
+ - Updated dependencies
525
+ - Updated dependencies [576af62]
526
+ - @robota-sdk/agent-core@3.0.0-beta.76
527
+ - @robota-sdk/agent-framework@3.0.0-beta.76
528
+ - @robota-sdk/agent-provider@3.0.0-beta.76
529
+ - @robota-sdk/agent-executor@3.0.0-beta.76
530
+
531
+ ## 3.0.0-beta.75
532
+
533
+ ### Patch Changes
534
+
535
+ - Updated dependencies
536
+ - @robota-sdk/agent-framework@3.0.0-beta.75
537
+ - @robota-sdk/agent-core@3.0.0-beta.75
538
+ - @robota-sdk/agent-executor@3.0.0-beta.75
539
+ - @robota-sdk/agent-provider@3.0.0-beta.75
540
+
541
+ ## 3.0.0-beta.74
542
+
543
+ ### Patch Changes
544
+
545
+ - Updated dependencies
546
+ - @robota-sdk/agent-framework@3.0.0-beta.74
547
+ - @robota-sdk/agent-core@3.0.0-beta.74
548
+ - @robota-sdk/agent-executor@3.0.0-beta.74
549
+ - @robota-sdk/agent-provider@3.0.0-beta.74
550
+
551
+ ## 3.0.0-beta.73
552
+
553
+ ### Patch Changes
554
+
555
+ - @robota-sdk/agent-core@3.0.0-beta.73
556
+ - @robota-sdk/agent-executor@3.0.0-beta.73
557
+ - @robota-sdk/agent-framework@3.0.0-beta.73
558
+ - @robota-sdk/agent-provider@3.0.0-beta.73
559
+
560
+ ## 3.0.0-beta.72
561
+
562
+ ### Patch Changes
563
+
564
+ - Updated dependencies
565
+ - @robota-sdk/agent-framework@3.0.0-beta.72
566
+ - @robota-sdk/agent-core@3.0.0-beta.72
567
+ - @robota-sdk/agent-executor@3.0.0-beta.72
568
+ - @robota-sdk/agent-provider@3.0.0-beta.72
569
+
570
+ ## 3.0.0-beta.71
571
+
572
+ ### Patch Changes
573
+
574
+ - fix(context): unify token estimation to single SSOT — status bar and /context list now use the same serialized JSON estimate
575
+ - Updated dependencies
576
+ - @robota-sdk/agent-core@3.0.0-beta.71
577
+ - @robota-sdk/agent-executor@3.0.0-beta.71
578
+ - @robota-sdk/agent-framework@3.0.0-beta.71
579
+ - @robota-sdk/agent-provider@3.0.0-beta.71
580
+
581
+ ## 3.0.0-beta.70
582
+
583
+ ### Patch Changes
584
+
585
+ - Updated dependencies
586
+ - @robota-sdk/agent-framework@3.0.0-beta.70
587
+ - @robota-sdk/agent-core@3.0.0-beta.70
588
+ - @robota-sdk/agent-executor@3.0.0-beta.70
589
+ - @robota-sdk/agent-provider@3.0.0-beta.70
590
+
591
+ ## 3.0.0-beta.69
592
+
593
+ ### Patch Changes
594
+
595
+ - Updated dependencies
596
+ - @robota-sdk/agent-framework@3.0.0-beta.69
597
+ - @robota-sdk/agent-core@3.0.0-beta.69
598
+ - @robota-sdk/agent-executor@3.0.0-beta.69
599
+ - @robota-sdk/agent-provider@3.0.0-beta.69
600
+
601
+ ## 3.0.0-beta.68
602
+
603
+ ### Patch Changes
604
+
605
+ - @robota-sdk/agent-core@3.0.0-beta.68
606
+ - @robota-sdk/agent-executor@3.0.0-beta.68
607
+ - @robota-sdk/agent-framework@3.0.0-beta.68
608
+ - @robota-sdk/agent-provider@3.0.0-beta.68
609
+
610
+ ## 3.0.0-beta.67
611
+
612
+ ### Patch Changes
613
+
614
+ - CLIR: agent-cli layer separation, agent-framework interactive session improvements, subagent runner fix, TUI interface README
615
+ - Updated dependencies
616
+ - @robota-sdk/agent-framework@3.0.0-beta.67
617
+ - @robota-sdk/agent-core@3.0.0-beta.67
618
+ - @robota-sdk/agent-executor@3.0.0-beta.67
619
+ - @robota-sdk/agent-provider@3.0.0-beta.67
620
+
621
+ ## 3.0.0-beta.66
622
+
623
+ ### Patch Changes
624
+
625
+ - Updated dependencies
626
+ - @robota-sdk/agent-framework@3.0.0-beta.66
627
+ - @robota-sdk/agent-core@3.0.0-beta.66
628
+ - @robota-sdk/agent-executor@3.0.0-beta.66
629
+ - @robota-sdk/agent-provider@3.0.0-beta.66