@sema-agent/core 7.51.2 → 7.53.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 (446) hide show
  1. package/CHANGELOG.md +698 -2
  2. package/README.md +3 -1
  3. package/dist/agents/agent-transcript-tool.d.ts +1 -1
  4. package/dist/agents/cascade.js +4 -0
  5. package/dist/agents/cross-session-envelope.d.ts +8 -0
  6. package/dist/agents/cross-session-envelope.js +6 -0
  7. package/dist/agents/cross-session-judge.d.ts +21 -1
  8. package/dist/agents/cross-session-judge.js +8 -0
  9. package/dist/agents/cross-session-ref.d.ts +5 -0
  10. package/dist/agents/cross-session-ref.js +1 -0
  11. package/dist/agents/cumulative-stats.d.ts +3 -0
  12. package/dist/agents/cumulative-stats.js +3 -0
  13. package/dist/agents/list-agents-tool.d.ts +1 -1
  14. package/dist/agents/org-delivery-gate.d.ts +122 -0
  15. package/dist/agents/org-delivery-gate.js +69 -0
  16. package/dist/agents/peer-held-queue.d.ts +9 -4
  17. package/dist/agents/peer-held-queue.js +6 -5
  18. package/dist/agents/peer-session-drain.d.ts +35 -5
  19. package/dist/agents/peer-session-drain.js +271 -180
  20. package/dist/agents/read-inbox-tool.d.ts +8 -1
  21. package/dist/agents/read-inbox-tool.js +5 -1
  22. package/dist/agents/repair-loop.js +4 -0
  23. package/dist/agents/send-message-tool.d.ts +11 -16
  24. package/dist/agents/send-message-tool.js +11 -13
  25. package/dist/agents/subagent.d.ts +3 -0
  26. package/dist/agents/subagent.js +105 -76
  27. package/dist/agents/tool-filter.d.ts +58 -13
  28. package/dist/agents/tool-filter.js +34 -14
  29. package/dist/bench/metrics.d.ts +1 -0
  30. package/dist/brain/anthropic.d.ts +6 -1
  31. package/dist/brain/anthropic.js +17 -13
  32. package/dist/brain/model-presets.d.ts +4 -5
  33. package/dist/brain/model-presets.js +6 -5
  34. package/dist/brain/open-responses.js +16 -12
  35. package/dist/brain/openai.js +16 -12
  36. package/dist/brain/request-params.d.ts +12 -33
  37. package/dist/brain/request-params.js +5 -2
  38. package/dist/brain/request-route.d.ts +9 -8
  39. package/dist/brain/request-route.js +1 -0
  40. package/dist/brain/route-adjudicator.d.ts +123 -47
  41. package/dist/brain/route-adjudicator.js +171 -42
  42. package/dist/brain/route-conformance.js +2 -2
  43. package/dist/brain/routing.d.ts +24 -1
  44. package/dist/brain/routing.js +54 -19
  45. package/dist/brain/status-sink.d.ts +18 -0
  46. package/dist/brain/status-sink.js +7 -0
  47. package/dist/brain/timeout.js +5 -4
  48. package/dist/core/a2a.d.ts +5 -2
  49. package/dist/core/a2a.js +30 -13
  50. package/dist/core/allow-entry.d.ts +42 -9
  51. package/dist/core/allow-entry.js +25 -18
  52. package/dist/core/auto-compaction.d.ts +80 -20
  53. package/dist/core/auto-compaction.js +65 -18
  54. package/dist/core/auto-promote.d.ts +2 -1
  55. package/dist/core/auto-promote.js +2 -2
  56. package/dist/core/caller-tool-name.d.ts +9 -0
  57. package/dist/core/caller-tool-name.js +13 -0
  58. package/dist/core/checkpoint-requirements.d.ts +7 -1
  59. package/dist/core/checkpoint-requirements.js +2 -0
  60. package/dist/core/checkpoint-store.d.ts +57 -24
  61. package/dist/core/checkpoint-store.js +3 -3
  62. package/dist/core/child-clamp-seats.d.ts +6 -0
  63. package/dist/core/child-clamp-seats.js +2 -1
  64. package/dist/core/compliance.js +3 -1
  65. package/dist/core/credential-vocabulary.d.ts +33 -8
  66. package/dist/core/credential-vocabulary.js +32 -7
  67. package/dist/core/decision-receipt.d.ts +2 -2
  68. package/dist/core/delegation-frames.d.ts +9 -2
  69. package/dist/core/delegation-name.d.ts +18 -0
  70. package/dist/core/delegation-name.js +47 -0
  71. package/dist/core/effective-path-target.d.ts +25 -6
  72. package/dist/core/effective-path-target.js +24 -2
  73. package/dist/core/engine-capabilities.d.ts +8 -1
  74. package/dist/core/engine-capabilities.js +1 -1
  75. package/dist/core/engine-notice.d.ts +49 -21
  76. package/dist/core/frontmatter-fence.d.ts +10 -0
  77. package/dist/core/frontmatter-fence.js +6 -0
  78. package/dist/core/gate-fold.js +8 -25
  79. package/dist/core/gate-lanes.js +358 -274
  80. package/dist/core/gate-outcome.d.ts +11 -6
  81. package/dist/core/governance-codes.d.ts +11 -4
  82. package/dist/core/governance-codes.js +12 -3
  83. package/dist/core/hands-band-screen.d.ts +7 -0
  84. package/dist/core/hands-band-screen.js +32 -0
  85. package/dist/core/hooks.d.ts +283 -739
  86. package/dist/core/hooks.js +100 -193
  87. package/dist/{tools/fs → core}/image-admission.d.ts +21 -3
  88. package/dist/{tools/fs → core}/image-admission.js +24 -6
  89. package/dist/core/locked-config.d.ts +84 -32
  90. package/dist/core/locked-config.js +128 -42
  91. package/dist/core/mcp-connection-pool.d.ts +4 -1
  92. package/dist/core/mcp-connection-pool.js +7 -2
  93. package/dist/core/mcp-probe.d.ts +12 -9
  94. package/dist/core/mcp-probe.js +3 -3
  95. package/dist/core/mcp-server-spec.d.ts +104 -10
  96. package/dist/core/mcp-server-spec.js +183 -33
  97. package/dist/core/mcp.d.ts +31 -20
  98. package/dist/core/mcp.js +66 -56
  99. package/dist/core/memory-engine/data-plane.js +5 -1
  100. package/dist/core/memory-engine/distiller.js +16 -2
  101. package/dist/core/memory-engine/engine.d.ts +22 -30
  102. package/dist/core/memory-engine/engine.js +16 -10
  103. package/dist/core/memory-engine/frontmatter.d.ts +6 -0
  104. package/dist/core/memory-engine/frontmatter.js +19 -16
  105. package/dist/core/memory.d.ts +2 -2
  106. package/dist/core/mode-policy.d.ts +5 -16
  107. package/dist/core/mode-policy.js +7 -19
  108. package/dist/core/model-seat.d.ts +4 -1
  109. package/dist/core/mods/dollar.d.ts +109 -0
  110. package/dist/core/mods/dollar.js +154 -0
  111. package/dist/core/mods/host.d.ts +23 -0
  112. package/dist/core/mods/host.js +21 -0
  113. package/dist/core/mods/kernel/budget.d.ts +43 -0
  114. package/dist/core/mods/kernel/budget.js +83 -0
  115. package/dist/core/mods/kernel/dispatch.d.ts +100 -0
  116. package/dist/core/mods/kernel/dispatch.js +699 -0
  117. package/dist/core/mods/kernel/events.d.ts +245 -0
  118. package/dist/core/mods/kernel/events.js +210 -0
  119. package/dist/core/mods/kernel/index.d.ts +6 -0
  120. package/dist/core/mods/kernel/index.js +5 -0
  121. package/dist/core/mods/kernel/receive.d.ts +94 -0
  122. package/dist/core/mods/kernel/receive.js +188 -0
  123. package/dist/core/mods/kernel/registration.d.ts +131 -0
  124. package/dist/core/mods/kernel/registration.js +102 -0
  125. package/dist/core/mods/kernel/site-rules.d.ts +149 -0
  126. package/dist/core/mods/kernel/site-rules.js +296 -0
  127. package/dist/core/mods/stations.d.ts +344 -0
  128. package/dist/core/mods/stations.js +437 -0
  129. package/dist/core/mounted-mcp.d.ts +57 -0
  130. package/dist/core/mounted-mcp.js +71 -2
  131. package/dist/core/own-property-receipt.d.ts +13 -0
  132. package/dist/core/own-property-receipt.js +13 -23
  133. package/dist/core/parent-spec-seat.d.ts +18 -7
  134. package/dist/core/parent-spec-seat.js +6 -2
  135. package/dist/core/path-identity.js +2 -1
  136. package/dist/core/permission-rule-model.d.ts +58 -9
  137. package/dist/core/permission-rule-model.js +81 -7
  138. package/dist/core/permission-rule-org.d.ts +163 -33
  139. package/dist/core/permission-rule-org.js +205 -71
  140. package/dist/core/permission-rule-syntax.d.ts +15 -0
  141. package/dist/core/permission-rule-syntax.js +24 -16
  142. package/dist/core/permission-rules.d.ts +14 -2
  143. package/dist/core/permission-rules.js +63 -23
  144. package/dist/core/prompt-section-seat.d.ts +15 -27
  145. package/dist/core/prompt-section-seat.js +73 -40
  146. package/dist/core/protocol-http-auth.d.ts +3 -1
  147. package/dist/core/protocol-http-auth.js +2 -0
  148. package/dist/core/reminder-mint.d.ts +2 -2
  149. package/dist/core/remote-env.d.ts +24 -12
  150. package/dist/core/remote-env.js +1 -0
  151. package/dist/core/resume-startup-cause.d.ts +16 -1
  152. package/dist/core/resume-startup-cause.js +4 -1
  153. package/dist/core/retention.js +7 -2
  154. package/dist/core/retired-keys.d.ts +12 -2
  155. package/dist/core/retired-keys.js +15 -1
  156. package/dist/core/roles.js +60 -10
  157. package/dist/core/rule-lane-reads.js +1 -1
  158. package/dist/core/runner/announce-once-ledger.d.ts +31 -1
  159. package/dist/core/runner/announce-once-ledger.js +22 -0
  160. package/dist/core/runner/assemble-result.d.ts +9 -0
  161. package/dist/core/runner/assemble-result.js +3 -1
  162. package/dist/core/runner/call-hook-stations.d.ts +23 -27
  163. package/dist/core/runner/call-hook-stations.js +58 -42
  164. package/dist/core/runner/caller-stop-gate.d.ts +25 -0
  165. package/dist/core/runner/caller-stop-gate.js +7 -0
  166. package/dist/core/runner/compaction-seams.d.ts +8 -22
  167. package/dist/core/runner/compaction-seams.js +28 -53
  168. package/dist/core/runner/construction-doors.js +11 -1
  169. package/dist/core/runner/contracts.d.ts +86 -83
  170. package/dist/core/runner/credential-origin-seat.d.ts +2 -0
  171. package/dist/core/runner/credential-origin-seat.js +19 -0
  172. package/dist/core/runner/extra-body-dropped-seat.d.ts +2 -6
  173. package/dist/core/runner/gate-exit.d.ts +47 -36
  174. package/dist/core/runner/gate-exit.js +12 -5
  175. package/dist/core/runner/image.js +1 -2
  176. package/dist/core/runner/inline-image.js +1 -1
  177. package/dist/core/runner/mcp-redial.d.ts +52 -10
  178. package/dist/core/runner/mcp-redial.js +38 -9
  179. package/dist/core/runner/notice-seat-input.d.ts +11 -0
  180. package/dist/core/runner/notice-seat-input.js +1 -0
  181. package/dist/core/runner/permission-rule-lanes.d.ts +5 -2
  182. package/dist/core/runner/permission-rule-lanes.js +22 -10
  183. package/dist/core/runner/person-path-rows.d.ts +3 -1
  184. package/dist/core/runner/person-path-rows.js +3 -2
  185. package/dist/core/runner/prepare-acquire-reconcile.js +5 -1
  186. package/dist/core/runner/prepare-ask-lane.d.ts +5 -7
  187. package/dist/core/runner/prepare-ask-lane.js +6 -15
  188. package/dist/core/runner/prepare-caps-and-workflow.d.ts +4 -2
  189. package/dist/core/runner/prepare-caps-and-workflow.js +25 -8
  190. package/dist/core/runner/prepare-config-doors.d.ts +52 -1
  191. package/dist/core/runner/prepare-config-doors.js +168 -143
  192. package/dist/core/runner/prepare-defer-classify.js +7 -11
  193. package/dist/core/runner/prepare-delegation-surface.d.ts +2 -2
  194. package/dist/core/runner/prepare-delegation-surface.js +7 -5
  195. package/dist/core/runner/prepare-gate-stations.d.ts +8 -11
  196. package/dist/core/runner/prepare-gate-stations.js +11 -10
  197. package/dist/core/runner/prepare-hands-readface.d.ts +1 -1
  198. package/dist/core/runner/prepare-hands-readface.js +2 -1
  199. package/dist/core/runner/prepare-inherited-gate.d.ts +8 -12
  200. package/dist/core/runner/prepare-inherited-gate.js +10 -23
  201. package/dist/core/runner/prepare-listings.d.ts +1 -1
  202. package/dist/core/runner/prepare-listings.js +4 -2
  203. package/dist/core/runner/prepare-memory-engine-session.d.ts +0 -6
  204. package/dist/core/runner/prepare-memory-engine-session.js +20 -7
  205. package/dist/core/runner/prepare-memory.d.ts +3 -2
  206. package/dist/core/runner/prepare-memory.js +6 -2
  207. package/dist/core/runner/prepare-offload-wrappers.d.ts +4 -4
  208. package/dist/core/runner/prepare-offload-wrappers.js +2 -1
  209. package/dist/core/runner/prepare-park-ask.js +10 -14
  210. package/dist/core/runner/prepare-policy-chain.d.ts +17 -15
  211. package/dist/core/runner/prepare-policy-chain.js +104 -109
  212. package/dist/core/runner/prepare-project-context.d.ts +1 -1
  213. package/dist/core/runner/prepare-project-context.js +11 -12
  214. package/dist/core/runner/prepare-prompt-assembly.d.ts +45 -40
  215. package/dist/core/runner/prepare-prompt-assembly.js +138 -101
  216. package/dist/core/runner/prepare-prompt-inputs.d.ts +28 -23
  217. package/dist/core/runner/prepare-prompt-inputs.js +11 -10
  218. package/dist/core/runner/prepare-protocol-tools.d.ts +11 -7
  219. package/dist/core/runner/prepare-protocol-tools.js +20 -13
  220. package/dist/core/runner/prepare-question-face.d.ts +4 -2
  221. package/dist/core/runner/prepare-question-face.js +4 -3
  222. package/dist/core/runner/prepare-safety-scan.js +6 -10
  223. package/dist/core/runner/prepare-suspend-saga.d.ts +6 -0
  224. package/dist/core/runner/prepare-suspend-saga.js +7 -5
  225. package/dist/core/runner/prepare-task.js +41 -23
  226. package/dist/core/runner/prepare-turn-wiring.d.ts +13 -15
  227. package/dist/core/runner/prepare-turn-wiring.js +29 -27
  228. package/dist/core/runner/prepare-wiring-manifest.d.ts +13 -9
  229. package/dist/core/runner/prepare-wiring-manifest.js +14 -11
  230. package/dist/core/runner/resume-admission.d.ts +4 -1
  231. package/dist/core/runner/resume-admission.js +7 -5
  232. package/dist/core/runner/resume-apply.d.ts +5 -2
  233. package/dist/core/runner/resume-apply.js +24 -42
  234. package/dist/core/runner/resume-checkpoint-screen.d.ts +1 -0
  235. package/dist/core/runner/resume-checkpoint-screen.js +9 -1
  236. package/dist/core/runner/resume-internals-and-config.d.ts +3 -3
  237. package/dist/core/runner/resume-internals-and-config.js +3 -8
  238. package/dist/core/runner/resume-preflight.js +38 -16
  239. package/dist/core/runner/retired-runner-deps.d.ts +5 -6
  240. package/dist/core/runner/retired-runner-deps.js +4 -5
  241. package/dist/core/runner/run-brain-sinks.d.ts +3 -2
  242. package/dist/core/runner/run-brain-sinks.js +5 -1
  243. package/dist/core/runner/run-compaction-machinery.d.ts +7 -1
  244. package/dist/core/runner/run-compaction-machinery.js +7 -33
  245. package/dist/core/runner/run-harness-handlers.js +4 -2
  246. package/dist/core/runner/run-identity-wiring.d.ts +3 -1
  247. package/dist/core/runner/run-identity-wiring.js +3 -2
  248. package/dist/core/runner/run-leg.js +103 -95
  249. package/dist/core/runner/run-notification-lane.js +1 -0
  250. package/dist/core/runner/run-recovery-lanes.d.ts +3 -0
  251. package/dist/core/runner/run-recovery-lanes.js +14 -11
  252. package/dist/core/runner/run-settle-and-teardown.js +9 -28
  253. package/dist/core/runner/run-stop-and-final-verify.js +18 -25
  254. package/dist/core/runner/run-terminal-adoption.d.ts +3 -0
  255. package/dist/core/runner/run-terminal-adoption.js +34 -22
  256. package/dist/core/runner/run-tool-mount-facts.js +5 -3
  257. package/dist/core/runner/run-turn-boundary.js +32 -37
  258. package/dist/core/runner/runtask.d.ts +6 -7
  259. package/dist/core/runner/runtask.js +15 -73
  260. package/dist/core/runner/session-rule-policy.d.ts +5 -5
  261. package/dist/core/runner/session-rule-policy.js +13 -8
  262. package/dist/core/runner/side-call-account.d.ts +68 -0
  263. package/dist/core/runner/side-call-account.js +61 -0
  264. package/dist/core/runner/skills-seat.d.ts +15 -0
  265. package/dist/core/runner/skills-seat.js +57 -0
  266. package/dist/core/runner/stream-halt-verbs.js +12 -17
  267. package/dist/core/runner/stream-lifecycle-verbs.js +8 -5
  268. package/dist/core/runner/stream-steer-verb.d.ts +1 -1
  269. package/dist/core/runner/stream-steer-verb.js +20 -38
  270. package/dist/core/runner/sub-agent-deny-lists.d.ts +124 -23
  271. package/dist/core/runner/sub-agent-deny-lists.js +230 -71
  272. package/dist/core/runner/synthetic-tools.d.ts +5 -2
  273. package/dist/core/runner/synthetic-tools.js +2 -12
  274. package/dist/core/runner/tool-end-body.d.ts +5 -6
  275. package/dist/core/runner/tool-end-body.js +6 -4
  276. package/dist/core/runner/tool-not-executed.d.ts +15 -0
  277. package/dist/core/runner/tool-not-executed.js +30 -0
  278. package/dist/core/runner/tool-occurrence.d.ts +8 -7
  279. package/dist/core/runner/tool-occurrence.js +5 -5
  280. package/dist/core/runner/tool-result-media-seat.d.ts +1 -1
  281. package/dist/core/runner-deps.d.ts +43 -36
  282. package/dist/core/safety-merge-corpus.js +18 -2
  283. package/dist/core/secret-env.d.ts +88 -20
  284. package/dist/core/secret-env.js +192 -38
  285. package/dist/core/session-policy-store.d.ts +71 -16
  286. package/dist/core/session-policy-store.js +138 -28
  287. package/dist/core/session-reconcile.d.ts +4 -0
  288. package/dist/core/session-reconcile.js +2 -1
  289. package/dist/core/shell-read-silence.js +3 -32
  290. package/dist/core/side-query.d.ts +5 -3
  291. package/dist/core/skill-grant.d.ts +3 -2
  292. package/dist/core/skill-grant.js +17 -9
  293. package/dist/core/skills-directory.d.ts +31 -11
  294. package/dist/core/skills-directory.js +655 -104
  295. package/dist/core/store-contracts/mailbox-store-contract.js +13 -0
  296. package/dist/core/task-event.d.ts +49 -3
  297. package/dist/core/task-notification.js +2 -2
  298. package/dist/core/task-result.d.ts +8 -0
  299. package/dist/core/task-spec.d.ts +20 -19
  300. package/dist/core/task-stream.d.ts +14 -4
  301. package/dist/core/tighten-task-spec.d.ts +4 -3
  302. package/dist/core/tighten-task-spec.js +2 -4
  303. package/dist/core/tool-check-reading.d.ts +74 -0
  304. package/dist/core/tool-check-reading.js +80 -0
  305. package/dist/core/tool-policy.d.ts +62 -18
  306. package/dist/core/tool-policy.js +86 -15
  307. package/dist/core/tool-registry.d.ts +20 -0
  308. package/dist/core/tool-registry.js +4 -0
  309. package/dist/core/tool-spec.d.ts +10 -6
  310. package/dist/core/tools.js +2 -0
  311. package/dist/core/trace.d.ts +51 -32
  312. package/dist/core/types.d.ts +2 -2
  313. package/dist/core/types.js +1 -1
  314. package/dist/core/unc-spelling.d.ts +10 -0
  315. package/dist/core/unc-spelling.js +3 -0
  316. package/dist/core/untrusted-egress.d.ts +8 -0
  317. package/dist/core/untrusted-egress.js +4 -1
  318. package/dist/core/untrusted-text.d.ts +16 -0
  319. package/dist/core/untrusted-text.js +7 -2
  320. package/dist/core/user-attachment.d.ts +25 -4
  321. package/dist/core/user-attachment.js +63 -42
  322. package/dist/core/wiring-manifest.d.ts +18 -15
  323. package/dist/core/wiring-manifest.js +2 -2
  324. package/dist/engine/compaction/utils.js +1 -2
  325. package/dist/engine/execution-env/node-execution-env.d.ts +4 -3
  326. package/dist/engine/execution-env/symlink-chain.js +1 -1
  327. package/dist/engine/harness/agent-harness.d.ts +1 -1
  328. package/dist/engine/harness/agent-harness.js +5 -4
  329. package/dist/engine/harness/types.d.ts +20 -16
  330. package/dist/engine/harness/types.js +7 -1
  331. package/dist/engine/llm/types.d.ts +12 -7
  332. package/dist/engine/loop/agent-loop.d.ts +12 -1
  333. package/dist/engine/loop/agent-loop.js +18 -6
  334. package/dist/engine/loop/types.d.ts +8 -2
  335. package/dist/engine/lsp/node-lsp-manager.d.ts +2 -2
  336. package/dist/engine/session/import-validate.js +3 -10
  337. package/dist/engine/session/session.d.ts +4 -4
  338. package/dist/engine/session/session.js +4 -4
  339. package/dist/index.d.ts +33 -23
  340. package/dist/index.js +23 -15
  341. package/dist/internal/harness.d.ts +2 -1
  342. package/dist/internal/harness.js +2 -1
  343. package/dist/orchestration/goal.d.ts +24 -1
  344. package/dist/orchestration/goal.js +3 -2
  345. package/dist/orchestration/run-spec.d.ts +4 -6
  346. package/dist/orchestration/run-spec.js +39 -63
  347. package/dist/orchestration/run-workflow-tool.js +1 -2
  348. package/dist/orchestration/workflow.d.ts +11 -3
  349. package/dist/orchestration/workflow.js +11 -2
  350. package/dist/prompt-assembly/artifact-store.d.ts +72 -56
  351. package/dist/prompt-assembly/artifact-store.js +60 -52
  352. package/dist/prompt-assembly/artifact.d.ts +90 -76
  353. package/dist/prompt-assembly/artifact.js +197 -145
  354. package/dist/prompt-assembly/assemble.d.ts +36 -29
  355. package/dist/prompt-assembly/assemble.js +34 -220
  356. package/dist/prompt-assembly/bands.d.ts +20 -0
  357. package/dist/prompt-assembly/bands.js +18 -0
  358. package/dist/prompt-assembly/catalog/constitution.d.ts +23 -0
  359. package/dist/prompt-assembly/catalog/constitution.js +69 -0
  360. package/dist/prompt-assembly/catalog/core-behavior.d.ts +9 -0
  361. package/dist/prompt-assembly/catalog/core-behavior.js +85 -0
  362. package/dist/prompt-assembly/catalog/index.d.ts +11 -0
  363. package/dist/prompt-assembly/catalog/index.js +60 -0
  364. package/dist/prompt-assembly/catalog/memory.d.ts +13 -0
  365. package/dist/prompt-assembly/catalog/memory.js +6 -0
  366. package/dist/prompt-assembly/catalog/modes.d.ts +15 -0
  367. package/dist/prompt-assembly/catalog/modes.js +137 -0
  368. package/dist/prompt-assembly/catalog/role.d.ts +10 -0
  369. package/dist/prompt-assembly/catalog/role.js +157 -0
  370. package/dist/prompt-assembly/catalog/schema.d.ts +138 -0
  371. package/dist/prompt-assembly/catalog/schema.js +25 -0
  372. package/dist/prompt-assembly/catalog/sections.d.ts +9 -0
  373. package/dist/prompt-assembly/catalog/sections.js +98 -0
  374. package/dist/prompt-assembly/catalog/team.d.ts +4 -0
  375. package/dist/prompt-assembly/catalog/team.js +258 -0
  376. package/dist/prompt-assembly/composer.d.ts +26 -28
  377. package/dist/prompt-assembly/composer.js +124 -46
  378. package/dist/prompt-assembly/epoch.d.ts +89 -79
  379. package/dist/prompt-assembly/epoch.js +115 -142
  380. package/dist/prompt-assembly/explain.d.ts +58 -34
  381. package/dist/prompt-assembly/explain.js +21 -24
  382. package/dist/prompt-assembly/overlay.d.ts +137 -0
  383. package/dist/prompt-assembly/overlay.js +339 -0
  384. package/dist/prompt-assembly/renderers.d.ts +21 -0
  385. package/dist/prompt-assembly/renderers.js +39 -0
  386. package/dist/prompt-assembly/section-usage.d.ts +3 -3
  387. package/dist/prompt-assembly/section-usage.js +1 -1
  388. package/dist/prompt-assembly/select.d.ts +71 -0
  389. package/dist/prompt-assembly/select.js +106 -0
  390. package/dist/prompt-assembly/sugar.d.ts +31 -0
  391. package/dist/prompt-assembly/sugar.js +20 -0
  392. package/dist/prompt-assembly/turn-snapshot.d.ts +3 -2
  393. package/dist/prompt-assembly/types.d.ts +45 -148
  394. package/dist/prompts/coordinator.d.ts +2 -21
  395. package/dist/prompts/coordinator.js +3 -255
  396. package/dist/prompts/cowork.d.ts +27 -16
  397. package/dist/prompts/cowork.js +2 -23
  398. package/dist/prompts/default.d.ts +38 -511
  399. package/dist/prompts/default.js +20 -288
  400. package/dist/prompts/supervisor.d.ts +6 -71
  401. package/dist/prompts/supervisor.js +6 -117
  402. package/dist/stores/file/permission-rule-store.d.ts +1 -1
  403. package/dist/stores/file/permission-rule-store.js +2 -1
  404. package/dist/tools/artifact/artifact-tool.js +4 -3
  405. package/dist/tools/fs/bash-readonly-classifier.d.ts +6 -5
  406. package/dist/tools/fs/dir-entries.d.ts +4 -2
  407. package/dist/tools/fs/dir-entries.js +16 -4
  408. package/dist/tools/fs/fs-bash.d.ts +1 -1
  409. package/dist/tools/fs/fs-bash.js +22 -11
  410. package/dist/tools/fs/fs-pdf.js +17 -13
  411. package/dist/tools/fs/fs-read.js +4 -3
  412. package/dist/tools/fs/fs-shared.d.ts +1 -10
  413. package/dist/tools/fs/fs-shared.js +3 -4
  414. package/dist/tools/fs/fs-write.js +2 -1
  415. package/dist/tools/fs/notebook.js +1 -1
  416. package/dist/tools/fs/pdf.d.ts +20 -10
  417. package/dist/tools/fs/pdf.js +19 -10
  418. package/dist/tools/fs/program-read-model.d.ts +68 -8
  419. package/dist/tools/fs/program-read-model.js +112 -33
  420. package/dist/tools/fs/program-read-model.rows.js +30 -10
  421. package/dist/tools/fs/read-deny-home.d.ts +25 -9
  422. package/dist/tools/fs/read-deny-home.js +28 -27
  423. package/dist/tools/fs/read-deny.d.ts +41 -11
  424. package/dist/tools/fs/read-deny.js +51 -5
  425. package/dist/tools/fs/safety.d.ts +4 -26
  426. package/dist/tools/fs/safety.js +10 -32
  427. package/dist/tools/fs/search.js +15 -10
  428. package/dist/tools/fs/shell-read-argv.d.ts +3 -2
  429. package/dist/tools/fs/shell-read-argv.js +118 -38
  430. package/dist/tools/fs/shell-read-establish.d.ts +5 -5
  431. package/dist/tools/fs/shell-read-establish.js +11 -61
  432. package/dist/tools/fs/shell-read-identity.js +6 -3
  433. package/dist/tools/fs/shell-read-judge.d.ts +13 -15
  434. package/dist/tools/fs/shell-read-judge.js +18 -4
  435. package/dist/tools/fs/shell-read-plan.d.ts +2 -2
  436. package/dist/tools/web.js +1 -1
  437. package/package.json +13 -1
  438. package/test/export-surface.snapshot.json +306 -103
  439. package/wire-changes/core@7.52.0.json +5859 -0
  440. package/wire-changes/core@7.53.0.json +1946 -0
  441. package/dist/core/hook-seats.d.ts +0 -66
  442. package/dist/core/hook-seats.js +0 -37
  443. package/dist/prompt-assembly/packs/sema-default.d.ts +0 -2
  444. package/dist/prompt-assembly/packs/sema-default.js +0 -147
  445. package/dist/prompts/simple-sections.d.ts +0 -58
  446. package/dist/prompts/simple-sections.js +0 -43
@@ -1,6 +1,6 @@
1
- import { withArgsReading } from "./effective-path-target.js";
2
- import { attest, attestationOf, decisionText, refuseOutOfContractDecision } from "./tool-policy.js";
3
- import { arbitrateByMode, classifyAsk, fileCommandOptionsSentence, persistedRuleMandateOf, ruleClearanceOf, safetyAxisOf, stampAskOrigin } from "./ask-origin.js";
1
+ import { argsAsTheToolReads, withArgsReading } from "./effective-path-target.js";
2
+ import { attest, attestationOf, decisionText, foldHookAsk, ownArgs, refusalOf, refuseOutOfContractDecision } from "./tool-policy.js";
3
+ import { arbitrateByMode, classifyAsk, decisionAskClassesOf, fileCommandOptionsSentence, persistedRuleMandateOf, ruleClearanceOf, safetyAxisOf, stampAskOrigin } from "./ask-origin.js";
4
4
  import { classifierParseFailureDenyMessage, denialLimitFallbackMessage, rungDidNotRule, unarmedWindow } from "./auto-mode.js";
5
5
  import { classifierNoRulingArm, settleNoRulingAsk } from "./classifier-unavailable-arm.js";
6
6
  import { SETTLEMENT_NOBODY_JUDGED } from "./gate-outcome.js";
@@ -16,12 +16,14 @@ import { catalogRuleFaceOf } from "./tool-registry.js";
16
16
  import { callFaceSeat } from "./tool-roster.js";
17
17
  import { heldBy, wireOf } from "./tool-name-readings.js";
18
18
  import { asksUnstated, modeAcceptsFileCommand, permissionSeatAt, unstatedAskMessage } from "./mode-policy.js";
19
- import { ORG_RULE_DECISION_REASON, ORG_UNAVAILABLE_DECISION_REASON } from "./permission-rule-org.js";
20
- import { exitGate, passAskFace } from "./runner/gate-exit.js";
19
+ import { ORG_RULE_DECISION_REASON, ORG_UNAVAILABLE_DECISION_REASON, orgUnreadableClause } from "./permission-rule-org.js";
20
+ import { exitGate, passAskFace, unownedArgsMessage } from "./runner/gate-exit.js";
21
21
  import { readOrgRuleLane, readPersistedRuleLane } from "./rule-lane-reads.js";
22
22
  import { traceHookCrash } from "./gate-crash-trace.js";
23
23
  import { createGateDeadline, awaitWriteProtectionJudgment, withGateTimeout } from "./gate-bounded-await.js";
24
24
  import { readStationAnswer } from "./shell-read-silence.js";
25
+ import { agentIdOf, judgedInputOf, raiseToolCheck } from "./mods/stations.js";
26
+ import { readToolChecks } from "./tool-check-reading.js";
25
27
  import { policyThrowLine, reportPolicyThrow } from "./runner/policy-throw.js";
26
28
  const QUESTION_TOOL_NAMES = new Set([ASK_USER_QUESTION_TOOL_NAME]);
27
29
  function parkWith(suspendAsk, parkArgs, carry) {
@@ -34,6 +36,38 @@ export async function runGateLanes(pass) {
34
36
  const boundedAwaitDeadlineMs = createGateDeadline(input, notifier);
35
37
  let orgRealApprovalRequired = false;
36
38
  let markedThisRound;
39
+ let approvedWithArgs = false;
40
+ let carriedOwnAsk;
41
+ const takeApprovedEdit = (read) => {
42
+ carriedOwnAsk = read.outstanding ?? (pass.decision.action === "ask" ? pass.decision : undefined);
43
+ pass.decision = read.allow;
44
+ approvedWithArgs = true;
45
+ };
46
+ const safetyOf = (d) => safetyAxisOf({ egress: input.egress, shellGated: input.shellGated, irreversibility: input.irreversibility, probeMandated: d.action === "ask" && d.probeMandated === true, probeUnanswered: pass.probeUnanswered === true, tightened: pass.tightenedBy });
47
+ const realApprovalOf = (d, org) => {
48
+ if (d.action !== "ask" || d.requiresRealApproval !== true)
49
+ return undefined;
50
+ if (d.origin === undefined)
51
+ throw new Error(`a real-approval ask for "${toolName}" reached a park site with no origin word — the origin stamp precedes every park`);
52
+ return { origin: d.origin, ...(org !== undefined ? { org } : {}) };
53
+ };
54
+ const carryOf = (d) => ({
55
+ ...(callSignal !== undefined ? { signal: callSignal } : {}),
56
+ ...(d.action === "ask" && d.denialLimitFallback !== undefined ? { denialLimitFallback: unarmedWindow(d.denialLimitFallback) } : {}),
57
+ ...(d.action === "ask" && d.classifierNoRuling !== undefined ? { classifierNoRuling: d.classifierNoRuling } : {}),
58
+ ...(d.action === "ask" && d.origin !== undefined ? { origin: d.origin } : {}),
59
+ ...(d.action === "ask" && d.askClass !== undefined && d.classes !== undefined ? { askClass: d.askClass, classes: d.classes } : {}),
60
+ ...(d.action === "ask" && d.mandated === true ? { mandated: true, ...(d.mandate !== undefined ? { mandate: d.mandate } : {}) } : {}),
61
+ ...(d.action === "ask" && d.authoredBy === "deployment" ? { authoredBy: "deployment" } : {}),
62
+ });
63
+ const parkAsk = async (d, req, args, safety, liveFaceUnavailable, org) => {
64
+ if (suspendAsk === undefined || d.action !== "ask")
65
+ return undefined;
66
+ const suspended = await parkWith(suspendAsk, [req, args, safety, liveFaceUnavailable, realApprovalOf(d, org), d.allowRuleShadowed, d.decisionReason, d.probeReason, d.probeCause, d.segmentCoverage, d.matchedAskRule, d.probeMandated], carryOf(d));
67
+ if (suspended && "parkFailed" in suspended)
68
+ pass.parkFailed = suspended.parkFailed;
69
+ return suspended && !("parkFailed" in suspended) ? { suspend: suspended, preToolContext: pass.preToolContext } : undefined;
70
+ };
37
71
  const markedUnresolvable = () => (markedThisRound ??= input.isMarkedUnresolvable?.(input.event.toolCallId) === true);
38
72
  const mandateMarksNow = () => ({
39
73
  egress: input.egress,
@@ -75,7 +109,7 @@ export async function runGateLanes(pass) {
75
109
  if (wireOf("lanes.orgContentAskExemption", pass.req) === ASK_USER_QUESTION_TOOL_NAME && input.orgRules.contentAskToolMounted === true)
76
110
  return { decision: current, org: undefined };
77
111
  let decided = current;
78
- const answer = await readOrgRuleLane(input.orgRules, { toolName, args, toolCallId, ...callFaceSeat(pass.req.face) }, input.abortSignal);
112
+ const answer = await readOrgRuleLane(input.orgRules, Object.freeze({ toolName, args, toolCallId, ...callFaceSeat(pass.req.face) }), input.abortSignal);
79
113
  if (answer.status === "unavailable") {
80
114
  orgEvidence = { revisionAbsent: "unavailable", ruleAbsent: "unavailable" };
81
115
  orgRealApprovalRequired = true;
@@ -103,14 +137,14 @@ export async function runGateLanes(pass) {
103
137
  orgTightenCount += 1;
104
138
  pass.deniedBy = "org";
105
139
  pass.denyCause = undefined;
106
- return { decision: { action: "deny", message: `an organization policy rule (${rule}) denies this call`, decisionReason: ORG_RULE_DECISION_REASON }, org: undefined };
140
+ return { decision: refusalOf({ action: "deny", message: `an organization policy rule (${rule}) denies this call${unreadable !== undefined ? `, ${orgUnreadableClause(unreadable)}` : ""}`, decisionReason: ORG_RULE_DECISION_REASON }, args), org: undefined };
107
141
  }
108
142
  if (decided.action === "deny")
109
143
  return { decision: decided, org: undefined };
110
144
  orgTightenCount += 1;
111
145
  orgRealApprovalRequired = true;
112
146
  const orgRuleMessage = unreadable !== undefined
113
- ? `an organization policy rule (${rule}) may reach this call, which could not be read against it (${unreadable}) — a person must decide`
147
+ ? `an organization policy rule (${rule}) may reach this call, ${orgUnreadableClause(unreadable)} — a person must decide`
114
148
  : `an organization policy rule (${rule}) requires approval for this call`;
115
149
  return {
116
150
  decision: decided.action === "ask"
@@ -120,33 +154,74 @@ export async function runGateLanes(pass) {
120
154
  org: "rule",
121
155
  };
122
156
  };
123
- const orgAnswer = await applyOrgLayer(pass.decision, pass.policyRewrite !== undefined ? pass.policyRewrite : pass.currentInput);
157
+ const finalArgs = pass.policyRewrite !== undefined ? pass.policyRewrite : pass.currentInput;
158
+ if (pass.decision.action === "deny")
159
+ pass.decision = refusalOf(pass.decision, finalArgs);
160
+ const orgAnswer = await applyOrgLayer(pass.decision, finalArgs);
124
161
  pass.decision = orgAnswer.decision;
125
162
  const readPersistedRules = (req) => readPersistedRuleLane(input.persistedRules, req, input.abortSignal);
126
- const reread = pass.policyRewrite !== undefined ? withArgsReading(pass.req, pass.policyRewrite, pass.callSignal ?? input.abortSignal) : undefined;
127
- const laneReq = reread !== undefined ? await reread : { ...pass.req, ...(pass.policyRewrite !== undefined ? { args: pass.policyRewrite } : {}) };
163
+ const laneReq = Object.freeze(pass.policyRewrite !== undefined ? await withArgsReading(pass.req, pass.policyRewrite, pass.callSignal ?? input.abortSignal) : { ...pass.req });
128
164
  const laneAnswer = input.persistedRules !== undefined && wireOf("lanes.persistedLaneSkip", pass.req) !== ASK_USER_QUESTION_TOOL_NAME ? await readPersistedRules(laneReq) : undefined;
129
165
  {
130
166
  const tightened = applyPersistedTightening(pass.decision, laneAnswer, laneReq);
131
- pass.decision = tightened.decision;
167
+ pass.decision = tightened.tightened === "deny" ? refusalOf(tightened.decision, laneReq.args) : tightened.decision;
132
168
  if (tightened.tightened === "deny")
133
169
  pass.deniedBy = "persisted_rule";
134
170
  if (tightened.tightened === "deny")
135
171
  pass.denyCause = undefined;
136
172
  const skillRefusal = pass.decision.action === "deny" ? undefined : skillRowRefusal(input.skillGrants, laneReq);
137
173
  if (skillRefusal !== undefined) {
138
- pass.decision = skillRefusal;
174
+ pass.decision = refusalOf(skillRefusal, laneReq.args);
139
175
  pass.deniedBy = "policy";
140
176
  pass.denyCause = undefined;
141
177
  }
142
178
  }
179
+ let settledRefusal;
180
+ const checkTool = async (standing, args, org, rewrite, mayClear) => {
181
+ const agentId = agentIdOf(input.identity);
182
+ const ceiling = org !== undefined ? { ceiling: "ask" } : {};
183
+ const e = { tool: toolName, input: judgedInputOf(args), tool_use_id: toolCallId, ...(agentId !== undefined ? { agentId } : {}), ...ceiling };
184
+ const signal = callSignal ?? input.abortSignal;
185
+ const own = input.modBus;
186
+ settledRefusal = undefined;
187
+ const settleThroughLedger = (settle) => async (ask, call, sig) => {
188
+ const read = ledger.fromDecision(await settle(ask, call, sig));
189
+ if (read.decision.action === "deny")
190
+ settledRefusal = { deniedBy: read.deniedBy ?? "policy", cause: ledger.causeOf(read.decision) };
191
+ return read.decision;
192
+ };
193
+ const chains = [
194
+ ...(own !== undefined ? [{ raise: (p) => raiseToolCheck(own, { ...e }, p, signal), ...(mayClear !== undefined ? { mayClear } : {}) }] : []),
195
+ ...(input.inheritedToolChecks ?? []).map((c) => ({ raise: (p) => raiseToolCheck(c.bus, { ...e }, p, signal, c.judges), settle: settleThroughLedger(c.settle) })),
196
+ ];
197
+ const project = (current, clears) => {
198
+ const reason = decisionText(current);
199
+ const said = reason !== undefined ? { reason } : {};
200
+ return current.action === "ask" ? { decision: "ask", ...said, classes: [...(current.classes ?? [])], mandated: clears?.() !== true, ...ceiling } : { decision: "allow", ...said, ...ceiling };
201
+ };
202
+ return await readToolChecks(chains, standing, { toolName, judged: args, rewrite, request: Object.freeze({ ...pass.req, args }), signal }, project);
203
+ };
204
+ const refuseByExtension = (deny) => {
205
+ pass.decision = deny;
206
+ pass.deniedBy = settledRefusal?.deniedBy ?? "hook";
207
+ pass.denyCause = settledRefusal?.cause;
208
+ };
209
+ if (pass.decision.action === "allow") {
210
+ const read = await checkTool(pass.decision, finalArgs, orgAnswer.org, pass.policyRewrite);
211
+ if (read !== undefined)
212
+ pass.toolCheckRaised = true;
213
+ if (read?.kind === "denied")
214
+ refuseByExtension(read.deny);
215
+ else if (read?.kind === "asked")
216
+ pass.decision = read.ask;
217
+ else if (read?.kind === "approved")
218
+ takeApprovedEdit(read);
219
+ }
143
220
  if (pass.decision.action === "ask") {
144
221
  pass.decision = { ...pass.decision };
145
222
  if (pass.policyRewrite !== undefined) {
146
223
  pass.currentInput = pass.policyRewrite;
147
- pass.req.args = pass.policyRewrite;
148
- if (laneReq.targetReading !== undefined)
149
- pass.req.targetReading = laneReq.targetReading;
224
+ pass.req = Object.freeze({ ...pass.req, args: pass.policyRewrite, ...(laneReq.targetReading !== undefined ? { targetReading: laneReq.targetReading } : {}) });
150
225
  }
151
226
  const ruleMayClear = () => ruleClearanceOf(pass.decision.action === "ask" ? pass.decision : undefined, mandateMarksNow()).ruleMayClear;
152
227
  const classMayClear = () => pass.decision.action === "ask" && classifyAsk(pass.decision, askOriginFacts(orgAnswer.org, laneAnswer)).row.ruleMayClear;
@@ -194,7 +269,7 @@ export async function runGateLanes(pass) {
194
269
  });
195
270
  const storedAllows = laneAnswer?.hit?.behavior === "allow" ? laneAnswer.hit.rules : undefined;
196
271
  const members = [
197
- ["hook", () => (pass.hookAllowed === true && pass.policyRewrite === undefined ? { entries: [], clear: () => ({ action: "allow", message: "a PreToolUse hook allowed this call", decisionReason: "hook" }), afterClear: async () => undefined } : undefined)],
272
+ ["hook", () => (pass.hookAllowedBy !== undefined && pass.policyRewrite === undefined ? { entries: pass.hookAllowedBy, clear: () => ({ action: "allow", message: "a PreToolUse hook allowed this call", decisionReason: "hook" }), afterClear: async () => undefined } : undefined)],
198
273
  ["deployment", () => {
199
274
  const hit = input.deploymentAllows?.allowing(pass.req, mode);
200
275
  return hit && { entries: hit.entries, clear: () => listAllow("deployment_rule", "the deployment's", hit.entries), afterClear: () => notifier.notifyAsync(() => input.deploymentAllows?.onAllowed?.({ toolName: pass.req.toolName, toolCallId, entries: hit.entries }), "toolGate.allowedToolsResolved") };
@@ -268,6 +343,24 @@ export async function runGateLanes(pass) {
268
343
  pass.decision = { ...pass.decision, message: CD_GIT_COMPOUND_SENTENCE };
269
344
  }
270
345
  }
346
+ if (pass.toolCheckRaised !== true && pass.decision.action !== "deny") {
347
+ const read = await checkTool(pass.decision, pass.currentInput, orgAnswer.org, pass.policyRewrite, () => allowLayerMayClear() && ruleMayClear() && classMayClear());
348
+ if (read?.kind === "denied")
349
+ refuseByExtension(read.deny);
350
+ else if (read?.kind === "cleared")
351
+ pass.decision = read.allow;
352
+ else if (read?.kind === "asked") {
353
+ const asked = read.minted ? { ...read.ask, ruleEvidence: mintRuleEvidence(personalEvidence) } : read.ask;
354
+ if (read.marked === true)
355
+ markedThisRound = undefined;
356
+ const facts = read.marked === true ? askOriginFacts(orgAnswer.org, laneAnswer) : originFacts;
357
+ pass.decision = stampAskOrigin(asked, facts, classifyStanding(asked, facts));
358
+ }
359
+ else if (read?.kind === "shadowed" && pass.decision.action === "ask")
360
+ pass.decision = { ...pass.decision, allowRuleShadowed: [...(pass.decision.allowRuleShadowed ?? []), ...read.shadows] };
361
+ else if (read?.kind === "approved")
362
+ takeApprovedEdit(read);
363
+ }
271
364
  if (pass.decision.action === "ask")
272
365
  ledger.supersede();
273
366
  if (input.autoMode && pass.decision.action === "ask" && pass.decision.origin !== undefined && pass.askClassification?.row.classifierEligible === true && (input.permissionMode === undefined || input.permissionMode() === "auto")) {
@@ -296,7 +389,7 @@ export async function runGateLanes(pass) {
296
389
  pass.classifierRound = undefined;
297
390
  }
298
391
  else if (arm?.kind === "denied")
299
- pass.decision = arm.deny;
392
+ pass.decision = refusalOf(arm.deny, finalArgs);
300
393
  else {
301
394
  const reason = verdict.kind === "block" ? (verdict.reason ? inlineUntrusted(verdict.reason) : "") : classifierParseFailureDenyMessage(verdict.classifier);
302
395
  const category = verdict.kind === "block" && verdict.category ? inlineUntrusted(verdict.category) : "";
@@ -310,7 +403,7 @@ export async function runGateLanes(pass) {
310
403
  message: verdict.kind === "block" ? `auto-mode classifier blocked this call${reason ? `: ${reason}` : category ? `: [${category}]` : ""}` : reason,
311
404
  decisionReason: "classifier",
312
405
  };
313
- pass.decision = verdict.kind === "parse_error" ? attest(denied, pass.req, { classifierCause: "parse_error" }) : denied;
406
+ pass.decision = refusalOf(verdict.kind === "parse_error" ? attest(denied, pass.req, { classifierCause: "parse_error" }) : denied, finalArgs);
314
407
  }
315
408
  }
316
409
  }
@@ -373,86 +466,46 @@ export async function runGateLanes(pass) {
373
466
  pass.arbitration = verdict;
374
467
  pass.deniedBy = "mode";
375
468
  pass.denyCause = undefined;
376
- pass.decision = {
469
+ pass.decision = refusalOf({
377
470
  action: "deny",
378
471
  message: verdict.mode === "dontAsk"
379
472
  ? `refused by the dontAsk permission mode: this call needed approval (${verdict.askClass}) and the mode answers no ask; run under a mode with an approver, or change the call`
380
473
  : `refused by the bypassPermissions permission mode: the write-protection judge could not resolve this write's target, and with nobody to ask the mode refuses rather than releases it`,
381
474
  decisionReason: "mode",
382
- };
475
+ }, finalArgs);
383
476
  }
384
477
  }
385
- const safety = safetyAxisOf({
386
- egress: input.egress,
387
- shellGated: input.shellGated,
388
- irreversibility: input.irreversibility,
389
- probeMandated: pass.decision.action === "ask" && pass.decision.probeMandated === true,
390
- probeUnanswered: pass.probeUnanswered === true,
391
- tightened: pass.tightenedBy,
392
- });
393
- const realApprovalOf = (d) => {
394
- if (d.action !== "ask" || d.requiresRealApproval !== true)
395
- return undefined;
396
- if (d.origin === undefined)
397
- throw new Error(`a real-approval ask for "${toolName}" reached a park site with no origin word — the origin stamp precedes every park`);
398
- return { origin: d.origin, ...(originFacts.org !== undefined ? { org: originFacts.org } : {}) };
399
- };
400
- const carryOf = (d) => ({
401
- ...(callSignal !== undefined ? { signal: callSignal } : {}),
402
- ...(d.action === "ask" && d.denialLimitFallback !== undefined ? { denialLimitFallback: unarmedWindow(d.denialLimitFallback) } : {}),
403
- ...(d.action === "ask" && d.classifierNoRuling !== undefined ? { classifierNoRuling: d.classifierNoRuling } : {}),
404
- ...(d.action === "ask" && d.origin !== undefined ? { origin: d.origin } : {}),
405
- ...(d.action === "ask" && d.askClass !== undefined && d.classes !== undefined ? { askClass: d.askClass, classes: d.classes } : {}),
406
- ...(d.action === "ask" && d.mandated === true ? { mandated: true, ...(d.mandate !== undefined ? { mandate: d.mandate } : {}) } : {}),
407
- ...(d.action === "ask" && d.authoredBy === "deployment" ? { authoredBy: "deployment" } : {}),
408
- });
478
+ const safety = safetyOf(pass.decision);
409
479
  if (suspendAsk && pass.decision.action === "ask") {
410
- const parkArgs = [pass.req, pass.currentInput, safety, undefined, realApprovalOf(pass.decision), pass.decision.action === "ask" ? pass.decision.allowRuleShadowed : undefined, pass.decision.action === "ask" ? pass.decision.decisionReason : undefined, pass.decision.action === "ask" ? pass.decision.probeReason : undefined, pass.decision.action === "ask" ? pass.decision.probeCause : undefined, pass.decision.action === "ask" ? pass.decision.segmentCoverage : undefined, pass.decision.action === "ask" ? pass.decision.matchedAskRule : undefined, pass.decision.action === "ask" ? pass.decision.probeMandated : undefined];
411
- const suspended = await parkWith(suspendAsk, parkArgs, carryOf(pass.decision));
412
- if (suspended) {
413
- if ("parkFailed" in suspended)
414
- pass.parkFailed = suspended.parkFailed;
415
- else
416
- return { suspend: suspended, preToolContext: pass.preToolContext };
417
- }
480
+ const parked = await parkAsk(pass.decision, pass.req, pass.currentInput, safety, undefined, originFacts.org);
481
+ if (parked)
482
+ return parked;
418
483
  }
419
484
  if (pass.decision.action === "ask" && wireOf("lanes.contentAskRoute", pass.req) === ASK_USER_QUESTION_TOOL_NAME) {
420
485
  const outcome = input.resolveContentAsk !== undefined ? await (callSignal !== undefined ? input.resolveContentAsk(pass.req, callSignal) : input.resolveContentAsk(pass.req)) : { kind: "unavailable", parkDeclined: false };
421
486
  if (outcome.kind === "answered") {
422
- pass.decision = { action: "allow", updatedInput: outcome.presentedInput };
487
+ pass.decision = { action: "allow" };
423
488
  }
424
489
  else if (outcome.kind === "unavailable") {
425
- if (outcome.presentedInput !== undefined) {
426
- pass.currentInput = outcome.presentedInput;
427
- pass.req.args = outcome.presentedInput;
428
- }
429
490
  if (suspendAsk && outcome.parkDeclined && pass.parkFailed === undefined) {
430
- const parkArgs = [pass.req, pass.currentInput, safety, true, realApprovalOf(pass.decision), pass.decision.action === "ask" ? pass.decision.allowRuleShadowed : undefined, pass.decision.action === "ask" ? pass.decision.decisionReason : undefined, pass.decision.action === "ask" ? pass.decision.probeReason : undefined, pass.decision.action === "ask" ? pass.decision.probeCause : undefined, pass.decision.action === "ask" ? pass.decision.segmentCoverage : undefined, pass.decision.action === "ask" ? pass.decision.matchedAskRule : undefined, pass.decision.action === "ask" ? pass.decision.probeMandated : undefined];
431
- const suspended = await parkWith(suspendAsk, parkArgs, carryOf(pass.decision));
432
- if (suspended) {
433
- if ("parkFailed" in suspended)
434
- pass.parkFailed = suspended.parkFailed;
435
- else
436
- return { suspend: suspended, preToolContext: pass.preToolContext };
437
- }
491
+ const parked = await parkAsk(pass.decision, pass.req, pass.currentInput, safety, true, originFacts.org);
492
+ if (parked)
493
+ return parked;
438
494
  }
439
495
  if (pass.decision.origin === undefined)
440
496
  throw new Error(`the content ask for "${toolName}" reached its refusal without an origin word`);
441
497
  ledger.set({ settlement: { kind: input.resolveContentAsk !== undefined ? "approver_unavailable" : "no_approver", who: { party: "none" }, when: Date.now() }, origin: pass.decision.origin });
442
498
  pass.deniedBy = "ask_resolution";
443
- pass.decision = {
499
+ pass.decision = refusalOf({
444
500
  action: "deny",
445
501
  message: "AskUserQuestion could not be parked for a durable human answer on this path (no checkpoint " +
446
502
  "facility, or the suspend failed) and a synchronous permission approver cannot carry an answer — " +
447
503
  "the question was NOT shown to anyone. Proceed with your best judgment and state the assumption " +
448
504
  "you made.",
449
- };
505
+ }, finalArgs);
450
506
  }
451
507
  else {
452
- if (outcome.presentedInput !== undefined)
453
- pass.decision = { action: "allow", updatedInput: outcome.presentedInput };
454
- else
455
- pass.decision = { action: "allow" };
508
+ pass.decision = { action: "allow" };
456
509
  }
457
510
  }
458
511
  if (pass.decision.action === "ask") {
@@ -467,16 +520,11 @@ export async function runGateLanes(pass) {
467
520
  resolved = ledger.fromResolved(resolved, askBeforeResolve, pass.req);
468
521
  if (resolved.action === "deny")
469
522
  pass.deniedBy = "ask_resolution";
470
- pass.decision = resolved;
523
+ pass.decision = resolved.action === "deny" ? refusalOf(resolved, finalArgs) : resolved;
471
524
  if (resolved.action === "deny" && resolved.approverUnavailable === true && suspendAsk && pass.parkFailed === undefined) {
472
- const parkArgs = [pass.req, pass.currentInput, safety, true, realApprovalOf(askBeforeResolve), askBeforeResolve.action === "ask" ? askBeforeResolve.allowRuleShadowed : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.decisionReason : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.probeReason : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.probeCause : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.segmentCoverage : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.matchedAskRule : undefined, askBeforeResolve.action === "ask" ? askBeforeResolve.probeMandated : undefined];
473
- const suspended = await parkWith(suspendAsk, parkArgs, carryOf(askBeforeResolve));
474
- if (suspended) {
475
- if ("parkFailed" in suspended)
476
- pass.parkFailed = suspended.parkFailed;
477
- else
478
- return { suspend: suspended, preToolContext: pass.preToolContext };
479
- }
525
+ const parked = await parkAsk(askBeforeResolve, pass.req, pass.currentInput, safety, true, originFacts.org);
526
+ if (parked)
527
+ return parked;
480
528
  }
481
529
  if (askBeforeResolve.action === "ask" && askBeforeResolve.denialLimitFallback !== undefined) {
482
530
  if (pass.decision.action === "allow") {
@@ -493,211 +541,247 @@ export async function runGateLanes(pass) {
493
541
  }
494
542
  }
495
543
  }
496
- if (pass.decision.action === "allow" && pass.decision.updatedInput !== undefined) {
497
- let editArgs = pass.decision.updatedInput;
498
- let editDenied;
499
- let editRewrittenSinceHuman = false;
500
- for (let round = 0;; round++) {
501
- if (round >= 3) {
502
- editDenied = {
503
- action: "deny",
504
- message: `the approval-edit chain for "${toolName}" exceeded the re-approval cap — denied fail-closed; re-submit the edited action directly`,
505
- };
506
- pass.deniedBy = "policy";
507
- break;
508
- }
509
- if (screening !== undefined) {
510
- let hr;
511
- let hrUnanswered;
512
- try {
513
- const seat = await screening.screen(editArgs);
514
- if (seat.expired)
515
- hrUnanswered = seat.cause;
516
- else
517
- hr = screening.screened(seat.value);
518
- }
519
- catch (err) {
520
- traceHookCrash(input, err, notifier);
521
- editDenied = { action: "deny", message: screening.crashReason(`the approved edit for "${toolName}"`, err) };
522
- pass.deniedBy = "hook";
523
- break;
524
- }
525
- if (hrUnanswered !== undefined) {
526
- editDenied = { action: "deny", message: await screening.unansweredReason(`the approved edit for "${toolName}"`, hrUnanswered) };
527
- pass.deniedBy = "hook";
528
- break;
529
- }
530
- if (hr) {
531
- if (hr.additionalContext)
532
- pass.preToolContext.push(hr.additionalContext);
533
- if (hr.action === "deny") {
534
- editDenied = { action: "deny", message: decisionText(hr) ?? `the approved edit for "${toolName}" was blocked by a PreToolUse hook` };
535
- pass.deniedBy = "hook";
536
- break;
537
- }
538
- if (hr.action === "ask") {
539
- editDenied = {
540
- action: "deny",
541
- message: `the approved edit for "${toolName}" raises a new PreToolUse approval requirement the original approval does not cover — denied fail-closed; re-submit the edited action directly`,
542
- };
543
- pass.deniedBy = "hook";
544
- break;
545
- }
546
- if (hr.updatedInput !== undefined) {
547
- editArgs = hr.updatedInput;
548
- editRewrittenSinceHuman = true;
549
- }
550
- }
551
- }
552
- let recheck = { action: "allow" };
553
- if (adjudicate) {
554
- try {
555
- const editReq = { toolName, args: editArgs, toolCallId, ...(pass.req.face !== undefined ? { face: pass.req.face } : {}) };
556
- recheck = refuseOutOfContractDecision(await (callSignal !== undefined ? adjudicate(editReq, callSignal) : adjudicate(editReq)));
557
- }
558
- catch (err) {
559
- reportPolicyThrow((e) => traceHookCrash(input, e, notifier), "the tool policy's re-check of the approved edit", { toolName, toolCallId }, err, callSignal ?? input.abortSignal);
560
- recheck = {
561
- action: "deny",
562
- message: `policy re-check of the approved edit for "${toolName}" errored: ${policyThrowLine(err)}`,
563
- };
564
- }
565
- }
566
- {
567
- const attributed = ledger.classifierRoundOf(recheck);
568
- if (attributed !== undefined)
569
- pass.classifierRound = attributed;
570
- const read = ledger.fromDecision(recheck);
571
- recheck = read.decision;
572
- if (recheck.action === "deny" && read.deniedBy !== undefined) {
573
- editDenied = recheck;
574
- pass.deniedBy = read.deniedBy;
575
- pass.denyCause = ledger.causeOf(recheck);
576
- break;
577
- }
578
- }
579
- if (recheck.updatedInput !== undefined) {
580
- editArgs = recheck.updatedInput;
581
- editRewrittenSinceHuman = true;
582
- }
583
- const editOrg = await applyOrgLayer(recheck, editArgs);
584
- recheck = editOrg.decision;
585
- if (recheck.action === "deny") {
586
- editDenied = recheck;
587
- break;
588
- }
589
- let editLane;
590
- const editReread = withArgsReading(pass.req, editArgs, callSignal ?? input.abortSignal);
591
- const editLaneReq = editReread !== undefined ? await editReread : { toolName, args: editArgs, toolCallId, ...(pass.req.face !== undefined ? { face: pass.req.face } : {}) };
592
- if (input.persistedRules !== undefined && wireOf("lanes.persistedEditSkip", pass.req) !== ASK_USER_QUESTION_TOOL_NAME) {
593
- editLane = await readPersistedRules(editLaneReq);
594
- const editTightened = applyPersistedTightening(recheck, editLane, editLaneReq);
595
- recheck = editTightened.decision;
596
- if (editTightened.tightened === "deny")
597
- pass.deniedBy = "persisted_rule";
598
- if (recheck.action === "deny") {
599
- editDenied = recheck;
600
- break;
601
- }
602
- }
603
- const editSkillRefusal = skillRowRefusal(input.skillGrants, editLaneReq);
604
- if (editSkillRefusal !== undefined) {
605
- editDenied = editSkillRefusal;
606
- pass.deniedBy = "policy";
544
+ approvedWithArgs = pass.decision.action === "allow" && pass.decision.updatedInput !== undefined;
545
+ }
546
+ }
547
+ if (approvedWithArgs && pass.decision.action === "allow" && pass.decision.updatedInput !== undefined) {
548
+ let editArgs = pass.decision.updatedInput;
549
+ let editDenied;
550
+ let editRewrittenSinceHuman = false;
551
+ let unanswered;
552
+ const refusedAtResolution = (d) => { editDenied = d; pass.deniedBy = "ask_resolution"; };
553
+ for (let round = 0;; round++) {
554
+ const taken = ownArgs(editArgs);
555
+ if (!taken.ok) {
556
+ editDenied = { action: "deny", message: unownedArgsMessage(`the approved edit for "${toolName}"`, taken.reason) };
557
+ pass.deniedBy = "policy";
558
+ break;
559
+ }
560
+ editArgs = argsAsTheToolReads(pass.req, taken.value);
561
+ if (round >= 3) {
562
+ editDenied = {
563
+ action: "deny",
564
+ message: `the approval-edit chain for "${toolName}" exceeded the re-approval cap — denied fail-closed; re-submit the edited action directly`,
565
+ };
566
+ pass.deniedBy = "policy";
567
+ break;
568
+ }
569
+ let editHookAsk;
570
+ if (screening !== undefined) {
571
+ const screened = await screening.screen(editArgs, `the approved edit for "${toolName}"`);
572
+ if (screened.kind === "refused") {
573
+ editDenied = { action: "deny", message: screened.reason };
574
+ pass.deniedBy = "hook";
575
+ break;
576
+ }
577
+ const hr = screened.answer;
578
+ if (hr) {
579
+ if (hr.additionalContext)
580
+ pass.preToolContext.push(hr.additionalContext);
581
+ if (hr.action === "deny") {
582
+ editDenied = { action: "deny", message: decisionText(hr) ?? `the approved edit for "${toolName}" was blocked by a PreToolUse hook` };
583
+ pass.deniedBy = "hook";
607
584
  break;
608
585
  }
609
- if (recheck.action === "allow") {
610
- if (recheck.updatedInput !== undefined) {
611
- editArgs = recheck.updatedInput;
612
- editRewrittenSinceHuman = true;
613
- }
614
- if (!editRewrittenSinceHuman || !asksUnstated(recheck, permissionSeatAt(input, editArgs)?.seat, input.permissionMode?.()))
615
- break;
616
- recheck = { action: "ask", message: permissionSeatAt(input, editArgs)?.question ?? unstatedAskMessage(toolName) };
617
- pass.tightenedBy = "unstated";
586
+ if (hr.action === "ask") {
587
+ const { updatedInput: _adopted, ...ask } = hr;
588
+ editHookAsk = ask;
618
589
  }
619
- if (recheck.updatedInput !== undefined) {
620
- editArgs = recheck.updatedInput;
590
+ if (hr.updatedInput !== undefined) {
591
+ editArgs = argsAsTheToolReads(pass.req, hr.updatedInput);
621
592
  editRewrittenSinceHuman = true;
622
593
  }
623
- const editAskSnapshot = { ...recheck, ruleEvidence: mintRuleEvidence({ dotsAbsent: "not_adjudicated" }) };
594
+ }
595
+ }
596
+ let recheck = { action: "allow" };
597
+ if (adjudicate) {
598
+ try {
599
+ const editReq = Object.freeze({ toolName, args: editArgs, toolCallId, ...(pass.req.face !== undefined ? { face: pass.req.face } : {}) });
600
+ recheck = refuseOutOfContractDecision(await (callSignal !== undefined ? adjudicate(editReq, callSignal) : adjudicate(editReq)));
601
+ }
602
+ catch (err) {
603
+ reportPolicyThrow((e) => traceHookCrash(input, e, notifier), "the tool policy's re-check of the approved edit", { toolName, toolCallId }, err, callSignal ?? input.abortSignal);
604
+ recheck = {
605
+ action: "deny",
606
+ message: `policy re-check of the approved edit for "${toolName}" errored: ${policyThrowLine(err)}`,
607
+ };
608
+ }
609
+ }
610
+ {
611
+ const attributed = ledger.classifierRoundOf(recheck);
612
+ if (attributed !== undefined)
613
+ pass.classifierRound = attributed;
614
+ const read = ledger.fromDecision(recheck);
615
+ recheck = read.decision;
616
+ if (recheck.action === "deny" && read.deniedBy !== undefined) {
617
+ editDenied = recheck;
618
+ pass.deniedBy = read.deniedBy;
619
+ pass.denyCause = ledger.causeOf(recheck);
620
+ break;
621
+ }
622
+ }
623
+ if (recheck.updatedInput !== undefined) {
624
+ editArgs = argsAsTheToolReads(pass.req, recheck.updatedInput);
625
+ editRewrittenSinceHuman = true;
626
+ }
627
+ const editOrg = await applyOrgLayer(recheck, editArgs);
628
+ recheck = editOrg.decision;
629
+ if (recheck.action === "deny") {
630
+ editDenied = recheck;
631
+ break;
632
+ }
633
+ let editLane;
634
+ const editLaneReq = Object.freeze(await withArgsReading(pass.req, editArgs, callSignal ?? input.abortSignal));
635
+ if (input.persistedRules !== undefined && wireOf("lanes.persistedEditSkip", pass.req) !== ASK_USER_QUESTION_TOOL_NAME) {
636
+ editLane = await readPersistedRules(editLaneReq);
637
+ const editTightened = applyPersistedTightening(recheck, editLane, editLaneReq);
638
+ recheck = editTightened.decision;
639
+ if (editTightened.tightened === "deny")
640
+ pass.deniedBy = "persisted_rule";
641
+ if (recheck.action === "deny") {
642
+ editDenied = recheck;
643
+ break;
644
+ }
645
+ }
646
+ const editSkillRefusal = skillRowRefusal(input.skillGrants, editLaneReq);
647
+ if (editSkillRefusal !== undefined) {
648
+ editDenied = editSkillRefusal;
649
+ pass.deniedBy = "policy";
650
+ break;
651
+ }
652
+ if (recheck.action === "allow") {
653
+ if (recheck.updatedInput !== undefined) {
654
+ editArgs = argsAsTheToolReads(pass.req, recheck.updatedInput);
655
+ editRewrittenSinceHuman = true;
656
+ }
657
+ if (editRewrittenSinceHuman && asksUnstated(recheck, permissionSeatAt(input, editArgs)?.seat, input.permissionMode?.())) {
658
+ recheck = { action: "ask", message: permissionSeatAt(input, editArgs)?.question ?? unstatedAskMessage(toolName) };
659
+ pass.tightenedBy = "unstated";
660
+ }
661
+ }
662
+ if (recheck.updatedInput !== undefined) {
663
+ editArgs = argsAsTheToolReads(pass.req, recheck.updatedInput);
664
+ editRewrittenSinceHuman = true;
665
+ }
666
+ let editFacts;
667
+ const stampEditAsk = (ask) => {
668
+ const editAskSnapshot = { ...ask, ruleEvidence: mintRuleEvidence({ dotsAbsent: "not_adjudicated" }) };
669
+ if (editFacts === undefined) {
624
670
  markedThisRound = undefined;
625
- const editFacts = askOriginFacts(editOrg.org, editLane);
626
- const editAskDecision = stampAskOrigin(editAskSnapshot, editFacts, classifyStanding(editAskSnapshot, editFacts));
627
- if (input.permissionMode !== undefined && pass.askClassification !== undefined) {
628
- const editVerdict = arbitrateByMode(input.permissionMode(), pass.askClassification, { ...(editAskDecision.origin !== undefined ? { origin: editAskDecision.origin } : {}), ...(editAskDecision.mandate !== undefined ? { mandate: editAskDecision.mandate } : {}) });
629
- if (editVerdict.kind === "released") {
630
- ledger.supersede();
631
- pass.arbitration = editVerdict;
632
- await notifier.notifyAsync(() => input.onModeReleased?.({ toolName, toolCallId, release: { mode: editVerdict.mode, askClass: editVerdict.askClass, classes: editVerdict.classes, ...(editVerdict.origin !== undefined ? { origin: editVerdict.origin } : {}), ...(editVerdict.mandate !== undefined ? { mandate: editVerdict.mandate } : {}), ...(editVerdict.reason !== undefined ? { reason: editVerdict.reason } : {}) }, ...(pass.shellReadUnestablished === true ? { readUnestablished: true } : {}) }), "toolGate.onModeReleased");
633
- break;
634
- }
635
- if (editVerdict.kind === "denied_by_mode") {
636
- ledger.supersede();
637
- pass.arbitration = editVerdict;
638
- editDenied = { action: "deny", message: `the approved edit for "${toolName}" raised a new approval requirement that the ${editVerdict.mode} permission mode refuses`, decisionReason: "mode" };
639
- pass.deniedBy = "mode";
640
- break;
641
- }
642
- }
643
- const editAskReq = { toolName, args: editArgs, toolCallId, ...(pass.req.face !== undefined ? { face: pass.req.face } : {}) };
644
- const rr = ledger.fromResolved(await (callSignal !== undefined ? resolveAsk(editAskDecision, editAskReq, callSignal) : resolveAsk(editAskDecision, editAskReq)), editAskDecision, editAskReq);
645
- if (rr.action !== "allow") {
646
- editDenied = rr;
647
- pass.deniedBy = "ask_resolution";
648
- break;
649
- }
650
- if (rr.updatedInput === undefined) {
651
- if (rr.presentedInput !== undefined)
652
- editArgs = rr.presentedInput;
653
- editRewrittenSinceHuman = false;
654
- break;
655
- }
656
- editArgs = rr.updatedInput;
657
- editRewrittenSinceHuman = false;
671
+ editFacts = askOriginFacts(editOrg.org, editLane);
658
672
  }
659
- if (editDenied === undefined && editRewrittenSinceHuman && input.writeProtectionCheck !== undefined) {
660
- const check = input.writeProtectionCheck;
661
- const verdict = await awaitWriteProtectionJudgment((deadline) => check(toolName, editArgs, pass.req.face, input.trackedCwd?.(), deadline), boundedAwaitDeadlineMs, callSignal ?? input.abortSignal);
662
- if (verdict !== undefined && verdict.kind !== "clear") {
663
- editDenied = {
664
- action: "deny",
665
- message: verdict.kind === "hit"
666
- ? `the approved edit for "${toolName}" was rewritten by the restriction chain onto a write-protected path (table entry "${verdict.hit.name}") that no approval covers — denied fail-closed; re-submit the edited action directly`
667
- : `the approved edit for "${toolName}" was rewritten by the restriction chain onto a target whose destination could not be determined (target_unresolved: ${verdict.cause}) — denied fail-closed; re-submit the edited action directly`,
668
- };
669
- pass.deniedBy = "write_protection";
670
- }
673
+ return stampAskOrigin(editAskSnapshot, editFacts, classifyStanding(editAskSnapshot, editFacts));
674
+ };
675
+ if (editHookAsk !== undefined)
676
+ recheck = foldHookAsk(recheck, editHookAsk);
677
+ let editDecision = recheck.action === "ask" ? stampEditAsk(recheck) : recheck;
678
+ if (carriedOwnAsk !== undefined) {
679
+ const { updatedInput: _theOriginalBytes, ...carried } = carriedOwnAsk;
680
+ const rra = carried.requiresRealApproval === true ? { requiresRealApproval: true } : {};
681
+ editDecision = stampEditAsk(editDecision.action === "ask" ? { ...editDecision, foldedAskClasses: [...(editDecision.foldedAskClasses ?? []), ...decisionAskClassesOf(carried), ...(carried.classes ?? [])], ...rra } : carried);
682
+ carriedOwnAsk = undefined;
683
+ }
684
+ const editRead = await checkTool(editDecision, editArgs, editOrg.org, undefined);
685
+ if (editRead?.kind === "denied") {
686
+ refuseByExtension(editRead.deny);
687
+ editDenied = editRead.deny;
688
+ break;
689
+ }
690
+ if (editRead?.kind === "approved") {
691
+ carriedOwnAsk = editRead.outstanding ?? (editDecision.action === "ask" ? editDecision : undefined);
692
+ editArgs = editRead.allow.updatedInput;
693
+ editRewrittenSinceHuman = false;
694
+ continue;
695
+ }
696
+ if (editRead?.kind === "asked" && editRead.marked === true)
697
+ editFacts = undefined;
698
+ if (editRead?.kind === "asked")
699
+ editDecision = stampEditAsk(editRead.ask);
700
+ else if (editRead?.kind === "shadowed" && editDecision.action === "ask")
701
+ editDecision = { ...editDecision, allowRuleShadowed: [...(editDecision.allowRuleShadowed ?? []), ...editRead.shadows] };
702
+ if (editDecision.action !== "ask")
703
+ break;
704
+ const editAskDecision = editDecision;
705
+ if (input.permissionMode !== undefined && pass.askClassification !== undefined) {
706
+ const editVerdict = arbitrateByMode(input.permissionMode(), pass.askClassification, { ...(editAskDecision.origin !== undefined ? { origin: editAskDecision.origin } : {}), ...(editAskDecision.mandate !== undefined ? { mandate: editAskDecision.mandate } : {}) });
707
+ if (editVerdict.kind === "released") {
708
+ ledger.supersede();
709
+ pass.arbitration = editVerdict;
710
+ await notifier.notifyAsync(() => input.onModeReleased?.({ toolName, toolCallId, release: { mode: editVerdict.mode, askClass: editVerdict.askClass, classes: editVerdict.classes, ...(editVerdict.origin !== undefined ? { origin: editVerdict.origin } : {}), ...(editVerdict.mandate !== undefined ? { mandate: editVerdict.mandate } : {}), ...(editVerdict.reason !== undefined ? { reason: editVerdict.reason } : {}) }, ...(pass.shellReadUnestablished === true ? { readUnestablished: true } : {}) }), "toolGate.onModeReleased");
711
+ break;
671
712
  }
672
- if (editDenied === undefined && input.shellReadCheck !== undefined) {
673
- const station = input.shellReadCheck;
674
- const judged = station.judge(pass.req, editArgs, input.trackedCwd?.(), callSignal ?? input.abortSignal, { seat: "rejudge", toolCallId });
675
- if (judged !== null) {
676
- let verdict;
677
- try {
678
- verdict = await withGateTimeout(judged, boundedAwaitDeadlineMs(), callSignal ?? input.abortSignal, "shellReadStation");
679
- }
680
- catch {
681
- verdict = station.unanswered(pass.req, "the read station could not answer");
682
- }
683
- const reading = readStationAnswer(verdict, { toolName, toolCallId, report: (e) => traceHookCrash(input, e, notifier) });
684
- if (reading.kind !== "vouch") {
685
- editDenied = {
686
- action: "deny",
687
- message: reading.verdict.sentence ?? `the approved edit for "${toolName}" reads where the read boundary does not vouch — denied fail-closed; re-submit the command as a fresh call and answer its card`,
688
- };
689
- pass.deniedBy = "read_boundary";
690
- if (reading.verdict.details !== undefined)
691
- pass.denyDetails = reading.verdict.details;
692
- }
693
- }
713
+ if (editVerdict.kind === "denied_by_mode") {
714
+ ledger.supersede();
715
+ pass.arbitration = editVerdict;
716
+ editDenied = { action: "deny", message: `the approved edit for "${toolName}" raised a new approval requirement that the ${editVerdict.mode} permission mode refuses`, decisionReason: "mode" };
717
+ pass.deniedBy = "mode";
718
+ break;
694
719
  }
695
- pass.decision = editDenied ?? { ...pass.decision, updatedInput: editArgs };
696
720
  }
697
- else if (pass.decision.action === "allow" && pass.decision.updatedInput === undefined && resolved.presentedInput !== undefined) {
698
- pass.decision = { ...pass.decision, updatedInput: resolved.presentedInput };
721
+ const editAskReq = Object.freeze({ toolName, args: editArgs, toolCallId, ...(pass.req.face !== undefined ? { face: pass.req.face } : {}) });
722
+ if (suspendAsk !== undefined && markedUnresolvable()) {
723
+ unanswered = { ask: editAskDecision, req: editAskReq, org: editOrg.org };
724
+ break;
725
+ }
726
+ const rr = ledger.fromResolved(await (callSignal !== undefined ? resolveAsk(editAskDecision, editAskReq, callSignal) : resolveAsk(editAskDecision, editAskReq)), editAskDecision, editAskReq);
727
+ if (rr.action !== "allow") {
728
+ refusedAtResolution(rr);
729
+ if (rr.approverUnavailable === true)
730
+ unanswered = { ask: editAskDecision, req: editAskReq, org: editOrg.org, deny: rr };
731
+ break;
699
732
  }
733
+ if (rr.updatedInput === undefined) {
734
+ editRewrittenSinceHuman = false;
735
+ break;
736
+ }
737
+ editArgs = rr.updatedInput;
738
+ editRewrittenSinceHuman = false;
739
+ }
740
+ const rejudged = () => editDenied === undefined || editDenied === unanswered?.deny;
741
+ if (rejudged() && editRewrittenSinceHuman && input.writeProtectionCheck !== undefined) {
742
+ const check = input.writeProtectionCheck;
743
+ const verdict = await awaitWriteProtectionJudgment((deadline) => check(toolName, editArgs, pass.req.face, input.trackedCwd?.(), deadline), boundedAwaitDeadlineMs, callSignal ?? input.abortSignal);
744
+ if (verdict !== undefined && verdict.kind !== "clear") {
745
+ editDenied = {
746
+ action: "deny",
747
+ message: verdict.kind === "hit"
748
+ ? `the approved edit for "${toolName}" was rewritten by the restriction chain onto a write-protected path (table entry "${verdict.hit.name}") that no approval covers — denied fail-closed; re-submit the edited action directly`
749
+ : `the approved edit for "${toolName}" was rewritten by the restriction chain onto a target whose destination could not be determined (target_unresolved: ${verdict.cause}) — denied fail-closed; re-submit the edited action directly`,
750
+ };
751
+ pass.deniedBy = "write_protection";
752
+ }
753
+ }
754
+ if (rejudged() && input.shellReadCheck !== undefined) {
755
+ const station = input.shellReadCheck;
756
+ const judged = station.judge(pass.req, editArgs, input.trackedCwd?.(), callSignal ?? input.abortSignal, { seat: "rejudge", toolCallId });
757
+ if (judged !== null) {
758
+ let verdict;
759
+ try {
760
+ verdict = await withGateTimeout(judged, boundedAwaitDeadlineMs(), callSignal ?? input.abortSignal, "shellReadStation");
761
+ }
762
+ catch {
763
+ verdict = station.unanswered(pass.req, "the read station could not answer");
764
+ }
765
+ const reading = readStationAnswer(verdict, { toolName, toolCallId, report: (e) => traceHookCrash(input, e, notifier) });
766
+ if (reading.kind !== "vouch") {
767
+ editDenied = {
768
+ action: "deny",
769
+ message: reading.verdict.sentence ?? `the approved edit for "${toolName}" reads where the read boundary does not vouch — denied fail-closed; re-submit the command as a fresh call and answer its card`,
770
+ };
771
+ pass.deniedBy = "read_boundary";
772
+ if (reading.verdict.details !== undefined)
773
+ pass.denyDetails = reading.verdict.details;
774
+ }
775
+ }
776
+ }
777
+ if (unanswered !== undefined && editDenied === unanswered.deny && pass.parkFailed === undefined) {
778
+ const parked = await parkAsk(unanswered.ask, unanswered.req, editArgs, safetyOf(unanswered.ask), unanswered.deny !== undefined || undefined, unanswered.org);
779
+ if (parked)
780
+ return parked;
700
781
  }
782
+ if (unanswered !== undefined && unanswered.deny === undefined && editDenied === undefined)
783
+ refusedAtResolution(ledger.fromResolved(await (callSignal !== undefined ? resolveAsk(unanswered.ask, unanswered.req, callSignal) : resolveAsk(unanswered.ask, unanswered.req)), unanswered.ask, unanswered.req));
784
+ pass.decision = editDenied !== undefined ? refusalOf(editDenied, editArgs) : { ...pass.decision, updatedInput: editArgs };
701
785
  }
702
786
  return await exitGate(pass);
703
787
  }