@sema-agent/core 7.14.0 → 7.16.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.
Files changed (136) hide show
  1. package/CHANGELOG.md +59 -0
  2. package/dist/core/ask-origin.d.ts +2 -2
  3. package/dist/core/checkpoint-store.d.ts +14 -15
  4. package/dist/core/governance-codes.js +2 -0
  5. package/dist/core/hooks.d.ts +4 -3
  6. package/dist/core/memory-engine/delegation-settlement.d.ts +37 -12
  7. package/dist/core/memory-engine/delegation-settlement.js +128 -39
  8. package/dist/core/memory-engine/engine.d.ts +9 -8
  9. package/dist/core/memory-engine/engine.js +115 -120
  10. package/dist/core/memory-engine/file-backend.d.ts +17 -5
  11. package/dist/core/memory-engine/file-backend.js +78 -34
  12. package/dist/core/memory-engine/index.d.ts +2 -2
  13. package/dist/core/memory-engine/index.js +2 -2
  14. package/dist/core/memory-engine/layout.d.ts +152 -54
  15. package/dist/core/memory-engine/layout.js +441 -104
  16. package/dist/core/memory-engine/types.d.ts +8 -3
  17. package/dist/core/memory-engine/types.js +5 -0
  18. package/dist/core/runner/abort-race.d.ts +3 -3
  19. package/dist/core/runner/active-skill-scope.d.ts +2 -2
  20. package/dist/core/runner/assemble-result.d.ts +29 -29
  21. package/dist/core/runner/checkpoint-scope.d.ts +4 -4
  22. package/dist/core/runner/clock-and-limits.d.ts +3 -3
  23. package/dist/core/runner/compaction-call-options.d.ts +11 -11
  24. package/dist/core/runner/compaction-knobs.d.ts +4 -4
  25. package/dist/core/runner/compaction-seams.d.ts +5 -5
  26. package/dist/core/runner/contracts.d.ts +224 -226
  27. package/dist/core/runner/decide-continuation.d.ts +6 -6
  28. package/dist/core/runner/denial-limit-arms.d.ts +8 -8
  29. package/dist/core/runner/derived-route-fallback.d.ts +2 -2
  30. package/dist/core/runner/gate-exit.d.ts +6 -6
  31. package/dist/core/runner/git-status-frame.d.ts +7 -7
  32. package/dist/core/runner/inherited-ask-grants.d.ts +6 -6
  33. package/dist/core/runner/memory-capture-optout.d.ts +1 -1
  34. package/dist/core/runner/memory-consolidation-driver.d.ts +4 -4
  35. package/dist/core/runner/memory-consolidation.d.ts +6 -6
  36. package/dist/core/runner/park-commit.d.ts +6 -6
  37. package/dist/core/runner/permission-rule-lanes.d.ts +22 -20
  38. package/dist/core/runner/permission-rule-lanes.js +1 -1
  39. package/dist/core/runner/prepare-acquire-reconcile.d.ts +4 -4
  40. package/dist/core/runner/prepare-ask-lane.d.ts +3 -3
  41. package/dist/core/runner/prepare-boundary-parks.d.ts +3 -3
  42. package/dist/core/runner/prepare-caps-and-workflow.d.ts +5 -5
  43. package/dist/core/runner/prepare-config-doors.d.ts +21 -21
  44. package/dist/core/runner/prepare-context-lane.d.ts +6 -6
  45. package/dist/core/runner/prepare-defer-classify.d.ts +3 -3
  46. package/dist/core/runner/prepare-defer-classify.js +12 -10
  47. package/dist/core/runner/prepare-delegation-surface.d.ts +1 -1
  48. package/dist/core/runner/prepare-file-history.d.ts +2 -2
  49. package/dist/core/runner/prepare-gate-stations.d.ts +8 -9
  50. package/dist/core/runner/prepare-gate-stations.js +2 -2
  51. package/dist/core/runner/prepare-hands-readface.d.ts +41 -41
  52. package/dist/core/runner/prepare-hands-readface.js +27 -29
  53. package/dist/core/runner/prepare-inherited-gate.d.ts +6 -6
  54. package/dist/core/runner/prepare-listings.d.ts +3 -3
  55. package/dist/core/runner/prepare-lsp.d.ts +3 -3
  56. package/dist/core/runner/prepare-memory-engine-session.d.ts +5 -5
  57. package/dist/core/runner/prepare-memory.js +6 -7
  58. package/dist/core/runner/prepare-offload-wrappers.d.ts +2 -2
  59. package/dist/core/runner/prepare-park-ask.d.ts +11 -12
  60. package/dist/core/runner/prepare-park-ask.js +3 -3
  61. package/dist/core/runner/prepare-policy-chain.d.ts +6 -6
  62. package/dist/core/runner/prepare-policy-chain.js +2 -2
  63. package/dist/core/runner/prepare-prompt-inputs.d.ts +5 -5
  64. package/dist/core/runner/prepare-protocol-tools.d.ts +1 -1
  65. package/dist/core/runner/prepare-question-face.d.ts +4 -4
  66. package/dist/core/runner/prepare-run-refs.d.ts +11 -11
  67. package/dist/core/runner/prepare-safety-scan.d.ts +1 -1
  68. package/dist/core/runner/prepare-suspend-saga.d.ts +4 -4
  69. package/dist/core/runner/prepare-task.d.ts +12 -12
  70. package/dist/core/runner/prepare-task.js +5 -7
  71. package/dist/core/runner/prepare-tool-disclosure-mount.d.ts +2 -3
  72. package/dist/core/runner/prepare-wiring-manifest.d.ts +4 -4
  73. package/dist/core/runner/prepare-workspace-restore.d.ts +1 -1
  74. package/dist/core/runner/remote-env-retry.d.ts +3 -3
  75. package/dist/core/runner/resume-admission.d.ts +1 -1
  76. package/dist/core/runner/resume-claim.d.ts +1 -1
  77. package/dist/core/runner/resume-internals-and-config.d.ts +1 -1
  78. package/dist/core/runner/resume-policy-outcome.d.ts +1 -1
  79. package/dist/core/runner/resume-preflight.d.ts +1 -1
  80. package/dist/core/runner/resume-review-outcome.d.ts +1 -1
  81. package/dist/core/runner/run-brain-sinks.d.ts +1 -1
  82. package/dist/core/runner/run-clock-and-content.d.ts +4 -4
  83. package/dist/core/runner/run-compaction-machinery.d.ts +3 -3
  84. package/dist/core/runner/run-git-lane.d.ts +1 -1
  85. package/dist/core/runner/run-harness-handlers.d.ts +2 -2
  86. package/dist/core/runner/run-identity-wiring.d.ts +4 -4
  87. package/dist/core/runner/run-leg.d.ts +3 -3
  88. package/dist/core/runner/run-notification-lane.d.ts +2 -2
  89. package/dist/core/runner/run-reasoning-seat.d.ts +2 -2
  90. package/dist/core/runner/run-settle-and-teardown.d.ts +4 -4
  91. package/dist/core/runner/run-telemetry-and-budget-seats.d.ts +2 -2
  92. package/dist/core/runner/run-terminal-adoption.d.ts +5 -5
  93. package/dist/core/runner/runtask.d.ts +14 -14
  94. package/dist/core/runner/session-file-state-replay.d.ts +3 -3
  95. package/dist/core/runner/session-rule-policy.d.ts +2 -2
  96. package/dist/core/runner/steer-admission.d.ts +2 -2
  97. package/dist/core/runner/stream-halt-verbs.d.ts +1 -1
  98. package/dist/core/runner/stream-reap.d.ts +1 -1
  99. package/dist/core/runner/synthetic-tools.d.ts +8 -8
  100. package/dist/core/runner/teardown-bounded.d.ts +2 -2
  101. package/dist/core/runner/tool-defer-gate.d.ts +86 -0
  102. package/dist/core/runner/tool-defer-gate.js +57 -0
  103. package/dist/core/runner/tool-disclosure.d.ts +33 -69
  104. package/dist/core/runner/tool-disclosure.js +0 -43
  105. package/dist/core/runner/tool-end-body.d.ts +3 -3
  106. package/dist/core/runner/tool-face-overlay.d.ts +2 -2
  107. package/dist/core/runner/tool-output-projection.d.ts +2 -2
  108. package/dist/core/runner/turn-attachments.d.ts +53 -53
  109. package/dist/core/runner/usage-accounting.d.ts +4 -4
  110. package/dist/core/runner/workspace-path.d.ts +1 -1
  111. package/dist/core/runner-deps.d.ts +16 -9
  112. package/dist/core/task-spec.d.ts +8 -2
  113. package/dist/core/tool-spec.d.ts +7 -4
  114. package/dist/core/types.d.ts +1 -1
  115. package/dist/engine/llm/types.d.ts +1 -1
  116. package/dist/index.d.ts +4 -4
  117. package/dist/index.js +3 -3
  118. package/dist/tools/fs/bash-readonly-classifier.d.ts +40 -40
  119. package/dist/tools/fs/encoding.d.ts +31 -40
  120. package/dist/tools/fs/fs-bash.d.ts +76 -35
  121. package/dist/tools/fs/fs-bash.js +86 -29
  122. package/dist/tools/fs/fs-pdf.d.ts +8 -8
  123. package/dist/tools/fs/fs-search-tools.d.ts +4 -4
  124. package/dist/tools/fs/fs-shared.d.ts +144 -158
  125. package/dist/tools/fs/fs-write.d.ts +8 -8
  126. package/dist/tools/fs/gh-rate-limit.d.ts +13 -14
  127. package/dist/tools/fs/index.d.ts +74 -78
  128. package/dist/tools/fs/notebook.d.ts +24 -25
  129. package/dist/tools/fs/pdf.d.ts +3 -3
  130. package/dist/tools/fs/read-deny.d.ts +22 -22
  131. package/dist/tools/fs/read-face.d.ts +21 -24
  132. package/dist/tools/fs/repo-map.d.ts +8 -8
  133. package/dist/tools/fs/safety.d.ts +116 -129
  134. package/dist/tools/fs/search.d.ts +63 -71
  135. package/package.json +5 -2
  136. package/test/export-surface.snapshot.json +9 -1
@@ -17,34 +17,34 @@ export * from "./read-face.js";
17
17
  import { type CwdRef, type ReadImageDownsamplerOption } from "./fs-shared.js";
18
18
  /** Options for {@link createHandsToolkit}. */
19
19
  export interface HandsToolkitOptions {
20
- /** design/119 (CC --add-dir parity): extra allowed containment roots (canonical). Widens file-tool
21
- * containment only; the primary root keeps the cwd/base role. The full `bash` (effect:write) is NOT
22
- * constrained by these — it is deliberately unsandboxed and only uses them for its post-`cd`
23
- * disclosure note. RB-413: `bash_readonly` IS constrained by them (that face refuses a read outside
24
- * the roots), so widening here widens what the read-only band may read. */
20
+ /** CC --add-dir parity: extra allowed containment roots (canonical). Widens file-tool containment
21
+ * only; the primary root keeps the cwd/base role. The full `bash` (effect:write) is NOT constrained
22
+ * by these — it is deliberately unsandboxed and only uses them for its post-`cd` disclosure note.
23
+ * `bash_readonly` IS constrained by them (that face refuses a read outside the roots), so widening
24
+ * here widens what the read-only band may read. */
25
25
  additionalRoots?: readonly string[];
26
- /** Ruled 2026-08-05 (read-boundary whitelist): extra allowed containment roots for the READ faces
27
- * only — read_file/grep/glob/repo_map and (RB-413) `bash_readonly` admit them; edit_file/
28
- * write_file/notebook_edit and the full `bash`'s disclosure roots deliberately do NOT (widening
29
- * reads must never silently widen writes). Caveat, same tradeoff RB-413 already states for
30
- * `additionalRoots`: `bash_readonly`'s COMMAND allowlist is a deployment declaration — a
26
+ /** The read-boundary whitelist: extra allowed containment roots for the READ faces only —
27
+ * read_file/grep/glob/repo_map and `bash_readonly` admit them; edit_file/write_file/notebook_edit
28
+ * and the full `bash`'s disclosure roots deliberately do NOT (widening reads must never silently
29
+ * widen writes). Caveat, the same tradeoff `additionalRoots` states:
30
+ * `bash_readonly`'s COMMAND allowlist is a deployment declaration — a
31
31
  * deployment that puts a mutating command into `bashReadonlyAllow` has declared it read-safe,
32
32
  * and that declaration applies inside every root, these included. Keep the allowlist genuinely
33
33
  * non-mutating if these roots must stay read-only through the shell face too. */
34
34
  additionalReadRoots?: readonly string[];
35
35
  /** Mount a shell tool. Pass false for an env without a real shell (e.g. `StubExecutionEnv`) so a bash
36
- * tool that can only error never reaches the model (design/44 §9 S1). Default false. */
36
+ * tool that can only error never reaches the model. Default false. */
37
37
  includeShell?: boolean;
38
- /** Verifier read-only boundary (design/44 §6): mount ONLY effect:read hand tools — read_file/grep/glob
38
+ /** Verifier read-only boundary: mount ONLY effect:read hand tools — read_file/grep/glob
39
39
  * (+ `bash_readonly` when `includeShell`). Drops edit_file/write_file and the full `bash`. Default false. */
40
40
  readOnly?: boolean;
41
41
  /** Override the `bash_readonly` command allowlist (default {@link BASH_READONLY_DEFAULT_ALLOW}). */
42
42
  bashReadonlyAllow?: readonly string[];
43
- /** Commit-message attribution trailer for the `bash` git protocol (design/64 §8.1D). Default NONE
44
- * ([c209] BREAKING: attribution is a deployment identity asset the branded scenario sets it);
45
- * pass `"Name <email>"` to advertise one, `false` (≡ unset) for no trailer section. */
43
+ /** Commit-message attribution trailer for the `bash` git protocol. Default NONE — attribution is a
44
+ * deployment identity asset, so the branded deployment sets it; pass `"Name <email>"` to advertise
45
+ * one, `false` (≡ unset) for no trailer section. */
46
46
  commitCoAuthor?: string | false;
47
- /** design/99 §E13 — the caller's own {@link CwdRef} to track this task's logical cwd, instead of one
47
+ /** The caller's own {@link CwdRef} to track this task's logical cwd, instead of one
48
48
  * created internally. The Runner passes its own so it can OBSERVE `cd` moves (`cwdRef.current` changes)
49
49
  * and emit a `workspace_changed` event. Ignored in `readOnly` mode (no `cd`). Default: a fresh ref at root. */
50
50
  cwdRef?: CwdRef;
@@ -53,56 +53,55 @@ export interface HandsToolkitOptions {
53
53
  /** Runner-owned owner/scope fallback used when a tool execute context is unavailable in tests. */
54
54
  taskOwner?: string;
55
55
  taskScope?: string;
56
- /** design/129 — see createBashTool's taskOpts.sessionId: session-resident background commands. */
56
+ /** See createBashTool's taskOpts.sessionId: session-resident background commands. */
57
57
  sessionId?: string;
58
58
  /** Mount TaskOutput/TaskStop directly from this band. Runner sets false and mounts the unified dispatcher once. */
59
59
  mountBackgroundTaskTools?: boolean;
60
- /** design/116 §7 G2b: completion-notification sink for finished background commands (threaded to
61
- * createBashTool's onTaskNotification; the Runner wires the run-local injection lane here). */
60
+ /** Completion-notification sink for finished background commands (threaded to createBashTool's
61
+ * onTaskNotification; the Runner wires the run-local injection lane here). */
62
62
  taskNotification?: (n: import("../../core/task-notification.js").TaskNotificationPayload, opts?: {
63
63
  priority?: "now" | "next" | "later";
64
64
  }) => void;
65
- /** design/116 detach: the run-local per-tool-call detach hub (mid-flight ctrl+b → adopt as background). */
65
+ /** The run-local per-tool-call detach hub (mid-flight ctrl+b → adopt as background). */
66
66
  detachHub?: import("../../core/tool-detach.js").ToolDetachHub;
67
- /** RB-370 ② (cli): the Bash `timeout` parameter's DEFAULT budget, in ms — applied when the
68
- * model omits `timeout`. Resolution (options over env over constant — the standing sema discipline:
69
- * deployments configure the tool, not the process): this field ?? env `BASH_DEFAULT_TIMEOUT_MS` ??
70
- * 120000; invalid (non-finite / <= 0) values are discarded at every leg. See
67
+ /** The Bash `timeout` parameter's DEFAULT budget, in ms — applied when the model omits `timeout`.
68
+ * Resolution (options over env over constant — the standing sema discipline: deployments configure
69
+ * the tool, not the process): this field ?? env `BASH_DEFAULT_TIMEOUT_MS` ?? 120000; invalid
70
+ * (non-finite / <= 0) values are discarded at every leg. See
71
71
  * {@link import("./fs-shared.js").resolveBashTimeoutCaps} — the SAME resolver renders the tool
72
- * description, so the advertised numbers always match the enforced ones. Additive: absent
73
- * byte-compat 120s. Applies to both shell legs (`bash` and `bash_readonly`). */
72
+ * description, so the advertised numbers always match the enforced ones. Absent 120s. Applies to
73
+ * both shell legs (`bash` and `bash_readonly`). */
74
74
  bashDefaultTimeoutMs?: number;
75
- /** RB-370 ② (cli): the Bash `timeout` parameter's engine CEILING, in ms — requests above it
76
- * are clamped (with the RB-370 requested/capped disclosure naming THIS value). Resolution: (this
77
- * field ?? env `BASH_MAX_TIMEOUT_MS` ?? 600000), then floored at the resolved default — CC's own
78
- * only-widen semantic: a ceiling below the default is a narrowing intent = invalid, ignored in
79
- * favor of the default. Additive: absent byte-compat 600s. */
75
+ /** The Bash `timeout` parameter's engine CEILING, in ms — requests above it are clamped (the
76
+ * requested/capped disclosure names THIS value). Resolution: (this field ?? env
77
+ * `BASH_MAX_TIMEOUT_MS` ?? 600000), then floored at the resolved default — CC's own only-widen
78
+ * semantic: a ceiling below the default is a narrowing intent = invalid, ignored in favor of the
79
+ * default. Absent ⇒ 600s. */
80
80
  bashMaxTimeoutMs?: number;
81
81
  /** Structured sink for the timeout-cap discard announcements both shell legs emit at mount (see
82
82
  * {@link import("../../core/types.js").EngineNotice} / `RunnerDeps.onNotice`). Wired, it REPLACES
83
83
  * their `console.warn` line (a forwarding host must not show every fact twice); absent, the
84
- * console line prints verbatim (byte-compat loudness). Threaded per toolkit build — never a
84
+ * console line prints verbatim (last-resort loudness). Threaded per toolkit build — never a
85
85
  * global. */
86
86
  onNotice?: (n: import("../../core/types.js").EngineNotice) => void;
87
- /** RB-220 — see createBashTool's taskOpts.oneShot / createTaskOutputTool's TaskToolOptions.oneShot for
88
- * the full contract: this run has no later turn for an async background notification to land in.
87
+ /** See createBashTool's taskOpts.oneShot / createTaskOutputTool's TaskToolOptions.oneShot for the
88
+ * full contract: this run has no later turn for an async background notification to land in.
89
89
  * Threaded to both the Bash background-launch receipt and (when this band mounts TaskOutput itself,
90
- * `mountBackgroundTaskTools: true`) the TaskOutput poll receipt. Absent ⇒ byte-compat (unbranched,
91
- * pre-RB-220 wording). */
90
+ * `mountBackgroundTaskTools: true`) the TaskOutput poll receipt. Absent ⇒ the unbranched wording. */
92
91
  oneShot?: boolean;
93
- /** RB-198 F1 (CC 220 `Zry`/`WZi.#m` parity): see createBashTool's taskOpts field of the same name for the
94
- * full contract. Threaded from {@link HandsBandOptions.autoBackgroundOnTimeout} (a deployment-level
95
- * opt-in) — NOT from `detachHub`/`taskRegistry` merely being present, which are wired unconditionally by
96
- * the Runner for every task and so cannot double as an opt-in signal. Default undefined ⇒ `false`
97
- * downstream (byte-compat: an omitted field changes nothing for any existing caller). */
92
+ /** CC `Zry`/`WZi.#m` parity: see createBashTool's taskOpts field of the same name for the full
93
+ * contract. Threaded from {@link HandsBandOptions.autoBackgroundOnTimeout} (a deployment-level
94
+ * opt-in) — NOT from `detachHub`/`taskRegistry` merely being present, which are wired unconditionally
95
+ * by the Runner for every task and so cannot double as an opt-in signal. Default undefined ⇒ `false`
96
+ * downstream. */
98
97
  autoBackgroundOnTimeout?: boolean;
99
- /** 批③: Read-image downsampler seam ({@link ReadImageDownsamplerOption}). Default undefined = auto-detect
98
+ /** Read-image downsampler seam ({@link ReadImageDownsamplerOption}). Default undefined = auto-detect
100
99
  * the optional sharp dependency once per process; `false` disables it (deterministic no-sharp behavior). */
101
100
  readImageDownsampler?: ReadImageDownsamplerOption;
102
- /** PDF degradation chain v2: the SERVING model's PDF capability profile (prepare-task derives it via
101
+ /** PDF degradation chain: the SERVING model's PDF capability profile (prepare-task derives it via
103
102
  * {@link import("./fs-pdf.js").pdfModelCapabilitiesOf}). A model without native document input gets pdftotext text extraction →
104
103
  * rendered page images (vision) → an honest placeholder, instead of a brain-level placeholder. Default
105
- * undefined = fully capable (byte-compat: native document block). */
104
+ * undefined = fully capable (native document block). */
106
105
  pdfModelCapabilities?: PdfModelCapabilities;
107
106
  /** Append the per-read content-safety reminder after a successful text read
108
107
  * ({@link import("./fs-shared.js").readCyberReminderText}). Default TRUE — a BYOM deployment cannot
@@ -112,10 +111,10 @@ export interface HandsToolkitOptions {
112
111
  * exemption gate the upstream 88 source had around the same mechanism (see readCyberReminderText's note
113
112
  * for the full attribution). Absent ⇒ appended. */
114
113
  readCyberReminder?: boolean;
115
- /** design/138 S2-C — write-time content gate for Write/Edit/NotebookEdit (see {@link BeforeWriteHook}).
116
- * The Runner wires the MemoryEngine's memory-domain scan here; absent ⇒ byte-identical behavior. */
114
+ /** Write-time content gate for Write/Edit/NotebookEdit (see {@link BeforeWriteHook}). The Runner
115
+ * wires the MemoryEngine's memory-domain scan here; absent ⇒ byte-identical behavior. */
117
116
  beforeWrite?: BeforeWriteHook;
118
- /** design/381 — first-touch file-history hook for Write/Edit/NotebookEdit (see
117
+ /** First-touch file-history hook for Write/Edit/NotebookEdit (see
119
118
  * {@link TrackFileEditHook}): called after the content gates pass, immediately before the final
120
119
  * env write, so the file's pre-edit state is durably recorded before it changes. The Runner
121
120
  * wires it to `FileHistoryStore.trackEdit`; absent ⇒ byte-identical behavior (no history). */
@@ -126,54 +125,51 @@ export interface HandsToolkitOptions {
126
125
  * Purely additive: it cannot refuse a write, and a fault in it is contained in both shapes (a
127
126
  * synchronous throw and a rejected promise), neither of them awaited. */
128
127
  onFileEdited?: FileEditedHook;
129
- /** #181-F6 — see createBashTool's taskOpts field of the same name: whether the Monitor tool is on
130
- * this run's roster (the Runner mounts Monitor, this band never does). `false` drops the gh
131
- * rate-limit hint's Monitor clause; absent ⇒ historic full wording (byte-compat). */
128
+ /** See createBashTool's taskOpts field of the same name: whether the Monitor tool is on this run's
129
+ * roster (the Runner mounts Monitor, this band never does). `false` drops the gh rate-limit hint's
130
+ * Monitor clause; absent ⇒ the full wording. */
132
131
  monitorToolActive?: boolean;
133
- /** design/199 件B — ADDITIONS to the built-in sensitive-path READ deny set
132
+ /** ADDITIONS to the built-in sensitive-path READ deny set
134
133
  * ({@link import("./read-deny.js").READ_FACE_DEFAULT_DENY_ENTRIES}), judged by the structured read
135
134
  * faces (Read/Grep/Glob/RepoMap and their traversals) in BOTH containment modes. Add-only:
136
135
  * additions union with the active built-ins, `[]` ≡ absent (union identity), and additions can
137
136
  * never remove a built-in — the one removal channel is the deployment's built-in configuration
138
- * ({@link readDenyBuiltinTiers} / {@link readDenyBuiltinExclude}, #245 revision of D-4). Bad entry
139
- * shapes throw at wiring time (#123). The write faces are untouched (their guard is
140
- * createSensitivePathPolicy). */
137
+ * ({@link readDenyBuiltinTiers} / {@link readDenyBuiltinExclude}). Bad entry shapes throw at wiring
138
+ * time. The write faces are untouched (their guard is createSensitivePathPolicy). */
141
139
  readDenyPatterns?: readonly ReadDenyEntry[];
142
- /** #245 — the deployment's built-in-table TIER selection ({@link import("./read-deny.js").ReadDenyBuiltinConfig}
140
+ /** The deployment's built-in-table TIER selection ({@link import("./read-deny.js").ReadDenyBuiltinConfig}
143
141
  * `tiers` key): EXACTLY the listed tiers of {@link import("./read-deny.js").READ_FACE_BUILTIN_DENY_TABLE}
144
142
  * are active (`[]` = none — explicit and legal); absent = the default selection
145
143
  * ({@link import("./read-deny.js").READ_DENY_DEFAULT_TIERS} — every tier except `shell-history`).
146
144
  * Composes with {@link readDenyBuiltinExclude} (tier selection first, then row removal) and never
147
- * touches the additions seats. Unknown tier names throw at wiring time (#123). Deployment seat
148
- * ONLY — deliberately not a TaskSpec key, so no task can widen below its deployment. */
145
+ * touches the additions seats. Unknown tier names throw at wiring time. Deployment seat ONLY —
146
+ * deliberately not a TaskSpec key, so no task can widen below its deployment. */
149
147
  readDenyBuiltinTiers?: readonly string[];
150
- /** #245 — per-row removal from the built-in table by STABLE NAME (= the row's canonical pattern
151
- * text, e.g. `".ssh"`, `".config/gcloud"`), applied after {@link readDenyBuiltinTiers} selection.
152
- * Naming a row of an inactive tier is a satisfied intent (no-op); a name matching NO table row
153
- * throws at wiring time (#123 — never silently ignored). Deployment seat ONLY, same clamp
154
- * argument as the tiers key. */
148
+ /** Per-row removal from the built-in table by STABLE NAME (= the row's canonical pattern text, e.g.
149
+ * `".ssh"`, `".config/gcloud"`), applied after {@link readDenyBuiltinTiers} selection. Naming a row
150
+ * of an inactive tier is a satisfied intent (no-op); a name matching NO table row throws at wiring
151
+ * time (never silently ignored). Deployment seat ONLY, same clamp argument as the tiers key. */
155
152
  readDenyBuiltinExclude?: readonly string[];
156
- /** design/199 件A — the READ-face containment state for the structured read faces
153
+ /** The READ-face containment state for the structured read faces
157
154
  * ({@link import("./read-face.js").ReadFace}; resolved through the SAME
158
155
  * {@link import("./read-face.js").resolveReadFace} order prepare-task uses). Absent ⇒ the
159
- * resolution order's default = "roots" (D-1b: the engine never opens implicitly). "open" skips
160
- * ONLY the roots containment judgment — the deny set, the UNC out-of-set refusal and the
161
- * special-file type gates run in both faces (§2.0). Beside `readOnly: true` the mount wins:
162
- * this seat is deps-shaped (a deployment default, not a per-call assertion), so its "open"
163
- * CLAMPS to "roots" and the clamp is ANNOUNCED (`config.read_face_deployment_clamped`, through
164
- * `onNotice` / `console.warn`) — the loud refusal belongs to the TASK seat (`TaskSpec.readFace`),
165
- * which is the one genuine per-call contradiction (#237; stale "refused loudly" wording here
166
- * predated the 96ef89d seat distinction). Never affects the write faces. */
156
+ * resolution order's default = "roots" (the engine never opens implicitly). "open" skips ONLY the
157
+ * roots containment judgment — the deny set, the UNC out-of-set refusal and the special-file type
158
+ * gates run in both faces. Beside `readOnly: true` the mount wins: this seat is deps-shaped (a
159
+ * deployment default, not a per-call assertion), so its "open" CLAMPS to "roots" and the clamp is
160
+ * ANNOUNCED (`config.read_face_deployment_clamped`, through `onNotice` / `console.warn`) — the loud
161
+ * refusal belongs to the TASK seat (`TaskSpec.readFace`), the one genuine per-call contradiction.
162
+ * Never affects the write faces. */
167
163
  readFace?: "open" | "roots";
168
- /** design/319 (A ticket) — the session's reminder provenance mark: the band's engine-minted
164
+ /** The session's reminder provenance mark: the band's engine-minted
169
165
  * `<system-reminder>` open tags (the Read cyber/dedup/offset/empty reminders and the gh
170
166
  * rate-limit hint) carry it as `mark="…"`, matching the system-prompt declaration the Runner
171
167
  * renders for the same session. Threaded by prepare-task; a library-direct mount that omits it
172
- * keeps the historic bare tags (byte-compat — with no declaration in its prompt, a bare tag is
173
- * the honest form). The tag is rendered by the mint home (core/reminder-mint.ts) — the content
174
- * BODY next to it is byte-untouched. */
168
+ * keeps bare tags — with no declaration in its prompt, a bare tag is the honest form. The tag is
169
+ * rendered by the mint home (core/reminder-mint.ts) — the content BODY next to it is
170
+ * byte-untouched. */
175
171
  reminderMark?: string;
176
- /** design/319 (B ticket) — the per-run trailer/defuse trigger counters (observation seat, G9②):
172
+ /** The per-run trailer/defuse trigger counters (observation seat):
177
173
  * the Read text/notebook/PDF-text disclosure trailers bump `read.*` / `notebook.*` / `pdf.*`
178
174
  * keys here. The form suffixes are enumerated once, on the consumer-facing contract
179
175
  * (`TaskResult.stats.mechanisms.reminderDisclosures` in core/types.ts) — this map is the same
@@ -184,10 +180,10 @@ export interface HandsToolkitOptions {
184
180
  reminderDisclosureCounts?: import("../../core/reminder-disclosure.js").ReminderDisclosureCounts;
185
181
  }
186
182
  /**
187
- * Build the per-task hand tool band over an injected env + fresh per-task read state (design/44 §11 A).
183
+ * Build the per-task hand tool band over an injected env + fresh per-task read state.
188
184
  * `rootCanonical` is the already-canonicalized containment root (prepare-task resolves it once). Normal
189
185
  * mode mounts read/edit/write/grep/glob (+`bash` when `includeShell`); `readOnly` mode mounts only the
190
186
  * effect:read tools read/grep/glob (+`bash_readonly` when `includeShell`) — the verifier boundary. Subset
191
- * selection beyond that is the caller's job via the existing design/38 tool-filter.
187
+ * selection beyond that is the caller's job via the tool-filter.
192
188
  */
193
189
  export declare function createHandsToolkit(env: ExecutionEnv, readFileState: ReadFileState, rootCanonical: string, opts?: HandsToolkitOptions): AgentTool[];
@@ -1,17 +1,16 @@
1
1
  import type { ImageContent } from "../../internal/llm.js";
2
2
  /**
3
- * RB-227 — the Read tool's Jupyter-notebook projection: `.ipynb` is rendered as cells
4
- * with outputs (CC 2.1.220 parity: `Ctd`/`wtd`/`Zx_`/`Qx_`/`eI_`/`tI_`/`Atd`, pretty220.js
5
- * :371265-:371426), never as raw JSON text. The raw-JSON rendering let a notebook's base64 outputs
6
- * overflow the Read token cap, auto-paginate into an `isPartialView` entry, and thereby lock
7
- * NotebookEdit out via the requireRead gate (RB-200 F2) with the marker's own offset/limit hint
8
- * pointing at a range that itself exceeds the cap (the base64 lives on one mega-line).
3
+ * The Read tool's Jupyter-notebook projection: `.ipynb` is rendered as cells with outputs (CC 2.1.220
4
+ * parity), never as raw JSON text. Raw-JSON rendering lets a notebook's base64 outputs overflow the
5
+ * Read token cap, auto-paginate into an `isPartialView` entry, and thereby lock NotebookEdit out via
6
+ * the requireRead gate — with the marker's own offset/limit hint pointing at a range that itself
7
+ * exceeds the cap (the base64 lives on one mega-line). That is the failure mode this lane removes.
9
8
  *
10
9
  * Pure module (no I/O, no env): index.ts owns reading/decoding/state; this owns parse + render.
11
10
  */
12
- /** CC 220 `o3r` (:60226): extname === ".ipynb". */
11
+ /** CC `o3r` parity: extname === ".ipynb". */
13
12
  export declare function isNotebookPath(p: string): boolean;
14
- /** CC 220 `Jx_ = 1e4` (:371426): PER-CELL cap on the summed output payload (text chars + image
13
+ /** CC `Jx_` = 1e4: PER-CELL cap on the summed output payload (text chars + image
15
14
  * base64 chars). A cell over it has its ENTIRE outputs array replaced by one pointer line —
16
15
  * per cell, never a running global budget (CC's `Xx_` accumulator restarts for every cell). */
17
16
  export declare const NOTEBOOK_CELL_OUTPUT_POINTER_CHARS = 10000;
@@ -20,12 +19,12 @@ export declare const NOTEBOOK_CELL_OUTPUT_POINTER_CHARS = 10000;
20
19
  * text exceeds 10K is always pointered, so this clip is unreachable insurance kept at the same
21
20
  * 10K yardstick (simplification of CC's two-stage clip, recorded deliberately). */
22
21
  export declare const NOTEBOOK_OUTPUT_TEXT_CLIP = 10000;
23
- /** RB-227 E4 — cumulative image budget across the WHOLE notebook: the 10K per-cell pointer bounds
24
- * one cell, but N cells × ~9KB images is unbounded. CC gets an implicit bound because image data
25
- * counts toward its 256KB projected-JSON cap (`ePi = 262144`, :61029) and then HARD-ERRORS; sema
26
- * reuses that same figure but as a DEGRADATION budget — images past it are dropped with an honest
27
- * marker instead of making the notebook unreadable/uneditable (which is the RB-227 failure mode
28
- * this whole lane exists to remove). Divergence-logged. */
22
+ /** Cumulative image budget across the WHOLE notebook: the 10K per-cell pointer bounds one cell, but
23
+ * N cells × ~9KB images is unbounded. CC gets an implicit bound because image data counts toward its
24
+ * 256KB projected-JSON cap (`ePi` = 262144) and then HARD-ERRORS; sema reuses that same figure but as
25
+ * a DEGRADATION budget — images past it are dropped with an honest marker instead of making the
26
+ * notebook unreadable/uneditable, which is the failure mode this lane exists to remove.
27
+ * Divergence-logged. */
29
28
  export declare const NOTEBOOK_IMAGE_BASE64_BUDGET = 262144;
30
29
  export interface NotebookOutputImage {
31
30
  /** Whitespace-stripped base64 (magic-validated — never an unverified blob, see `imageFromData`). */
@@ -40,9 +39,9 @@ export interface NotebookOutput {
40
39
  export interface NotebookCell {
41
40
  /** `cell.id`, or the synthesized `cell-${index}` for nbformat<4.5 — index = the UNFILTERED array
42
41
  * position, because NotebookEdit's `/^cell-(\d+)$/` positional fallback resolves exactly that.
43
- * Deliberate delta (review r2 finding 2): sema synthesizes for any NON-STRING id (`typeof id ===
44
- * "string"` guard in `parseNotebookCells`) where CC's `wtd` uses `e.id ?? cell-${t}` (:371314)
45
- * and would render e.g. a numeric id literally — but NotebookEdit's id match is string-only, so
42
+ * Deliberate delta: sema synthesizes for any NON-STRING id (`typeof id === "string"` guard in
43
+ * `parseNotebookCells`) where CC's `wtd` uses `e.id ?? cell-${t}` and would render e.g. a numeric
44
+ * id literally — but NotebookEdit's id match is string-only, so
46
45
  * CC's literal form would be un-addressable while sema's positional alias resolves; nbformat
47
46
  * ids are spec-string, so this branch only fires on out-of-spec input. */
48
47
  cell_id: string;
@@ -62,7 +61,7 @@ export type ParsedNotebook = {
62
61
  reason: "json" | "shape";
63
62
  };
64
63
  /**
65
- * CC `Ctd` + `wtd` (:371373 / :371313): parse the notebook JSON into the projected cell list.
64
+ * CC `Ctd` + `wtd`: parse the notebook JSON into the projected cell list.
66
65
  * Failure is a typed reason, not a throw — the Read lane falls back to raw text on it (sema
67
66
  * divergence from CC's hard error: a corrupt notebook stays readable so the model can see what is
68
67
  * wrong; NotebookEdit still refuses it with its own JSON-validation errors, so nothing is loosened).
@@ -81,13 +80,13 @@ export interface NotebookRender {
81
80
  imageChars: number;
82
81
  }
83
82
  /**
84
- * CC `eI_`/`tI_`/`Atd` (:371339/:371349/:371399): render projected cells to content blocks.
85
- * Tag shape is CC-verbatim, including the deliberately malformed closing tag `</cell id="X">`;
86
- * `<cell_type>` only when not code, `<language>` only for code cells whose language !== "python".
87
- * Output text rides with a leading "\n" (tI_) and adjacent text blocks merge with "\n" (Atd), so an
88
- * all-text notebook collapses to a single text block. Images ride as real image blocks in sema's
89
- * `{type:"image", data, mimeType}` shape, bounded by the cumulative `imageBase64Budget` (E4): past
90
- * it the image is DROPPED with an honest text marker — a degradation, never an error.
83
+ * CC `eI_`/`tI_`/`Atd`: render projected cells to content blocks. Tag shape is CC-verbatim, including
84
+ * the deliberately malformed closing tag `</cell id="X">`; `<cell_type>` only when not code,
85
+ * `<language>` only for code cells whose language !== "python". Output text rides with a leading "\n"
86
+ * and adjacent text blocks merge with "\n", so an all-text notebook collapses to a single text block.
87
+ * Images ride as real image blocks in sema's `{type:"image", data, mimeType}` shape, bounded by the
88
+ * cumulative `imageBase64Budget`: past it the image is DROPPED with an honest text marker a
89
+ * degradation, never an error.
91
90
  */
92
91
  export declare function renderNotebookCells(cells: readonly NotebookCell[], imageBase64Budget: number): NotebookRender;
93
92
  /** Wire-card projection of a cell: base64 replaced by a length marker so the `details` card never
@@ -1,7 +1,7 @@
1
1
  /**
2
- * PDF read pipeline (+ 审计 — CC FileReadTool parity).
2
+ * PDF read pipeline (CC FileReadTool parity).
3
3
  *
4
- * CC ground truth (original-source-code, 取证 2026-07-07):
4
+ * CC ground truth (original source code):
5
5
  * - Whole-PDF path (`FileReadTool.ts:987-1016` + `utils/pdf.ts:88-103`): the file bytes are base64'd and
6
6
  * sent as a native `{type:"document",source:{type:"base64",media_type:"application/pdf",data}}` content
7
7
  * block — the model reads the text layer directly (no local text extraction).
@@ -40,7 +40,7 @@ export declare function parsePdfPageRange(pages: string): PdfPageRange | undefin
40
40
  * nothing matches (page tree inside compressed object streams — modern writers), NEVER a guess.
41
41
  */
42
42
  export declare function countPdfPagesFromBytes(bytes: Uint8Array): number | undefined;
43
- /** Max chars of a failed poppler call's stderr/stdout kept in the reported error (A-005.15). */
43
+ /** Max chars of a failed poppler call's stderr/stdout kept in the reported error. */
44
44
  export declare const PDF_EXEC_ERROR_PREVIEW_CHARS = 400;
45
45
  /** Bound a poppler exec failure's captured stream to {@link PDF_EXEC_ERROR_PREVIEW_CHARS}, marking the cut
46
46
  * (a bare slice reads identical to a short capture that just happened to end there — the model has no way
@@ -60,9 +60,9 @@ export interface ReadDenyMatcher {
60
60
  readonly rgProbeGlobs: readonly ReadDenyRgGlob[];
61
61
  }
62
62
  /**
63
- * The closed set of built-in tiers (#245). A tier is the deployment's selection unit
63
+ * The closed set of built-in tiers. A tier is the deployment's selection unit
64
64
  * ({@link ReadDenyBuiltinConfig.tiers}); every {@link READ_FACE_BUILTIN_DENY_TABLE} row belongs to
65
- * exactly one. Unknown tier names refuse loudly (#123) — this array is the validation source and the
65
+ * exactly one. Unknown tier names refuse loudly — this array is the validation source and the
66
66
  * admin-face vocabulary, never re-spelled downstream.
67
67
  */
68
68
  export declare const READ_DENY_BUILTIN_TIERS: readonly ["credentials", "shell-history", "browser", "wallet", "agent-config"];
@@ -78,12 +78,12 @@ export interface ReadDenyBuiltinRow {
78
78
  readonly tier: ReadDenyBuiltinTier;
79
79
  }
80
80
  /**
81
- * READ_FACE_BUILTIN_DENY_TABLE — the FULL built-in table with tier metadata (#245: the material
82
- * basis of the deployment admin face what an org administrator "sees" before selecting tiers /
83
- * excluding rows). Activation is a separate fact: the default face is the table under
81
+ * READ_FACE_BUILTIN_DENY_TABLE — the FULL built-in table with tier metadata: the material basis of
82
+ * the deployment admin face, what an org administrator "sees" before selecting tiers / excluding
83
+ * rows. Activation is a separate fact: the default face is the table under
84
84
  * {@link READ_DENY_DEFAULT_TIERS} (shell-history rows exist here but are OFF by default).
85
85
  * The dotenv family is deliberately NOT here — workspace `.env` files are working material for the
86
- * tasks this engine runs (the design's `outside_workspace` tier was also ruled OUT).
86
+ * tasks this engine runs; an `outside_workspace` tier is likewise deliberately absent.
87
87
  *
88
88
  * Each row states its tradeoff. Rows are matched as segment runs anywhere in the path, so a repo
89
89
  * fixture spelled `fixtures/.ssh/id_rsa` is refused too — deliberate: the refusal names the pattern,
@@ -99,20 +99,20 @@ export interface ReadDenyBuiltinRow {
99
99
  *
100
100
  * agent-config tier — the agent's OWN configuration files whose `env` / server blocks carry API keys
101
101
  * in cleartext (the shell's `settings.json` env block, a project `.mcp.json` server env, the engine
102
- * host's data-root `.env`). A structured read of one of these used to land the key verbatim in the
103
- * tool result and therefore in the session record. Rows name FILES, not the config DIRECTORIES:
102
+ * host's data-root `.env`). Unguarded, a structured read of one of these lands the key verbatim in
103
+ * the tool result and therefore in the session record. Rows name FILES, not the config DIRECTORIES:
104
104
  * `.sema`/`.claude` also hold agents, skills, hooks and (under the shell's layout,
105
105
  * `~/.sema/engine-data`) the engine data root with the memory library — material the model reads
106
106
  * and edits as ordinary work, and a directory-wide row would need a data-root passthrough (one more
107
107
  * rule) to keep it readable. The write face guards the directories (`sensitive-path-policy.ts`): a
108
108
  * write there is self-authorization; a read of a non-credential file there is debugging. Token
109
- * STORES of the same tooling (`.credentials.json`, `.codex/auth.json`, …) are credentials rows, not
109
+ * STORES of the same tooling (`.credentials.json`, an agent CLI's `auth.json`, …) are credentials rows, not
110
110
  * agent-config rows: a deployment that switches this tier off to debug its agent configuration must
111
111
  * not also expose the OAuth stores beside it.
112
112
  */
113
113
  export declare const READ_FACE_BUILTIN_DENY_TABLE: readonly ReadDenyBuiltinRow[];
114
114
  /**
115
- * The DEFAULT tier selection (#245 ruling ②): every tier EXCEPT `shell-history` — history files are
115
+ * The DEFAULT tier selection: every tier EXCEPT `shell-history` — history files are
116
116
  * unrestricted unless a deployment opts the tier in. Derived, not re-listed: a tier added to the
117
117
  * closed set is default-ON unless this expression is deliberately revisited (`agent-config` joined
118
118
  * default-ON this way: an unconfigured deployment refuses the agent's own key-bearing settings files;
@@ -120,30 +120,30 @@ export declare const READ_FACE_BUILTIN_DENY_TABLE: readonly ReadDenyBuiltinRow[]
120
120
  */
121
121
  export declare const READ_DENY_DEFAULT_TIERS: readonly ReadDenyBuiltinTier[];
122
122
  /**
123
- * The deployment's built-in-table configuration (#245 — deployment seat ONLY: RunnerDeps /
123
+ * The deployment's built-in-table configuration — deployment seat ONLY (RunnerDeps /
124
124
  * HandsToolkitOptions; deliberately NOT a TaskSpec key and NOT in the governed workflow whitelist,
125
125
  * so no task or governed script can widen below its deployment).
126
126
  * - `tiers` — EXACTLY-these tier selection: listed tiers are active, unlisted ones are not
127
127
  * (`[]` = no built-in tiers at all — an explicit, legal posture; absent = {@link READ_DENY_DEFAULT_TIERS}).
128
128
  * - `exclude` — per-row removal by canonical pattern name, applied AFTER tier selection.
129
- * Unknown tier names / unknown row names refuse loudly (#123) — never silently ignored.
129
+ * Unknown tier names / unknown row names refuse loudly — never silently ignored.
130
130
  */
131
131
  export interface ReadDenyBuiltinConfig {
132
132
  tiers?: readonly string[];
133
133
  exclude?: readonly string[];
134
134
  }
135
135
  /**
136
- * Resolve the ACTIVE built-in rows under a deployment configuration (validated, loud — #123's three
137
- * bad-value states all throw: garbage shapes, unknown tier names, unknown row names). The one
136
+ * Resolve the ACTIVE built-in rows under a deployment configuration (validated, loud — all three
137
+ * bad-value states throw: garbage shapes, unknown tier names, unknown row names). The one
138
138
  * resolution used by {@link compileReadDeny}; exported so an admin face can preview the effective
139
139
  * table under a candidate configuration with the engine's own rules.
140
140
  */
141
141
  export declare function resolveReadDenyBuiltins(config?: ReadDenyBuiltinConfig): readonly ReadDenyBuiltinRow[];
142
142
  /**
143
143
  * READ_FACE_DEFAULT_DENY_ENTRIES — the DEFAULT-ACTIVE built-in set: {@link READ_FACE_BUILTIN_DENY_TABLE}
144
- * under {@link READ_DENY_DEFAULT_TIERS} (#245: shell-history rows are in the table, not in this face).
145
- * Kept as the historical name for consumers rendering "what does an unconfigured deployment refuse";
146
- * the tier-annotated table is the admin-face export.
144
+ * under {@link READ_DENY_DEFAULT_TIERS} (shell-history rows are in the table, not in this face). This
145
+ * is the export for consumers rendering "what does an unconfigured deployment refuse"; the
146
+ * tier-annotated table is the admin-face export.
147
147
  */
148
148
  export declare const READ_FACE_DEFAULT_DENY_ENTRIES: readonly ReadDenyEntry[];
149
149
  /** A compiled segment-run pattern (shared engine — the write guard delegates here too). */
@@ -159,8 +159,8 @@ export interface CompiledSegmentPattern {
159
159
  * · "ascii" — ASCII-case-insensitive (deny-set contract);
160
160
  * · "unicode" — RegExp `i` flag (the write guard's historical host-keyed behavior — kept for it
161
161
  * byte-identically; NOT used by the deny set).
162
- * Returns null when the pattern reduces to zero segments — the CALLER owns its loud path (#123: the
163
- * two consumers refuse with their own surface-specific texts).
162
+ * Returns null when the pattern reduces to zero segments — the CALLER owns its loud path (the two
163
+ * consumers refuse with their own surface-specific texts).
164
164
  */
165
165
  export declare function compileSegmentPattern(raw: string, fold: "none" | "ascii" | "unicode"): CompiledSegmentPattern | null;
166
166
  /**
@@ -185,10 +185,10 @@ export declare function persistedReadDenyEntryProblem(e: unknown): string | null
185
185
  * Compile the read-face deny judge: ACTIVE built-in rows ∪ additions. Additions are add-only at every
186
186
  * task layer (`[]` additions ≡ absent, deliberately a no-op rather than a refusal: an array API
187
187
  * cannot observe a "replace" intent, and union-with-empty is the identity, not a silent fallback);
188
- * the built-in half is selected by the DEPLOYMENT's `builtin` config (#245 — absent = the default
189
- * tier selection, see {@link resolveReadDenyBuiltins}). A deployment that turned a tier off can still
188
+ * the built-in half is selected by the DEPLOYMENT's `builtin` config (absent = the default tier
189
+ * selection, see {@link resolveReadDenyBuiltins}). A deployment that turned a tier off can still
190
190
  * re-add single patterns through the additions seats — they then ride as ordinary additions.
191
191
  * Bad entry shapes / zero-segment patterns / unknown tier or row names throw loudly, naming the
192
- * layer or knob (#123).
192
+ * layer or knob.
193
193
  */
194
194
  export declare function compileReadDeny(additions?: readonly ReadDenyEntry[], layer?: string, builtin?: ReadDenyBuiltinConfig): ReadDenyMatcher;
@@ -1,13 +1,12 @@
1
- /** The read-face containment state. `"roots"` = the historical containment judgment, unchanged.
1
+ /** The read-face containment state. `"roots"` = the containment judgment runs.
2
2
  * `"open"` = the containment step is skipped (canonicalization, deny set, UNC out-of-set refusal
3
3
  * and the type gates all still run). */
4
4
  export type ReadFace = "open" | "roots";
5
- /** Loud value gate (#123): a `readFace` seat carries exactly "open" | "roots" — anything else
6
- * (case variants, truthy garbage) refuses at wiring time, never folds to a default. Exported
5
+ /** Loud value gate: a `readFace` seat carries exactly "open" | "roots" — anything else (case
6
+ * variants, truthy garbage) refuses at wiring time, never folds to a default. Exported
7
7
  * module-internally (not on the package surface) so prepare's unconditional config-guard leg can
8
- * screen the seats on runs that never mount hands early and unconditionally (since #242 the
9
- * resolver itself ALSO runs on every hands-less leg; this screen still fires first, so a garbage
10
- * value refuses before any leg-shape branching). */
8
+ * screen the seats on runs that never mount hands. The resolver itself also runs on every hands-less
9
+ * leg; this screen still fires first, so a garbage value refuses before any leg-shape branching. */
11
10
  export declare function assertReadFaceValue(v: unknown, seat: string): ReadFace | undefined;
12
11
  /** Inputs to {@link resolveReadFace} — all structural/declaration facts, never permission modes
13
12
  * (a deliberate axis separation: this shape carries facts, not verdicts). */
@@ -20,17 +19,16 @@ export interface ReadFaceInputs {
20
19
  * LOAD-BEARING wall (bash_readonly is genuinely confined by it) — never openable. */
21
20
  readOnlyMount: boolean;
22
21
  /** Org governance declared (`RunnerDeps.permissionRuleStore.partitions.org === true`): default roots; the task layer
23
- * may not open (D-2 — tighten-only under governance; the deps layer, being the deployment's own
22
+ * may not open (tighten-only under governance; the deps layer, being the deployment's own
24
23
  * declaration, still may). */
25
24
  orgGoverned: boolean;
26
- /** D-6: is the FULL shell (`core.bash@1`) structurally reachable on this mount? Computed BEFORE
27
- * tool-band assembly from spec-time facts (env kind / handsReadOnly / Bash exclusion — recon §3:
28
- * every exclusion source is spec-time-frozen, so this is always computable). When false, the
29
- * roots fence is the ONLY read boundary and the default stays roots even under a deps-layer
30
- * "open"… no — see the resolution order: an EXPLICIT open still wins (row 4 is a default, not a
31
- * clamp); what it changes is that NOTHING implicit opens a bash-less mount. */
25
+ /** Is the FULL shell (`core.bash@1`) structurally reachable on this mount? Computed BEFORE
26
+ * tool-band assembly from spec-time facts (env kind / handsReadOnly / Bash exclusion — every
27
+ * exclusion source is spec-time-frozen, so this is always computable). When false, the roots fence
28
+ * is the ONLY read boundary, so no IMPLICIT default may open the face; an EXPLICIT "open" on
29
+ * either seat still wins (row 4 of the order is a default, not a clamp). */
32
30
  fullShellReachable: boolean;
33
- /** #237 — observation hook for the ONE silent branch of the order: row 1's deployment-seat clamp
31
+ /** Observation hook for the ONE silent branch of the order: row 1's deployment-seat clamp
34
32
  * (readOnly mount + deps "open" + NO task seat). Fired exactly when the deps declaration was the
35
33
  * deciding seat and the mount overrode it — not when a task-level "roots" pinned the same value
36
34
  * anyway (the mount changed nothing there, and announcing it would claim a false cause), and
@@ -39,24 +37,23 @@ export interface ReadFaceInputs {
39
37
  onDeploymentClamp?: () => void;
40
38
  }
41
39
  /**
42
- * The ONE resolution order (§2.2), first hit wins. prepare-task AND createHandsToolkit both call
43
- * this — a library-direct mount gets identical validation and identical defaults.
40
+ * The ONE resolution order, first hit wins. prepare-task AND createHandsToolkit both call this — a
41
+ * library-direct mount gets identical validation and identical defaults.
44
42
  *
45
43
  * 1. read-only (verifier) mount → ROOTS; an explicit "open" on the TASK seat is a genuine
46
- * per-call CONTRADICTION and refuses loudly (#123 — never silently pick a side). An "open"
47
- * on the DEPLOYMENT seat alone is a deployment-wide default, not a per-task assertion — it
48
- * silently CLAMPS to roots (stricter-wins), same seat distinction row 2 already draws for
49
- * org governance below.
50
- * 2. org-governed: TaskSpec "open" refuses (task layer only tightens, D-2); deps "open" wins;
44
+ * per-call CONTRADICTION and refuses loudly (never silently pick a side). An "open" on the
45
+ * DEPLOYMENT seat alone is a deployment-wide default, not a per-task assertion — it silently
46
+ * CLAMPS to roots (stricter-wins), the same seat distinction row 2 draws for org governance.
47
+ * 2. org-governed: TaskSpec "open" refuses (task layer only tightens); deps "open" wins;
51
48
  * otherwise ROOTS.
52
49
  * 3. explicit seat: spec ?? deps.
53
- * 4. bash-less mount (D-6): ROOTS (the fence is the only read boundary there — "the fence guards
50
+ * 4. bash-less mount: ROOTS (the fence is the only read boundary there — "the fence guards
54
51
  * nothing bash reaches anyway" does not hold, so no implicit default may open it).
55
- * 5. default: ROOTS (D-1b — the engine never opens implicitly).
52
+ * 5. default: ROOTS — the engine never opens implicitly.
56
53
  */
57
54
  export declare function resolveReadFace(i: ReadFaceInputs): ReadFace;
58
55
  /**
59
- * #237 — the ONE text of the deployment-clamp announcement (`config.read_face_deployment_clamped`).
56
+ * The ONE text of the deployment-clamp announcement (`config.read_face_deployment_clamped`).
60
57
  * Both stations deliver THIS object through their own `deliverEngineNotice` call (prepare-task with
61
58
  * the `RunnerDeps.onNotice` seat, once per notice sink — the sink, not the deps object, because the
62
59
  * Runner rebuilds its deps; `createHandsToolkit` with its band-local `HandsToolkitOptions.onNotice`
@@ -3,14 +3,14 @@ import type { ExecutionEnv } from "../../internal/harness-types.js";
3
3
  import type { ReadDenyMatcher } from "./read-deny.js";
4
4
  import type { ReadFace } from "./read-face.js";
5
5
  /** Extract top-level symbol names (deduped, in first-seen order) from source text. A lightweight
6
- * comment/docstring state machine (council #4) skips column-0 declaration-like lines that are really
7
- * inside a `/* … *​/` block comment or a Python `"""`/`'''` docstring — otherwise e.g. a module
8
- * docstring containing `def foo():` at column 0 produces a phantom symbol. Not a full parser (v1
9
- * heuristic): it tracks whole-line block/docstring regions, the common false-positive source.
6
+ * comment/docstring state machine skips column-0 declaration-like lines that are really inside a
7
+ * `/* … *​/` block comment or a Python `"""`/`'''` docstring — otherwise e.g. a module docstring
8
+ * containing `def foo():` at column 0 produces a phantom symbol. Not a full parser: it tracks
9
+ * whole-line block/docstring regions, the common false-positive source.
10
10
  *
11
- * ⚠️ **Exported ONLY as a v1 heuristic, NOT a containment proof** (design/79 §3): it is column-0 /
12
- * source-only and skips indented lines, so it CANNOT enumerate everything an artifact can call. The
13
- * auto-promote tripwire (src/core/auto-promote.ts) consumes it in ESCALATE-ONLY mode — a clean scan
14
- * contributes nothing; it can only ever raise an escalation, never clear one. */
11
+ * ⚠️ **A heuristic, NOT a containment proof**: it is column-0 / source-only and skips indented lines,
12
+ * so it CANNOT enumerate everything an artifact can call. The auto-promote tripwire
13
+ * (src/core/auto-promote.ts) consumes it in ESCALATE-ONLY mode — a clean scan contributes nothing;
14
+ * it can only ever raise an escalation, never clear one. */
15
15
  export declare function extractSymbols(text: string): string[];
16
16
  export declare function createRepoMapTool(env: ExecutionEnv, rootCanonical: string, additionalRoots?: readonly string[], readDeny?: ReadDenyMatcher, readFace?: ReadFace): AgentTool;