@iowarp/clio-coder 0.3.4 → 0.3.7

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 (376) hide show
  1. package/CHANGELOG.md +65 -2
  2. package/CONTRIBUTING.md +6 -6
  3. package/README.md +16 -5
  4. package/dist/{acp-S5R4RR5B.js → acp-SK4MD6MM.js} +11 -11
  5. package/dist/{agents-P6DMMVZY.js → agents-2FN2K6ME.js} +33 -26
  6. package/dist/assets/codewiki.json +1 -1
  7. package/dist/{auth-2XCZLPKS.js → auth-QIYZWM5I.js} +15 -15
  8. package/dist/{chunk-EKMEHE4H.js → chunk-33YXPOE3.js} +2 -3
  9. package/dist/{chunk-VAWWTKDP.js → chunk-3HAPLH5M.js} +11 -11
  10. package/dist/{chunk-YCWGATWI.js → chunk-465YSENW.js} +3 -3
  11. package/dist/{chunk-4OC57DA6.js → chunk-4DGYLA73.js} +53 -2
  12. package/dist/{chunk-UZHIZC5S.js → chunk-4DWFMQDR.js} +61 -76
  13. package/dist/{chunk-ZWMF7253.js → chunk-5C3AQNDW.js} +328 -9
  14. package/dist/{chunk-22NAGB7X.js → chunk-5C77SEEY.js} +5 -94
  15. package/dist/{chunk-WPQLXFOZ.js → chunk-5FR74PWO.js} +3 -2
  16. package/dist/{chunk-35MKKU5R.js → chunk-5UJ6ECTS.js} +18 -10
  17. package/dist/{chunk-BRXQQJFP.js → chunk-6M7VS3J3.js} +571 -50
  18. package/dist/{chunk-QQK64KLB.js → chunk-6TUKSZVF.js} +141 -23
  19. package/dist/{chunk-N4CZJQRK.js → chunk-AB4XIIVB.js} +8 -6
  20. package/dist/{chunk-KRPY7NTG.js → chunk-BMWK7ZIZ.js} +14 -20
  21. package/dist/{chunk-4BPJXDWC.js → chunk-C4JBQ5SR.js} +30 -14
  22. package/dist/{chunk-ZYKPLLNQ.js → chunk-CEYBNUGC.js} +821 -83
  23. package/dist/{chunk-VEZEGCGW.js → chunk-D4MDIG46.js} +20 -18
  24. package/dist/chunk-DJNLUABN.js +843 -0
  25. package/dist/{chunk-BP4OYD6A.js → chunk-DMD2AGVS.js} +21 -2
  26. package/dist/{chunk-KOHPCX4K.js → chunk-DOOEX22V.js} +2 -2
  27. package/dist/chunk-DQA7QLMD.js +123 -0
  28. package/dist/chunk-DR52UMZW.js +21 -0
  29. package/dist/{chunk-3HZ5RWN2.js → chunk-EBEFWSGL.js} +9 -7
  30. package/dist/{chunk-EDRHSCIE.js → chunk-EELBMBT6.js} +128 -13
  31. package/dist/{chunk-HV5X7OR2.js → chunk-EOOQZZDE.js} +16 -14
  32. package/dist/{chunk-WR67VIZY.js → chunk-FOT2FX5J.js} +63 -5
  33. package/dist/{chunk-BPGS2WCQ.js → chunk-GEYXPTRF.js} +2 -1
  34. package/dist/{chunk-FYYLNIL5.js → chunk-GH5622CP.js} +2 -2
  35. package/dist/{chunk-BEY543CS.js → chunk-GOXNB3AO.js} +5 -2
  36. package/dist/chunk-GWS3VEIW.js +195 -0
  37. package/dist/{chunk-G4BMMOKF.js → chunk-HVDIIIQW.js} +2 -2
  38. package/dist/chunk-HWUFFB6L.js +83 -0
  39. package/dist/{chunk-X6COSD2O.js → chunk-J7PIKKWC.js} +8 -436
  40. package/dist/{chunk-NILBFAPG.js → chunk-JNXPYBB4.js} +2 -2
  41. package/dist/{chunk-4VP4KH3K.js → chunk-JRIO5UD2.js} +4 -4
  42. package/dist/{chunk-K6WL7QZT.js → chunk-JTSEDYVQ.js} +7 -7
  43. package/dist/{chunk-QKMUKYO7.js → chunk-KCMKRQX4.js} +236 -84
  44. package/dist/chunk-KZ2H5X4G.js +1026 -0
  45. package/dist/{chunk-A2GZF7DC.js → chunk-LADCF22A.js} +13 -13
  46. package/dist/chunk-LCGCVYZ4.js +57 -0
  47. package/dist/chunk-M4AKACEO.js +382 -0
  48. package/dist/{chunk-POHLU5DW.js → chunk-M6L6IDJG.js} +3 -3
  49. package/dist/{chunk-4JUF2NNX.js → chunk-MXI6J5JF.js} +7 -7
  50. package/dist/{chunk-X4RCMKVQ.js → chunk-NDINPTJ4.js} +2 -2
  51. package/dist/{chunk-TTNYS3EA.js → chunk-OB5HIGJY.js} +1 -1
  52. package/dist/{chunk-7RXG6QRZ.js → chunk-OBMAI2DP.js} +61 -840
  53. package/dist/{chunk-5M54SPOL.js → chunk-ODFEOB4F.js} +161 -5
  54. package/dist/chunk-PD3MESLB.js +242 -0
  55. package/dist/{chunk-ED4KHGC3.js → chunk-PPAMZ32Z.js} +9 -2
  56. package/dist/{chunk-VMNQ6OZA.js → chunk-QCTRSGHQ.js} +963 -786
  57. package/dist/chunk-RVG5JXAL.js +41 -0
  58. package/dist/{chunk-RD5U66HV.js → chunk-SROCI7ZU.js} +7 -7
  59. package/dist/{chunk-MFFY33HR.js → chunk-THKY7CD7.js} +466 -205
  60. package/dist/{chunk-34475P3I.js → chunk-TSHXZTOQ.js} +5 -4
  61. package/dist/{chunk-PCZJO5TI.js → chunk-UFQ3F4FW.js} +13 -178
  62. package/dist/{chunk-AD2SYQYC.js → chunk-UHXRNZ2J.js} +121 -3
  63. package/dist/chunk-UND3GU2L.js +103 -0
  64. package/dist/{chunk-QQL5RT5M.js → chunk-UUANF5CR.js} +2323 -2114
  65. package/dist/{chunk-VJWL6YS5.js → chunk-UUVG37B4.js} +2 -2
  66. package/dist/chunk-UVDSQ6LW.js +472 -0
  67. package/dist/{chunk-QWU7ZBO7.js → chunk-VQNODYQ4.js} +215 -56
  68. package/dist/chunk-VREKEFLL.js +37 -0
  69. package/dist/{chunk-2TZWSW76.js → chunk-WHGPSPT5.js} +2 -2
  70. package/dist/{chunk-TW3WDMVS.js → chunk-WHJYKASB.js} +2 -2
  71. package/dist/{chunk-MEQ45TQ4.js → chunk-WJHBC77E.js} +21 -7
  72. package/dist/{chunk-HXG4IURW.js → chunk-X2KV5FXT.js} +2 -2
  73. package/dist/{chunk-YHZX5GEU.js → chunk-XAKHZX5N.js} +2 -2
  74. package/dist/{chunk-2LZI5CAG.js → chunk-XEGB6BCN.js} +228 -36
  75. package/dist/{chunk-E25LMLRW.js → chunk-YD734TPH.js} +2 -2
  76. package/dist/{verifiers-4UUM6TEE.js → chunk-YTYFXUI3.js} +121 -372
  77. package/dist/{chunk-3JLKSKD7.js → chunk-ZGH7FGS5.js} +17 -7
  78. package/dist/{chunk-VSNATDE6.js → chunk-ZZMN5OM4.js} +2 -2
  79. package/dist/cli/index.js +34 -32
  80. package/dist/{clio-J5JIOIDS.js → clio-WBVQEBKO.js} +7 -7
  81. package/dist/{code-nav-AXCXSBHX.js → code-nav-FGGFIE7L.js} +7 -7
  82. package/dist/codewiki/build-worker.js +4 -4
  83. package/dist/{components-KELWS457.js → components-F7OEATSO.js} +5 -5
  84. package/dist/{config-OEBMIN2U.js → config-TRBL3RCF.js} +48 -41
  85. package/dist/{configure-PUQOSIXQ.js → configure-OLCVPHNM.js} +17 -17
  86. package/dist/{context-URSXPBCK.js → context-MJIJ6GOX.js} +12 -12
  87. package/dist/{context-EKDCKUUZ.js → context-WFPKQSM6.js} +26 -9
  88. package/dist/{context-MGSE4Z2T.js → context-XEWE3MOJ.js} +44 -37
  89. package/dist/{context-clear-KDAJRNUK.js → context-clear-KNOS2JPB.js} +44 -37
  90. package/dist/{context-index-BZ4UYMTC.js → context-index-SSR5ECNE.js} +3 -3
  91. package/dist/{context-working-set-SBKMPPI2.js → context-working-set-EUXAZI6N.js} +14 -13
  92. package/dist/{dispatch-runner-MSWN72NK.js → dispatch-runner-B7MTOVKL.js} +321 -60
  93. package/dist/{docs-2C2LTVT2.js → docs-FLJTIDSE.js} +5 -5
  94. package/dist/{doctor-7BSE27PJ.js → doctor-RN4YKO2X.js} +15 -15
  95. package/dist/{eval-IZGDOO4H.js → eval-RUBJVSNQ.js} +52 -236
  96. package/dist/{evidence-SR7WXB5B.js → evidence-JZNBUOQZ.js} +39 -33
  97. package/dist/{evolve-K7VE2CBX.js → evolve-FJVC4KKI.js} +39 -33
  98. package/dist/{extensions-QVDOHDGJ.js → extensions-IQL36S7K.js} +5 -5
  99. package/dist/{fleet-7XMJNQNF.js → fleet-BDKYJFCP.js} +243 -370
  100. package/dist/fleet-commands-ZFIWZSB3.js +70 -0
  101. package/dist/fleet-graph-Y6HPXIVF.js +125 -0
  102. package/dist/fleet-new-RDVJLHHH.js +48 -0
  103. package/dist/{fleet-preflight-AQNAH644.js → fleet-preflight-BHSNPBMH.js} +2 -2
  104. package/dist/fleet-validate-BIYREGIK.js +79 -0
  105. package/dist/{init-JGNPAYXT.js → init-LQUB5COQ.js} +57 -48
  106. package/dist/library-NJAHIGG4.js +217 -0
  107. package/dist/memory-OG6HOYKM.js +472 -0
  108. package/dist/{models-ZMMLFJNN.js → models-5ZG5XY7J.js} +23 -22
  109. package/dist/{monitor-2F3T5KHP.js → monitor-TJ7AMTGB.js} +69 -35
  110. package/dist/{orchestrator-ORHT43JB.js → orchestrator-WZYB54DM.js} +4868 -1189
  111. package/dist/{paths-UXLN5YYZ.js → paths-XUC7GS6E.js} +5 -5
  112. package/dist/{reset-NXGTYNUO.js → reset-PXQT45IY.js} +8 -8
  113. package/dist/{run-RF4WJGMT.js → run-FQ74YF62.js} +82 -62
  114. package/dist/{share-UT3W6E4M.js → share-FW7SVCL3.js} +34 -10
  115. package/dist/{skills-PSACKC5Q.js → skills-7E7IRB3R.js} +25 -9
  116. package/dist/{skills-eval-WJSI55RZ.js → skills-eval-LI75W6OK.js} +43 -35
  117. package/dist/{targets-PIIRAOYS.js → targets-4CIFKCTW.js} +27 -24
  118. package/dist/{terminal-lease-ULWXWNVY.js → terminal-lease-WUZY7ZV5.js} +5 -4
  119. package/dist/{uninstall-FZCQCDKC.js → uninstall-7FV7IP4E.js} +5 -5
  120. package/dist/{upgrade-346TZ6AV.js → upgrade-K2HVIVMQ.js} +21 -20
  121. package/dist/{usage-6KKXR32N.js → usage-GTZELZQX.js} +159 -59
  122. package/dist/verifiers-RLAHT27O.js +336 -0
  123. package/dist/{verify-X5HDROLA.js → verify-BX3BRKH5.js} +7 -6
  124. package/dist/{wiki-generate-7STOCIFZ.js → wiki-generate-ASIFASCN.js} +58 -48
  125. package/dist/worker/entry.js +98 -84
  126. package/dist/{workspace-G4ZWUIPR.js → workspace-ZJ6BFM3Q.js} +4 -4
  127. package/docs/README.md +4 -3
  128. package/docs/acp.md +1 -1
  129. package/docs/alcf-provider.md +1 -1
  130. package/docs/architecture.md +2 -2
  131. package/docs/artifact-placement.md +1 -2
  132. package/docs/artifact-versions.md +10 -6
  133. package/docs/built-in-agents.md +26 -2
  134. package/docs/capacity-and-scheduling.md +1 -1
  135. package/docs/commands-and-modes.md +90 -8
  136. package/docs/configuration-and-targets.md +90 -2
  137. package/docs/context-engine.md +4 -2
  138. package/docs/context-working-set.md +4 -4
  139. package/docs/development-pipeline.md +1 -1
  140. package/docs/dispatch-architecture-rationale.md +1 -1
  141. package/docs/documentation-coverage.md +4 -4
  142. package/docs/documentation-guide.md +4 -4
  143. package/docs/eval-runner.md +1 -1
  144. package/docs/evals-internal.md +4 -45
  145. package/docs/evidence-and-memory.md +70 -10
  146. package/docs/evolution.md +1 -1
  147. package/docs/exit-codes-and-output.md +4 -1
  148. package/docs/extensions-and-sharing.md +6 -2
  149. package/docs/fleet-demo-runbook.md +2 -2
  150. package/docs/fleet-dispatch.md +224 -11
  151. package/docs/git-commit-provenance.md +2 -2
  152. package/docs/glossary.md +1 -1
  153. package/docs/installation-and-lifecycle.md +2 -2
  154. package/docs/middleware-and-components.md +20 -2
  155. package/docs/model-catalog.md +1 -1
  156. package/docs/observability.md +55 -8
  157. package/docs/proactive-memory.md +26 -16
  158. package/docs/prompt-envelope-and-tools.md +4 -2
  159. package/docs/provider-adapter-cookbook.md +1 -1
  160. package/docs/release-cut-checklist.md +83 -65
  161. package/docs/resource-library.md +59 -0
  162. package/docs/safety-model.md +29 -7
  163. package/docs/scientific-validation.md +3 -3
  164. package/docs/session-lifecycle.md +37 -1
  165. package/docs/skills-marketplace.md +16 -3
  166. package/docs/tool-usage.md +14 -7
  167. package/docs/trace-store.md +1 -1
  168. package/docs/troubleshooting.md +1 -1
  169. package/docs/tui-design.md +38 -4
  170. package/docs/worker-dispatch-mechanics.md +3 -3
  171. package/package.json +7 -4
  172. package/src/cli/agents.ts +2 -3
  173. package/src/cli/argv.ts +14 -1
  174. package/src/cli/fleet-commands.ts +37 -0
  175. package/src/cli/fleet-graph.ts +102 -0
  176. package/src/cli/fleet-new.ts +36 -0
  177. package/src/cli/fleet-preflight.ts +121 -0
  178. package/src/cli/fleet-validate.ts +30 -0
  179. package/src/cli/fleet.ts +188 -335
  180. package/src/cli/index.ts +4 -2
  181. package/src/cli/library.ts +190 -0
  182. package/src/cli/memory.ts +272 -10
  183. package/src/cli/modes/json-stream.ts +2 -2
  184. package/src/cli/modes/print.ts +12 -1
  185. package/src/cli/run.ts +22 -2
  186. package/src/cli/share.ts +13 -1
  187. package/src/cli/targets.ts +12 -3
  188. package/src/cli/usage.ts +160 -20
  189. package/src/core/bus-events.ts +7 -0
  190. package/src/core/commit-attribution.ts +4 -4
  191. package/src/core/config.ts +130 -0
  192. package/src/core/defaults.ts +81 -0
  193. package/src/core/response-model-id.ts +134 -0
  194. package/src/core/toml.ts +62 -0
  195. package/src/core/workspace-files.ts +0 -1
  196. package/src/domains/agents/builtins/architect.md +2 -1
  197. package/src/domains/agents/builtins/oracle.md +33 -0
  198. package/src/domains/agents/catalog.ts +18 -5
  199. package/src/domains/agents/fleet-contract.ts +278 -16
  200. package/src/domains/agents/index.ts +14 -0
  201. package/src/domains/agents/recipe.ts +54 -14
  202. package/src/domains/agents/result-contract.ts +242 -5
  203. package/src/domains/config/classify.ts +4 -0
  204. package/src/domains/context/bootstrap.ts +36 -27
  205. package/src/domains/context/project-metadata.ts +19 -63
  206. package/src/domains/context/prompt-context.ts +8 -0
  207. package/src/domains/context/working-set/policies/index.ts +3 -4
  208. package/src/domains/dispatch/active-route-planner.ts +14 -0
  209. package/src/domains/dispatch/backoff.ts +2 -1
  210. package/src/domains/dispatch/budget-envelope.ts +396 -0
  211. package/src/domains/dispatch/capability-match.ts +1 -0
  212. package/src/domains/dispatch/checkout-writer-lease.ts +175 -0
  213. package/src/domains/dispatch/contract.ts +36 -0
  214. package/src/domains/dispatch/delegation-plan.ts +167 -0
  215. package/src/domains/dispatch/execution-plan.ts +76 -5
  216. package/src/domains/dispatch/execution-role.ts +3 -1
  217. package/src/domains/dispatch/execution-scheduler.ts +183 -67
  218. package/src/domains/dispatch/extension.ts +339 -36
  219. package/src/domains/dispatch/fleet-gate.ts +14 -0
  220. package/src/domains/dispatch/fleet-plan.ts +63 -3
  221. package/src/domains/dispatch/fleet-run.ts +737 -0
  222. package/src/domains/dispatch/gate-role-prompts.ts +9 -0
  223. package/src/domains/dispatch/host-verification.ts +178 -0
  224. package/src/domains/dispatch/index.ts +38 -0
  225. package/src/domains/dispatch/intent.ts +159 -0
  226. package/src/domains/dispatch/orphan-recovery.ts +1 -0
  227. package/src/domains/dispatch/receipt-integrity.ts +12 -4
  228. package/src/domains/dispatch/state.ts +37 -3
  229. package/src/domains/dispatch/types.ts +61 -9
  230. package/src/domains/dispatch/validation.ts +80 -6
  231. package/src/domains/dispatch/worker-spawn.ts +14 -3
  232. package/src/domains/eval/metrics/evidence.ts +0 -116
  233. package/src/domains/eval/metrics/invariants.ts +1 -1
  234. package/src/domains/eval/runners/clio-run.ts +1 -10
  235. package/src/domains/eval/runners/external-command.ts +2 -29
  236. package/src/domains/eval/schema/suite.ts +0 -7
  237. package/src/domains/eval/suites/run.ts +1 -7
  238. package/src/domains/evidence/trust-status.ts +10 -1
  239. package/src/domains/memory/index.ts +22 -0
  240. package/src/domains/memory/operations.ts +58 -1
  241. package/src/domains/memory/promotion.ts +281 -0
  242. package/src/domains/memory/prompt-section.ts +25 -5
  243. package/src/domains/memory/proposal.ts +51 -7
  244. package/src/domains/memory/task-bank.ts +3 -2
  245. package/src/domains/memory/task-memory-handoff.ts +181 -24
  246. package/src/domains/memory/task-memory-policy.ts +3 -1
  247. package/src/domains/memory/types.ts +37 -0
  248. package/src/domains/memory/validate.ts +178 -0
  249. package/src/domains/middleware/index.ts +15 -0
  250. package/src/domains/middleware/memory-intervention.ts +35 -25
  251. package/src/domains/middleware/runtime.ts +6 -0
  252. package/src/domains/middleware/skills-reminder.ts +19 -4
  253. package/src/domains/middleware/stalled-turn.ts +43 -1
  254. package/src/domains/middleware/types.ts +10 -0
  255. package/src/domains/middleware/watchdog.ts +281 -0
  256. package/src/domains/observability/contract.ts +9 -2
  257. package/src/domains/observability/cost.ts +31 -4
  258. package/src/domains/observability/extension.ts +2 -2
  259. package/src/domains/observability/index.ts +10 -0
  260. package/src/domains/observability/out-of-turn-usage.ts +223 -0
  261. package/src/domains/providers/index.ts +3 -0
  262. package/src/domains/providers/model-discovery.ts +9 -0
  263. package/src/domains/providers/runtime-resolution.ts +38 -1
  264. package/src/domains/providers/runtimes/common/probe-helpers.ts +97 -16
  265. package/src/domains/providers/types/context-window-slots.ts +18 -0
  266. package/src/domains/providers/types/runtime-descriptor.ts +3 -1
  267. package/src/domains/resources/index.ts +20 -0
  268. package/src/domains/resources/library.ts +326 -0
  269. package/src/domains/resources/skills/marketplace.ts +37 -12
  270. package/src/domains/safety/call-target.ts +211 -14
  271. package/src/domains/safety/decision-presentation.ts +268 -0
  272. package/src/domains/safety/redaction.ts +73 -0
  273. package/src/domains/session/context-ledger.ts +10 -1
  274. package/src/domains/session/decision-board.ts +4 -0
  275. package/src/domains/session/entries.ts +3 -0
  276. package/src/domains/session/handoff.ts +629 -0
  277. package/src/domains/session/history.ts +68 -19
  278. package/src/domains/session/usage.ts +24 -7
  279. package/src/domains/share/archive.ts +67 -2
  280. package/src/engine/acp/event-mapper.ts +7 -0
  281. package/src/engine/acp/server.ts +29 -2
  282. package/src/engine/apis/lmstudio.ts +25 -4
  283. package/src/engine/apis/openai-completions.ts +147 -22
  284. package/src/engine/claude/sdk-runtime.ts +8 -2
  285. package/src/engine/claude/tool-safety.ts +13 -0
  286. package/src/engine/loop-guard.ts +27 -3
  287. package/src/engine/worker-events.ts +4 -3
  288. package/src/engine/worker-runtime.ts +59 -54
  289. package/src/entry/orchestrator.ts +55 -1
  290. package/src/interactive/bus-notices.ts +26 -0
  291. package/src/interactive/chat-loop-messages.ts +22 -0
  292. package/src/interactive/chat-loop.ts +248 -1
  293. package/src/interactive/chat-renderer.ts +41 -3
  294. package/src/interactive/clio-editor.ts +44 -7
  295. package/src/interactive/context-overlay.ts +43 -5
  296. package/src/interactive/cost-overlay.ts +70 -11
  297. package/src/interactive/council-dispatch.ts +30 -0
  298. package/src/interactive/council-grid.ts +213 -0
  299. package/src/interactive/council.ts +99 -0
  300. package/src/interactive/dispatch-board.ts +471 -50
  301. package/src/interactive/fleet-run-preview.ts +307 -0
  302. package/src/interactive/footer/notifications.ts +219 -0
  303. package/src/interactive/footer/widgets.ts +13 -0
  304. package/src/interactive/handoff-round.ts +56 -0
  305. package/src/interactive/interactive-application.ts +49 -2
  306. package/src/interactive/interactive-event-projection.ts +9 -1
  307. package/src/interactive/interactive-input-runtime.ts +11 -1
  308. package/src/interactive/interactive-presentation.ts +11 -1
  309. package/src/interactive/interactive-slash-runtime.ts +52 -2
  310. package/src/interactive/interactive-subscriptions.ts +14 -2
  311. package/src/interactive/memory-overlay.ts +89 -4
  312. package/src/interactive/oracle.ts +179 -0
  313. package/src/interactive/overlay-ask-user-lifecycle.ts +7 -1
  314. package/src/interactive/overlay-frame.ts +5 -2
  315. package/src/interactive/overlay-general-openers.ts +230 -2
  316. package/src/interactive/overlay-key-routing.ts +58 -2
  317. package/src/interactive/overlay-lifecycle.ts +52 -5
  318. package/src/interactive/overlay-permission-lifecycle.ts +33 -8
  319. package/src/interactive/overlay-resource-openers.ts +11 -3
  320. package/src/interactive/overlay-session-lifecycle.ts +234 -2
  321. package/src/interactive/overlay-transitions.ts +11 -0
  322. package/src/interactive/overlays/ask-user.ts +74 -30
  323. package/src/interactive/overlays/decisions.ts +3 -1
  324. package/src/interactive/overlays/fleet-run-approval.ts +208 -0
  325. package/src/interactive/overlays/handoff-review.ts +185 -0
  326. package/src/interactive/overlays/library-install-confirm.ts +151 -0
  327. package/src/interactive/overlays/list-overlay.ts +168 -2
  328. package/src/interactive/overlays/settings.ts +101 -4
  329. package/src/interactive/overlays/side-question.ts +139 -0
  330. package/src/interactive/overlays/skills-hub.ts +401 -15
  331. package/src/interactive/permission-hint.ts +35 -0
  332. package/src/interactive/permission-overlay.ts +95 -45
  333. package/src/interactive/renderers/tool-execution.ts +19 -49
  334. package/src/interactive/session-last-turn.ts +8 -1
  335. package/src/interactive/session-usage-reseed.ts +36 -10
  336. package/src/interactive/side-question.ts +171 -0
  337. package/src/interactive/slash-commands.ts +434 -7
  338. package/src/interactive/slash-spec.ts +19 -6
  339. package/src/interactive/status/summary.ts +5 -0
  340. package/src/interactive/status/types.ts +5 -0
  341. package/src/interactive/terminal-lease.ts +1 -0
  342. package/src/interactive/theme/tokens.ts +30 -0
  343. package/src/interactive/turn-context.ts +96 -23
  344. package/src/interactive/turn-middleware.ts +16 -1
  345. package/src/interactive/turn-runtime.ts +37 -8
  346. package/src/interactive/turn-state.ts +3 -0
  347. package/src/interactive/watchdog-run.ts +75 -0
  348. package/src/interactive/worker-progress.ts +440 -0
  349. package/src/interactive/worker-share.ts +56 -1
  350. package/src/interactive/worker-stream.ts +58 -110
  351. package/src/tools/agent-tools.ts +28 -3
  352. package/src/tools/ask-user.ts +21 -1
  353. package/src/tools/bootstrap.ts +3 -0
  354. package/src/tools/compete-worktrees.ts +13 -79
  355. package/src/tools/context/index.ts +2 -2
  356. package/src/tools/dispatch-admission.ts +242 -8
  357. package/src/tools/dispatch-arguments.ts +65 -1
  358. package/src/tools/dispatch-event-text.ts +19 -0
  359. package/src/tools/dispatch-plan.ts +136 -6
  360. package/src/tools/dispatch-runner.ts +319 -13
  361. package/src/tools/dispatch-types.ts +20 -1
  362. package/src/tools/dispatch.ts +96 -3
  363. package/src/tools/monitor.ts +31 -0
  364. package/src/tools/profiles.ts +18 -4
  365. package/src/tools/registry.ts +15 -5
  366. package/src/tools/result-disposition.ts +156 -0
  367. package/src/tools/result-shaping.ts +59 -1
  368. package/src/tools/task-worktree.ts +238 -0
  369. package/src/tools/verify/authoring.ts +116 -55
  370. package/src/tools/verify/scripts.ts +62 -0
  371. package/src/tools/worker-evidence.ts +21 -1
  372. package/src/worker/spec-contract.ts +44 -3
  373. package/dist/chunk-EFADSJET.js +0 -18
  374. package/dist/chunk-HC4CLZ2Y.js +0 -68
  375. package/dist/memory-4ALKDJ4Q.js +0 -246
  376. package/src/domains/eval/metrics/chaos-stream.ts +0 -93
@@ -0,0 +1,268 @@
1
+ import type { ActionClass } from "./action-classifier.js";
2
+ import type { AutonomyExposure } from "./autonomy.js";
3
+
4
+ /** Closed consequence categories used only to explain an already-made decision request. */
5
+ export const DECISION_TIERS = ["conversation", "workspace", "outward", "safety-net", "system", "worker"] as const;
6
+
7
+ export type DecisionTier = (typeof DECISION_TIERS)[number];
8
+ export type DecisionSemanticToken = "accent" | "action" | "warning";
9
+ export type DecisionRequestKind = "question" | "permission";
10
+ export type DecisionAffectedScope = "conversation" | "workspace" | "outward" | "system";
11
+ export type DecisionReversibility = "reversible" | "limited" | "unknown";
12
+ export type DecisionAuthorityEffect = "records-answer" | "grants-once";
13
+ export type DecisionActionId = "record-answer" | "cancel" | "approve-once" | "deny" | "stop";
14
+
15
+ export type DecisionAxis =
16
+ | { kind: "answer" }
17
+ | { kind: "autonomy"; level: string }
18
+ | { kind: "safety-net"; ruleId: string };
19
+
20
+ export type DecisionOrigin = { kind: "main" } | { kind: "worker"; agentId: string; runId: string };
21
+
22
+ /**
23
+ * Facts the host has already authenticated or derived from enforced policy.
24
+ * No model-authored title, question, reason, summary, or option label belongs
25
+ * here, so prose has no path to the tier selection.
26
+ */
27
+ export interface TrustedDecisionFacts {
28
+ requestKind: DecisionRequestKind;
29
+ axis: DecisionAxis;
30
+ exposure: AutonomyExposure;
31
+ affectedScope: DecisionAffectedScope;
32
+ reversibility: DecisionReversibility;
33
+ origin: DecisionOrigin;
34
+ authorityEffect: DecisionAuthorityEffect;
35
+ tool?: string;
36
+ actionClass?: ActionClass;
37
+ }
38
+
39
+ export interface DecisionPresentationAction {
40
+ id: DecisionActionId;
41
+ label: string;
42
+ consequence: string;
43
+ }
44
+
45
+ /**
46
+ * This projection contains display data only. Registry admission and interview
47
+ * settlement never consume it, and it contains no allow, deny, or autonomy
48
+ * disposition that an execution layer could mistake for authority.
49
+ */
50
+ export interface DecisionPresentation {
51
+ tier: DecisionTier;
52
+ tierLabel: string;
53
+ title: string;
54
+ semanticToken: DecisionSemanticToken;
55
+ authorizationCopy: string;
56
+ consequenceCopy: string;
57
+ reversibilityCopy: string;
58
+ requestedByCopy: string;
59
+ requiredActions: ReadonlyArray<DecisionPresentationAction>;
60
+ }
61
+
62
+ const ACTION_CLASSES = new Set<ActionClass>([
63
+ "read",
64
+ "write",
65
+ "execute",
66
+ "dispatch",
67
+ "system_modify",
68
+ "git_destructive",
69
+ "unknown",
70
+ ]);
71
+
72
+ /** Unknown or malformed action classes classify conservatively as unknown. */
73
+ export function decisionActionClass(value: unknown): ActionClass {
74
+ return typeof value === "string" && ACTION_CLASSES.has(value as ActionClass) ? (value as ActionClass) : "unknown";
75
+ }
76
+
77
+ function actionConsequence(actionClass: ActionClass): {
78
+ affectedScope: DecisionAffectedScope;
79
+ reversibility: DecisionReversibility;
80
+ } {
81
+ switch (actionClass) {
82
+ case "read":
83
+ return { affectedScope: "workspace", reversibility: "reversible" };
84
+ case "write":
85
+ return { affectedScope: "workspace", reversibility: "reversible" };
86
+ case "execute":
87
+ case "dispatch":
88
+ return { affectedScope: "workspace", reversibility: "limited" };
89
+ case "system_modify":
90
+ case "git_destructive":
91
+ case "unknown":
92
+ return { affectedScope: "system", reversibility: "unknown" };
93
+ }
94
+ }
95
+
96
+ export function decisionFactsForPermission(input: {
97
+ tool: string;
98
+ actionClass: ActionClass;
99
+ axis: Exclude<DecisionAxis, { kind: "answer" }>;
100
+ origin: DecisionOrigin;
101
+ exposure?: AutonomyExposure;
102
+ }): TrustedDecisionFacts {
103
+ const exposure = input.exposure ?? "local";
104
+ const consequence = actionConsequence(input.actionClass);
105
+ return {
106
+ requestKind: "permission",
107
+ axis: input.axis,
108
+ exposure,
109
+ affectedScope: exposure === "outward" ? "outward" : consequence.affectedScope,
110
+ reversibility: exposure === "outward" ? "limited" : consequence.reversibility,
111
+ origin: input.origin,
112
+ authorityEffect: "grants-once",
113
+ tool: input.tool,
114
+ actionClass: input.actionClass,
115
+ };
116
+ }
117
+
118
+ export function decisionFactsForAnswer(exposure: AutonomyExposure): TrustedDecisionFacts {
119
+ return {
120
+ requestKind: "question",
121
+ axis: { kind: "answer" },
122
+ exposure,
123
+ affectedScope: exposure === "outward" ? "outward" : "conversation",
124
+ reversibility: exposure === "outward" ? "limited" : "reversible",
125
+ origin: { kind: "main" },
126
+ authorityEffect: "records-answer",
127
+ };
128
+ }
129
+
130
+ function classifyTier(facts: TrustedDecisionFacts): DecisionTier {
131
+ if (facts.origin.kind === "worker") return "worker";
132
+ if (facts.affectedScope === "system") return "system";
133
+ if (facts.exposure === "outward" || facts.affectedScope === "outward") return "outward";
134
+ if (facts.axis.kind === "safety-net") return "safety-net";
135
+ if (facts.authorityEffect === "grants-once") return "workspace";
136
+ return "conversation";
137
+ }
138
+
139
+ function tierIdentity(tier: DecisionTier): {
140
+ tierLabel: string;
141
+ title: string;
142
+ semanticToken: DecisionSemanticToken;
143
+ } {
144
+ switch (tier) {
145
+ case "conversation":
146
+ return { tierLabel: "Conversational answer", title: "Answer a question", semanticToken: "accent" };
147
+ case "workspace":
148
+ return { tierLabel: "Workspace authority", title: "Approve workspace action", semanticToken: "action" };
149
+ case "outward":
150
+ return { tierLabel: "Outward consequence", title: "Confirm outward consequence", semanticToken: "warning" };
151
+ case "safety-net":
152
+ return { tierLabel: "Safety-net confirmation", title: "Safety-net confirmation", semanticToken: "warning" };
153
+ case "system":
154
+ return { tierLabel: "System change", title: "Approve system change", semanticToken: "warning" };
155
+ case "worker":
156
+ return { tierLabel: "Worker escalation", title: "Worker needs approval", semanticToken: "action" };
157
+ }
158
+ }
159
+
160
+ function requestedByCopy(facts: TrustedDecisionFacts): string {
161
+ const requester =
162
+ facts.origin.kind === "worker" ? `worker ${facts.origin.agentId} (run ${facts.origin.runId})` : "main agent";
163
+ if (facts.axis.kind === "answer") return requester;
164
+ if (facts.axis.kind === "safety-net") return `${requester} through safety-net rail ${facts.axis.ruleId}`;
165
+ return `${requester} through autonomy level (${facts.axis.level})`;
166
+ }
167
+
168
+ function authorizationCopy(facts: TrustedDecisionFacts): string {
169
+ if (facts.authorityEffect === "records-answer") {
170
+ return facts.exposure === "outward"
171
+ ? "Your response records an answer about an outward step. It does not publish or send anything by itself."
172
+ : "Your response records an answer for this interview. It grants no tool authority.";
173
+ }
174
+ const tool = facts.tool ?? "the presented tool";
175
+ const actionClass = facts.actionClass ?? "unknown";
176
+ if (tool === "ask_user" && facts.exposure === "outward") {
177
+ return "Approval opens this one outward-decision interview. It does not publish or send anything by itself.";
178
+ }
179
+ return `Approval authorizes one ${actionClass} call to ${tool}. It does not change the autonomy level.`;
180
+ }
181
+
182
+ function consequenceCopy(facts: TrustedDecisionFacts, tier: DecisionTier): string {
183
+ switch (tier) {
184
+ case "conversation":
185
+ return "The answer stays in this session's decision record.";
186
+ case "workspace":
187
+ return facts.actionClass === "read"
188
+ ? "The call reads within the workspace without mutating it."
189
+ : "The call can affect files or processes inside the workspace.";
190
+ case "outward":
191
+ return "The resulting step can reach people or systems outside the workspace.";
192
+ case "safety-net":
193
+ return "An always-on safety-net rail requires a one-shot operator decision before this call can run.";
194
+ case "system":
195
+ return "The call can change state outside the workspace or state the classifier cannot safely bound.";
196
+ case "worker":
197
+ return "A dispatched worker is parked. Your answer returns only to that run's exact request.";
198
+ }
199
+ }
200
+
201
+ function reversibilityCopy(facts: TrustedDecisionFacts): string {
202
+ if (facts.requestKind === "question") {
203
+ return facts.reversibility === "reversible"
204
+ ? "Reversible: yes. The recorded answer can be superseded later."
205
+ : "Reversible: not guaranteed. An outward step that later uses this answer may have lasting effects.";
206
+ }
207
+ if (facts.actionClass === "read" && facts.reversibility === "reversible") {
208
+ return "Reversible: yes. This call does not mutate the workspace.";
209
+ }
210
+ switch (facts.reversibility) {
211
+ case "reversible":
212
+ return "Reversible: yes. Workspace changes can be reviewed and reverted.";
213
+ case "limited":
214
+ return "Reversible: not guaranteed. Effects that already ran or reached an outward system may remain.";
215
+ case "unknown":
216
+ return "Reversible: unknown. Treat the effect as not safely reversible.";
217
+ }
218
+ }
219
+
220
+ function requiredActions(facts: TrustedDecisionFacts, tier: DecisionTier): ReadonlyArray<DecisionPresentationAction> {
221
+ if (facts.authorityEffect === "records-answer") {
222
+ return [
223
+ {
224
+ id: "record-answer",
225
+ label: facts.exposure === "outward" ? "Record outward answer" : "Record answer",
226
+ consequence: "Records the selected or typed answer without granting tool authority.",
227
+ },
228
+ { id: "cancel", label: "Cancel", consequence: "Closes the interview without recording an answer for this round." },
229
+ ];
230
+ }
231
+ const approveLabel =
232
+ tier === "system"
233
+ ? "Approve system change once"
234
+ : tier === "safety-net"
235
+ ? "Approve guarded action once"
236
+ : tier === "worker"
237
+ ? "Approve worker request once"
238
+ : tier === "outward"
239
+ ? "Approve outward decision once"
240
+ : "Approve workspace action once";
241
+ const stopConsequence =
242
+ facts.origin.kind === "worker"
243
+ ? "Denies this worker request and ends the active main-agent turn. Other worker requests retain their timeout policy."
244
+ : "Denies every parked request from this turn and ends the run.";
245
+ return [
246
+ {
247
+ id: "approve-once",
248
+ label: approveLabel,
249
+ consequence: "Runs only the presented request and does not change the autonomy level.",
250
+ },
251
+ { id: "deny", label: "Deny this request", consequence: "Denies only the presented request and advances the queue." },
252
+ { id: "stop", label: "Deny and stop", consequence: stopConsequence },
253
+ ];
254
+ }
255
+
256
+ /** Pure presentation classifier. It performs no I/O and has no execution authority. */
257
+ export function classifyDecisionPresentation(facts: TrustedDecisionFacts): DecisionPresentation {
258
+ const tier = classifyTier(facts);
259
+ return {
260
+ tier,
261
+ ...tierIdentity(tier),
262
+ authorizationCopy: authorizationCopy(facts),
263
+ consequenceCopy: consequenceCopy(facts, tier),
264
+ reversibilityCopy: reversibilityCopy(facts),
265
+ requestedByCopy: requestedByCopy(facts),
266
+ requiredActions: requiredActions(facts, tier),
267
+ };
268
+ }
@@ -0,0 +1,73 @@
1
+ /**
2
+ * Display-time secret redaction for tool arguments.
3
+ *
4
+ * Two surfaces need the same rules and must not drift. The transcript's tool
5
+ * renderer projects a call's arguments for the operator's own screen, and the
6
+ * worker tool-admission seam composes a bounded action descriptor that crosses
7
+ * the NDJSON stdout boundary. A credential that one of them scrubs and the
8
+ * other prints is a leak, so the patterns live here and both import them.
9
+ *
10
+ * This is presentation only. Execution, receipts, and the safety verdict all
11
+ * keep the original argument values; nothing here changes what a tool runs.
12
+ */
13
+
14
+ function isPlainObject(value: unknown): value is Record<string, unknown> {
15
+ return value !== null && typeof value === "object" && !Array.isArray(value);
16
+ }
17
+
18
+ const SECRET_KEY_RE =
19
+ /(?:api[-_]?key|access[-_]?key|auth(?:orization)?|credential|password|private[-_]?key|secret|token)/iu;
20
+ const ENV_KEY_RE = /^env(?:ironment)?$/iu;
21
+ const SECRET_STRING_RE = /(https?:\/\/[^\s/@]+:)[^\s/@]+@/giu;
22
+ const SECRET_URL_PARAM_RE =
23
+ /([?&](?:api[-_]?key|access[-_]?token|auth(?:orization)?|credential|password|secret|token)[^=\s]*=)[^&#\s]+/giu;
24
+ const SECRET_ASSIGNMENT_RE =
25
+ /(?<![A-Z0-9_])((?:[A-Z0-9_]*(?:ACCESS|API|AUTH|CREDENTIAL|KEY|PASS(?:WORD)?|PRIVATE|SECRET|TOKEN)[A-Z0-9_]*)=)[^\s;&|]+/giu;
26
+ const SECRET_FLAG_RE =
27
+ /(--?(?:[a-z0-9-]*(?:api[-_]?key|access[-_]?token|auth(?:orization)?|credential|password|secret|token)[a-z0-9-]*))(=|\s+)([^\s;&|]+)/giu;
28
+
29
+ /** Scrub credentials embedded in one string: URL userinfo, query params, `KEY=value`, and `--flag value`. */
30
+ export function redactSecretString(value: string): string {
31
+ return value
32
+ .replace(SECRET_STRING_RE, "$1[redacted]@")
33
+ .replace(SECRET_URL_PARAM_RE, "$1[redacted]")
34
+ .replace(SECRET_ASSIGNMENT_RE, "$1[redacted]")
35
+ .replace(SECRET_FLAG_RE, "$1$2[redacted]");
36
+ }
37
+
38
+ /** Whether an argument key names a secret outright, so its value never renders. */
39
+ export function isSecretArgKey(key: string): boolean {
40
+ return SECRET_KEY_RE.test(key);
41
+ }
42
+
43
+ /** Whether an argument key names an environment block, whose every string value is a candidate secret. */
44
+ function isEnvironmentArgKey(key: string): boolean {
45
+ return ENV_KEY_RE.test(key);
46
+ }
47
+
48
+ function redactEnvironmentValue(value: unknown, depth: number): unknown {
49
+ if (depth > 8) return "[redacted nested values]";
50
+ if (typeof value === "string") return "[redacted]";
51
+ if (Array.isArray(value)) return value.map((item) => redactEnvironmentValue(item, depth + 1));
52
+ if (!isPlainObject(value)) return value;
53
+ const out: Record<string, unknown> = {};
54
+ for (const [childKey, childValue] of Object.entries(value)) {
55
+ out[childKey] = redactEnvironmentValue(childValue, depth + 1);
56
+ }
57
+ return out;
58
+ }
59
+
60
+ /** Project tool arguments for display only; execution and receipts retain the original values. */
61
+ export function redactToolArgs(value: unknown, key = "", depth = 0): unknown {
62
+ if (isSecretArgKey(key)) return "[redacted]";
63
+ if (isEnvironmentArgKey(key)) return redactEnvironmentValue(value, depth);
64
+ if (typeof value === "string") return redactSecretString(value);
65
+ if (depth > 8) return "[redacted nested values]";
66
+ if (Array.isArray(value)) return value.map((item) => redactToolArgs(item, key, depth + 1));
67
+ if (!isPlainObject(value)) return value;
68
+ const out: Record<string, unknown> = {};
69
+ for (const [childKey, childValue] of Object.entries(value)) {
70
+ out[childKey] = redactToolArgs(childValue, childKey, depth + 1);
71
+ }
72
+ return out;
73
+ }
@@ -16,7 +16,7 @@
16
16
  * proportional reconciliation the footer bar already performs.
17
17
  */
18
18
 
19
- import type { ContextWindowSource } from "../providers/index.js";
19
+ import type { ContextWindowSlots, ContextWindowSource } from "../providers/index.js";
20
20
  import { DEFAULT_COMPACTION_THRESHOLD } from "./compaction/auto.js";
21
21
 
22
22
  /** Distinct buckets a context window is divided into for display. */
@@ -46,6 +46,8 @@ export interface BuildContextLedgerInput {
46
46
  contextWindow: number | null;
47
47
  /** Which layer answered `contextWindow`; omitted before a runtime resolves. */
48
48
  contextWindowSource?: ContextWindowSource | null;
49
+ /** The server-side split the probed window is a share of, when there is one. */
50
+ contextWindowSlots?: ContextWindowSlots | null;
49
51
  /**
50
52
  * Per-segment token estimates from the prompt compiler's segment manifest.
51
53
  * When empty, `systemPromptTokens` is used as a single opaque system bucket.
@@ -146,6 +148,12 @@ export interface ContextLedger {
146
148
  * the difference decides whether autocompact fires in time.
147
149
  */
148
150
  contextWindowSource: ContextWindowSource | null;
151
+ /**
152
+ * Present when `contextWindow` is one slot's share of the server's KV
153
+ * budget, so the overlay can show `196,608 (786,432 / 4 slots)` instead of
154
+ * a number that looks like the whole server.
155
+ */
156
+ contextWindowSlots: ContextWindowSlots | null;
149
157
  /** Sum of every content category (system..pending). */
150
158
  usedTokens: number;
151
159
  /** Autocompact headroom held in reserve above the conversation. */
@@ -346,6 +354,7 @@ export function buildContextLedger(input: BuildContextLedgerInput): ContextLedge
346
354
  model: input.model ?? null,
347
355
  contextWindow: window,
348
356
  contextWindowSource: input.contextWindowSource ?? null,
357
+ contextWindowSlots: input.contextWindowSlots ?? null,
349
358
  usedTokens,
350
359
  reserveTokens,
351
360
  freeTokens,
@@ -1,4 +1,5 @@
1
1
  import type { AskUserToolPolicy } from "../../tools/registry.js";
2
+ import type { AutonomyExposure } from "../safety/autonomy.js";
2
3
  import type { DecisionLedgerEntry, DecisionRecord } from "./entries.js";
3
4
 
4
5
  export interface DecisionLedgerEntryFields {
@@ -11,6 +12,7 @@ export interface DecisionLedgerEntryFields {
11
12
  roundCount: number;
12
13
  summary?: string;
13
14
  transcriptPath?: string;
15
+ exposure?: AutonomyExposure;
14
16
  decisions: DecisionRecord[];
15
17
  }
16
18
 
@@ -83,6 +85,7 @@ export function finalizedInterviewEntryFields(policy: AskUserToolPolicy): Decisi
83
85
  roundCount: policy.rounds.length,
84
86
  ...(policy.summary ? { summary: policy.summary } : {}),
85
87
  ...(policy.transcriptPath ? { transcriptPath: policy.transcriptPath } : {}),
88
+ exposure: policy.exposure ?? "local",
86
89
  decisions: [...decisionsByKey.values()],
87
90
  };
88
91
  }
@@ -172,6 +175,7 @@ export function createDecisionBoardStore(deps: DecisionBoardStoreDeps = {}): Dec
172
175
  roundCount: interview.roundCount,
173
176
  ...(interview.summary ? { summary: interview.summary } : {}),
174
177
  ...(interview.transcriptPath ? { transcriptPath: interview.transcriptPath } : {}),
178
+ ...(interview.exposure ? { exposure: interview.exposure } : {}),
175
179
  decisions: interview.decisions.map((decision) => {
176
180
  if (decision.key !== selected.key) return { ...decision };
177
181
  const next: DecisionRecord = { ...decision, status: "superseded", revisedAt };
@@ -13,6 +13,7 @@
13
13
 
14
14
  import { isSkillActivation, type SkillActivation } from "../../core/skill-activation.js";
15
15
  import type { ClioTurnRecord } from "../../engine/session.js";
16
+ import { AUTONOMY_EXPOSURES, type AutonomyExposure } from "../safety/autonomy.js";
16
17
 
17
18
  export interface SessionHeader {
18
19
  type: "session";
@@ -229,6 +230,7 @@ export interface DecisionLedgerEntry extends BaseSessionEntry {
229
230
  roundCount: number;
230
231
  summary?: string;
231
232
  transcriptPath?: string;
233
+ exposure?: AutonomyExposure;
232
234
  decisions: DecisionRecord[];
233
235
  }
234
236
 
@@ -643,6 +645,7 @@ export function isSessionEntry(value: unknown): value is SessionEntry {
643
645
  v.roundCount >= 0 &&
644
646
  isOptionalString(v.summary) &&
645
647
  isOptionalString(v.transcriptPath) &&
648
+ (v.exposure === undefined || isOneOf(v.exposure, AUTONOMY_EXPOSURES)) &&
646
649
  Array.isArray(v.decisions) &&
647
650
  v.decisions.every(isDecisionRecord)
648
651
  );