chainlesschain 0.165.2 → 0.165.4

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 (210) hide show
  1. package/README.md +151 -29
  2. package/package.json +2 -2
  3. package/src/assets/web-panel/assets/{AIOps-lS1R0Cza.js → AIOps-C__nnraW.js} +1 -1
  4. package/src/assets/web-panel/assets/{ActionButton-BmlgBPsj.js → ActionButton-CsKWHEZ-.js} +1 -1
  5. package/src/assets/web-panel/assets/{Analytics-CNKczv1S.js → Analytics-BhIjfjWO.js} +3 -3
  6. package/src/assets/web-panel/assets/{AppLayout-BuZGJARQ.js → AppLayout-BjuXFzWZ.js} +4 -4
  7. package/src/assets/web-panel/assets/{Artifacts-Dm73Sl-O.js → Artifacts-k6whDkZJ.js} +1 -1
  8. package/src/assets/web-panel/assets/{Audit-BGMW7A5e.js → Audit-C4FBMYRh.js} +1 -1
  9. package/src/assets/web-panel/assets/{BackgroundAgents-BQ6M54JR.js → BackgroundAgents-C_vRrSXk.js} +1 -1
  10. package/src/assets/web-panel/assets/{Backup-DBzGP0bR.js → Backup-CngFZeVp.js} +1 -1
  11. package/src/assets/web-panel/assets/{BaseInput-D1mLCoOV.js → BaseInput-B_H9EBRm.js} +1 -1
  12. package/src/assets/web-panel/assets/{Chat-BUfcN7p8.js → Chat-DLEC5kt7.js} +4 -4
  13. package/src/assets/web-panel/assets/ChatBubbleRenderer-xijcWkJe.js +1 -0
  14. package/src/assets/web-panel/assets/{Checkbox-Du0Yg5Pi.js → Checkbox-m3ClR4xh.js} +1 -1
  15. package/src/assets/web-panel/assets/{Codegen-B2RXziHW.js → Codegen-CmLSFrgp.js} +1 -1
  16. package/src/assets/web-panel/assets/{Col-DWhekOrR.js → Col-DFGQteHN.js} +1 -1
  17. package/src/assets/web-panel/assets/{Community-HQhrkon4.js → Community-EUUVORHE.js} +1 -1
  18. package/src/assets/web-panel/assets/{Compact-izHNb4uz.js → Compact-2PSg0Yr7.js} +1 -1
  19. package/src/assets/web-panel/assets/{Compliance-BDwLy41-.js → Compliance-CcKur7gB.js} +1 -1
  20. package/src/assets/web-panel/assets/{Cowork-DFJhLa7K.js → Cowork-DK_Fezfa.js} +3 -3
  21. package/src/assets/web-panel/assets/{Cron-DYY9RG7-.js → Cron-Dbw89xl7.js} +2 -2
  22. package/src/assets/web-panel/assets/{Crosschain-rr7tJTtv.js → Crosschain-CH66h_Ec.js} +1 -1
  23. package/src/assets/web-panel/assets/{DID-D2sfHRLi.js → DID-D1igRb17.js} +2 -2
  24. package/src/assets/web-panel/assets/{Dashboard-q_eGdhha.js → Dashboard-DVAsrobk.js} +2 -2
  25. package/src/assets/web-panel/assets/{Dropdown-Cufrh2Bz.js → Dropdown-Dl7W8AQs.js} +1 -1
  26. package/src/assets/web-panel/assets/{EmailListRenderer-B-kdv10f.js → EmailListRenderer-D5tpaEQC.js} +1 -1
  27. package/src/assets/web-panel/assets/{FamilyGuardDashboard-D21XjgfG.js → FamilyGuardDashboard-O_VQf8gq.js} +1 -1
  28. package/src/assets/web-panel/assets/{Federation-CAwRTLZH.js → Federation-BTVcgS9n.js} +1 -1
  29. package/src/assets/web-panel/assets/{FormItemContext-vx3daNDF.js → FormItemContext-BRnkJAIz.js} +1 -1
  30. package/src/assets/web-panel/assets/{GenericCardRenderer-CRWY2wU4.js → GenericCardRenderer-8OWSCkDj.js} +1 -1
  31. package/src/assets/web-panel/assets/{Git-Q6SwauyD.js → Git-WXLYTQj2.js} +2 -2
  32. package/src/assets/web-panel/assets/{Governance-BJ1q4IQZ.js → Governance-BezaUhtc.js} +1 -1
  33. package/src/assets/web-panel/assets/{Inference-CSWjROgD.js → Inference-CuRay3Gu.js} +1 -1
  34. package/src/assets/web-panel/assets/{KnowledgeGraph-fzuQsWuY.js → KnowledgeGraph-DfWLDW1m.js} +1 -1
  35. package/src/assets/web-panel/assets/{Logs-DVF8Mnns.js → Logs-C55y2pPY.js} +2 -2
  36. package/src/assets/web-panel/assets/MarkdownRenderer-hDpWdiBc.js +1 -0
  37. package/src/assets/web-panel/assets/{Marketplace-BQP7LOA4.js → Marketplace-Dk08Uycg.js} +1 -1
  38. package/src/assets/web-panel/assets/{McpTools-BNlJCmNc.js → McpTools-C11fSB5V.js} +4 -4
  39. package/src/assets/web-panel/assets/{Memory-DLLg5WQ4.js → Memory-mr0eZc97.js} +2 -2
  40. package/src/assets/web-panel/assets/{MobileBridge-CR2skNAF.js → MobileBridge-C0iCSRbb.js} +1 -1
  41. package/src/assets/web-panel/assets/{MobileProjects-BxVavObl.js → MobileProjects-CY-xMG8Z.js} +1 -1
  42. package/src/assets/web-panel/assets/{Mtc-B17pgqMI.js → Mtc-Bplqc_Wc.js} +4 -4
  43. package/src/assets/web-panel/assets/{MtcAudit-4UmV5cIL.js → MtcAudit-BlzwsoSM.js} +2 -2
  44. package/src/assets/web-panel/assets/{Multisig-DoMEXEcU.js → Multisig-BBLmTty6.js} +3 -3
  45. package/src/assets/web-panel/assets/{NLProgramming-h9DMXFX4.js → NLProgramming-DtT1uf1W.js} +1 -1
  46. package/src/assets/web-panel/assets/{Notes-Cihn-xX8.js → Notes-DcqQAxTK.js} +3 -3
  47. package/src/assets/web-panel/assets/{NotificationSettings-BE6ZGa3R.js → NotificationSettings-cb0kWoZe.js} +1 -1
  48. package/src/assets/web-panel/assets/{OrderTableRenderer-CnwojoSI.js → OrderTableRenderer-kw9HZQNN.js} +1 -1
  49. package/src/assets/web-panel/assets/{Organization-B2vpwmjb.js → Organization-DlTlbkUN.js} +4 -4
  50. package/src/assets/web-panel/assets/{Overflow-C4z28R0-.js → Overflow-pp1qs-oY.js} +1 -1
  51. package/src/assets/web-panel/assets/{P2P-BVlFkwhW.js → P2P-BESLnyYz.js} +2 -2
  52. package/src/assets/web-panel/assets/{PdhVaultBrowser-BXbEdL5B.js → PdhVaultBrowser-B-J1mGuf.js} +3 -3
  53. package/src/assets/web-panel/assets/{Permissions-C28xs4lp.js → Permissions-B36PeT1_.js} +4 -4
  54. package/src/assets/web-panel/assets/{PersonalDataHub-Dgl_rBjM.js → PersonalDataHub-CTK2ad-3.js} +3 -3
  55. package/src/assets/web-panel/assets/{Pipeline-3QUIhrKI.js → Pipeline-zJNGXsac.js} +1 -1
  56. package/src/assets/web-panel/assets/{Privacy-8Gh33OZ5.js → Privacy-b9fz0Qf0.js} +1 -1
  57. package/src/assets/web-panel/assets/{ProjectInit-BNmg4tZi.js → ProjectInit-DjZbZgiB.js} +2 -2
  58. package/src/assets/web-panel/assets/{ProjectSettings-vgMfeCf9.js → ProjectSettings-C-hHJXlD.js} +2 -2
  59. package/src/assets/web-panel/assets/Projects-BC9KSDM6.js +1 -0
  60. package/src/assets/web-panel/assets/{Providers-CXoOa8eX.js → Providers-Dz-CAYYU.js} +1 -1
  61. package/src/assets/web-panel/assets/{QrScannerModal-BhfTF0oS.js → QrScannerModal-A0yoQ3-3.js} +1 -1
  62. package/src/assets/web-panel/assets/{QuickAsk-C746HEAj.js → QuickAsk-DrFgFJNC.js} +1 -1
  63. package/src/assets/web-panel/assets/{Recommend-BSej8Eo0.js → Recommend-KC8hF1g4.js} +1 -1
  64. package/src/assets/web-panel/assets/{RemoteSession-f3gmnlG3.js → RemoteSession-DGTPIk6u.js} +3 -3
  65. package/src/assets/web-panel/assets/{Reputation-CyvybpkN.js → Reputation-QmbwM7Yk.js} +1 -1
  66. package/src/assets/web-panel/assets/{Row-DwV2PeYn.js → Row-BxjJylia.js} +1 -1
  67. package/src/assets/web-panel/assets/{RssFeed-11GrzjZy.js → RssFeed-B7Wda1J6.js} +3 -3
  68. package/src/assets/web-panel/assets/{Search-BjKXkrAY.js → Search-_plQ_YSA.js} +1 -1
  69. package/src/assets/web-panel/assets/{Security-eWiFb9Yk.js → Security-CD2YJZfx.js} +2 -2
  70. package/src/assets/web-panel/assets/{Services-CdCsMAtt.js → Services-qQE7NmwE.js} +2 -2
  71. package/src/assets/web-panel/assets/{Skeleton-4Q2UTKQ5.js → Skeleton-DgQqkFf7.js} +1 -1
  72. package/src/assets/web-panel/assets/{Skills-v4rtYrRj.js → Skills-C4C0oFFt.js} +1 -1
  73. package/src/assets/web-panel/assets/{Sla-CRhsFvd_.js → Sla-Px2N2B5c.js} +1 -1
  74. package/src/assets/web-panel/assets/SpeechSettings-DN6C3lQd.js +1 -0
  75. package/src/assets/web-panel/assets/{SyncSettings-D16zonl7.js → SyncSettings-jm5aH_m7.js} +2 -2
  76. package/src/assets/web-panel/assets/{Tasks-Xxozz0i_.js → Tasks-DlkJcv67.js} +1 -1
  77. package/src/assets/web-panel/assets/{Templates-CXJpPtCT.js → Templates-DyrTHUBs.js} +1 -1
  78. package/src/assets/web-panel/assets/{Tenant-XRV0L1ZF.js → Tenant-mC434PtL.js} +1 -1
  79. package/src/assets/web-panel/assets/{Terminal-CYuO1i_w.js → Terminal-o0_s3NgK.js} +2 -2
  80. package/src/assets/web-panel/assets/{TimelineRenderer-BXqitWsu.js → TimelineRenderer-DAGlAXOw.js} +1 -1
  81. package/src/assets/web-panel/assets/{Tokens-BvPrDHIy.js → Tokens-BnulS_bs.js} +1 -1
  82. package/src/assets/web-panel/assets/{Trigger-DhCrSTf5.js → Trigger-suQbVXYM.js} +1 -1
  83. package/src/assets/web-panel/assets/{Trust-DmsuZD6K.js → Trust-DbIJAPo5.js} +1 -1
  84. package/src/assets/web-panel/assets/{UkeySign-D_yrts5C.js → UkeySign-CQNpbIHi.js} +1 -1
  85. package/src/assets/web-panel/assets/{VideoEditing-B01ihPrm.js → VideoEditing-D8aWCERk.js} +1 -1
  86. package/src/assets/web-panel/assets/{Wallet-DpUjKa-N.js → Wallet-CuLpYfZc.js} +2 -2
  87. package/src/assets/web-panel/assets/{WebAuthn-CL07yON6.js → WebAuthn-CsfG8ZMc.js} +2 -2
  88. package/src/assets/web-panel/assets/{WorkflowEditor-CLMflnRr.js → WorkflowEditor-BYsEAZbd.js} +1 -1
  89. package/src/assets/web-panel/assets/{chat-DtUqe8h_.js → chat-FT4Um3-I.js} +1 -1
  90. package/src/assets/web-panel/assets/{colors-DPKrgVfy.js → colors-CKbS_Wlt.js} +1 -1
  91. package/src/assets/web-panel/assets/{compact-item-BTt2GtOm.js → compact-item-CFJtzuJM.js} +1 -1
  92. package/src/assets/web-panel/assets/{createContext-D_VeUc1J.js → createContext-B9kSRW6K.js} +1 -1
  93. package/src/assets/web-panel/assets/devWarning-DJZ0gAMu.js +1 -0
  94. package/src/assets/web-panel/assets/{hasIn-1kndiylj.js → hasIn-DR-x0Xpi.js} +1 -1
  95. package/src/assets/web-panel/assets/{index-dVc-CXY4.js → index-7jHr_A_k.js} +1 -1
  96. package/src/assets/web-panel/assets/{index-DFIZ_1Sf.js → index-B3ZX81mK.js} +1 -1
  97. package/src/assets/web-panel/assets/{index-fk2Rjacw.js → index-B7osrXqy.js} +3 -3
  98. package/src/assets/web-panel/assets/{index-CHG-KcS4.js → index-BGbPnC5x.js} +1 -1
  99. package/src/assets/web-panel/assets/{index-Dbbymxpj.js → index-BI5hP_qy.js} +1 -1
  100. package/src/assets/web-panel/assets/{index-BaZAbw9A.js → index-BK3TiKVq.js} +1 -1
  101. package/src/assets/web-panel/assets/{index-CzjkKUmR.js → index-BVPU43b1.js} +1 -1
  102. package/src/assets/web-panel/assets/{index-BAXfRKfG.js → index-BW-t9n-q.js} +1 -1
  103. package/src/assets/web-panel/assets/{index-8nz_fmlj.js → index-BfFCQHL3.js} +1 -1
  104. package/src/assets/web-panel/assets/index-Bizb4hkw.js +1 -0
  105. package/src/assets/web-panel/assets/{index-DdkplL9R.js → index-Bt4fS2eL.js} +1 -1
  106. package/src/assets/web-panel/assets/{index-DG2MZQ3f.js → index-BwR7yc2h.js} +1 -1
  107. package/src/assets/web-panel/assets/{index-DfKBRdSS.js → index-Bzz0C1BZ.js} +1 -1
  108. package/src/assets/web-panel/assets/{index-GsoUQ2M7.js → index-C2JvmYRc.js} +1 -1
  109. package/src/assets/web-panel/assets/{index-l1BETrDb.js → index-CGaXUsIs.js} +1 -1
  110. package/src/assets/web-panel/assets/{index-4bna2_SR.js → index-CJmIQ9XR.js} +1 -1
  111. package/src/assets/web-panel/assets/{index-DfGl8CqG.js → index-C_enk9I_.js} +1 -1
  112. package/src/assets/web-panel/assets/{index-D95OFht7.js → index-Cr2FLUsD.js} +1 -1
  113. package/src/assets/web-panel/assets/{index-DsJCDUJG.js → index-CvrCCqJt.js} +1 -1
  114. package/src/assets/web-panel/assets/{index-sDoMHTNA.js → index-D4LfPvWA.js} +1 -1
  115. package/src/assets/web-panel/assets/{index-By5n8up9.js → index-DMGmg497.js} +1 -1
  116. package/src/assets/web-panel/assets/{index-ocf06EVQ.js → index-DShSkww-.js} +1 -1
  117. package/src/assets/web-panel/assets/{index-Bhudc_Ez.js → index-DTxNy0ZU.js} +1 -1
  118. package/src/assets/web-panel/assets/{index-CX81qSM4.js → index-DW4BWjTk.js} +1 -1
  119. package/src/assets/web-panel/assets/{index-BlDNVgBt.js → index-DWdqx7zI.js} +1 -1
  120. package/src/assets/web-panel/assets/{index-CcO04eDn.js → index-Dap9c3eD.js} +1 -1
  121. package/src/assets/web-panel/assets/{index-Dwqmtk65.js → index-DcfxhKXR.js} +1 -1
  122. package/src/assets/web-panel/assets/{index-2eyAXE3d.js → index-DdkIhfi-.js} +1 -1
  123. package/src/assets/web-panel/assets/{index-brCInrzq.js → index-DeSgw-WV.js} +1 -1
  124. package/src/assets/web-panel/assets/{index-DJ8vXGOa.js → index-DiNUEpSQ.js} +1 -1
  125. package/src/assets/web-panel/assets/{index-BHpBMWCh.js → index-DjEP7WkH.js} +1 -1
  126. package/src/assets/web-panel/assets/{index-m31Ka8hZ.js → index-DtkFqPVA.js} +1 -1
  127. package/src/assets/web-panel/assets/{index-CtF7EN49.js → index-KqDaCApw.js} +1 -1
  128. package/src/assets/web-panel/assets/index-OHSl-xCh.js +1 -0
  129. package/src/assets/web-panel/assets/{index-B9KvcS7R.js → index-OSzjTzGM.js} +1 -1
  130. package/src/assets/web-panel/assets/{index-CauoBQkH.js → index-QBSeNVO3.js} +1 -1
  131. package/src/assets/web-panel/assets/{index-FzdwcSy2.js → index-WE08gMJP.js} +1 -1
  132. package/src/assets/web-panel/assets/{index-DxdTdBix.js → index-r2VI1Ikk.js} +1 -1
  133. package/src/assets/web-panel/assets/{index-BepLZwgB.js → index-tqSEHPRT.js} +1 -1
  134. package/src/assets/web-panel/assets/{initDefaultProps-CvyYJd7z.js → initDefaultProps-Dd7n7VgI.js} +1 -1
  135. package/src/assets/web-panel/assets/{motion-DYZkhUdz.js → motion-BwxouRw1.js} +1 -1
  136. package/src/assets/web-panel/assets/{move-slnJRVT1.js → move-DObN0PG9.js} +1 -1
  137. package/src/assets/web-panel/assets/{mtc-parser-DVc0CKmy.js → mtc-parser-B3nOUQc7.js} +1 -1
  138. package/src/assets/web-panel/assets/{omit-BCXAtHCq.js → omit-o9WU2Nbl.js} +1 -1
  139. package/src/assets/web-panel/assets/{pickAttrs-DBsemz_K.js → pickAttrs-CL_vvfQ_.js} +1 -1
  140. package/src/assets/web-panel/assets/{placementArrow-BRtkJ-nv.js → placementArrow-CYrM2tyK.js} +1 -1
  141. package/src/assets/web-panel/assets/{responsiveObserve-Cebq7EZn.js → responsiveObserve-k_06cQ96.js} +1 -1
  142. package/src/assets/web-panel/assets/{slide-DT7qvId2.js → slide-CPKG0pxS.js} +1 -1
  143. package/src/assets/web-panel/assets/{statusUtils-pQiITLkG.js → statusUtils-BDDEeLTw.js} +1 -1
  144. package/src/assets/web-panel/assets/{styleChecker-c-19BVKQ.js → styleChecker-Cmb7RTh7.js} +1 -1
  145. package/src/assets/web-panel/assets/{useFlexGapSupport-DsS5-0bE.js → useFlexGapSupport-e2IedC4N.js} +1 -1
  146. package/src/assets/web-panel/assets/{useFs-CxGiMe5n.js → useFs-CE_gxVnm.js} +1 -1
  147. package/src/assets/web-panel/assets/{usePersonalDataHub-D9btVID5.js → usePersonalDataHub-BkMIIKMz.js} +1 -1
  148. package/src/assets/web-panel/assets/{vnode-CUYFsFEN.js → vnode-DW886XV1.js} +1 -1
  149. package/src/assets/web-panel/assets/{zoom-CXmn_35j.js → zoom-Dwo_adaf.js} +1 -1
  150. package/src/assets/web-panel/index.html +1 -1
  151. package/src/command-help-index.json +3 -3
  152. package/src/commands/agent.js +105 -35
  153. package/src/commands/artifacts.js +363 -33
  154. package/src/commands/cowork.js +202 -36
  155. package/src/commands/session-budget.js +155 -0
  156. package/src/commands/session-location.js +948 -0
  157. package/src/commands/session.js +72 -46
  158. package/src/data/changelog.json +26 -0
  159. package/src/gateways/ws/artifact-protocol.js +77 -13
  160. package/src/gateways/ws/session-protocol.js +391 -24
  161. package/src/gateways/ws/ws-agent-handler.js +191 -14
  162. package/src/gateways/ws/ws-server.js +14 -3
  163. package/src/gateways/ws/ws-session-gateway.js +101 -5
  164. package/src/harness/jsonl-session-store.js +1210 -0
  165. package/src/lib/agent-team/team-runner.js +43 -13
  166. package/src/lib/artifact-access-ledger.js +461 -0
  167. package/src/lib/artifact-cleanup-ledger.js +861 -0
  168. package/src/lib/artifact-deletion-ledger.js +677 -0
  169. package/src/lib/artifact-store.js +256 -51
  170. package/src/lib/background-agent-keeper-protocol.js +75 -4
  171. package/src/lib/background-agent-launch-barrier.js +74 -0
  172. package/src/lib/background-agent-supervisor.js +149 -5
  173. package/src/lib/background-turn-bootstrap-protocol.js +4 -0
  174. package/src/lib/command-lifecycle-report.js +8 -4
  175. package/src/lib/cowork-adapter.js +9 -5
  176. package/src/lib/cowork-task-runner.js +20 -0
  177. package/src/lib/cowork-workflow.js +178 -20
  178. package/src/lib/direct-model-usage.js +62 -22
  179. package/src/lib/dynamic-workflow-runtime.js +3184 -111
  180. package/src/lib/execution-location-result-apply.js +339 -0
  181. package/src/lib/execution-location-result-artifact.js +271 -0
  182. package/src/lib/execution-location-result-review.js +253 -0
  183. package/src/lib/execution-location-result-store.js +331 -0
  184. package/src/lib/execution-location-result.js +617 -0
  185. package/src/lib/execution-location-target.js +236 -1
  186. package/src/lib/managed-tool-checkpoint.js +47 -4
  187. package/src/lib/process-execution-broker/workspace-transaction.js +3 -0
  188. package/src/lib/session-budget-production-root.js +376 -0
  189. package/src/lib/session-budget-runtime.js +109 -18
  190. package/src/lib/session-budget-usage.js +63 -0
  191. package/src/lib/session-host-snapshot.js +19 -2
  192. package/src/lib/session-resource-budget.js +766 -105
  193. package/src/lib/sub-agent-context.js +69 -22
  194. package/src/lib/web-ui-server.js +12 -1
  195. package/src/lib/with-file-lock.js +175 -26
  196. package/src/repl/agent-repl.js +237 -16
  197. package/src/runtime/agent-core.js +123 -0
  198. package/src/runtime/headless-runner.js +135 -46
  199. package/src/runtime/headless-stream.js +133 -25
  200. package/src/runtime/policies/agent-policy.js +10 -0
  201. package/src/workers/background-agent-keeper.js +112 -19
  202. package/src/workers/background-agent-worker.js +383 -134
  203. package/src/workers/background-turn-bootstrap.js +13 -8
  204. package/src/assets/web-panel/assets/ChatBubbleRenderer-CY5m8ZHg.js +0 -1
  205. package/src/assets/web-panel/assets/MarkdownRenderer-BLif4QSg.js +0 -1
  206. package/src/assets/web-panel/assets/Projects-BhtAVilc.js +0 -1
  207. package/src/assets/web-panel/assets/SpeechSettings-DLjKsDVu.js +0 -1
  208. package/src/assets/web-panel/assets/devWarning-Bj5nUW2v.js +0 -1
  209. package/src/assets/web-panel/assets/index-CPcM-eqo.js +0 -1
  210. package/src/assets/web-panel/assets/index-xeSyVoRe.js +0 -1
@@ -67,6 +67,7 @@ import { registerSessionMcpRecoveryCommands } from "./session-mcp-recovery.js";
67
67
  import { registerSessionShowSubcommand } from "./session-show.js";
68
68
  import { registerSessionObservabilitySubcommand } from "./session-observability.js";
69
69
  import { registerSessionLocationSubcommands } from "./session-location.js";
70
+ import { registerSessionBudgetCommands } from "./session-budget.js";
70
71
 
71
72
  export const _deps = {
72
73
  execFileSync: (...args) => executionBroker.execFileSync(...args),
@@ -103,8 +104,9 @@ function _sessionEpoch(ts) {
103
104
  * @returns {{statusBar:string, autoMerge:{allow:boolean,reason:string,unmet:string[]}, lines:string[]}}
104
105
  */
105
106
  export async function renderPrStatus(signals = {}, opts = {}) {
106
- const { strictAutoMergeDecision, describePrStatusBar } =
107
- await import("../lib/pr-automation-policy.js");
107
+ const { strictAutoMergeDecision, describePrStatusBar } = await import(
108
+ "../lib/pr-automation-policy.js"
109
+ );
108
110
  const autoMerge = strictAutoMergeDecision({
109
111
  enabled: opts.enabled === true,
110
112
  hasOpenPr: signals.hasOpenPr,
@@ -224,6 +226,7 @@ export function registerSessionCommand(program) {
224
226
 
225
227
  registerSessionMcpRecoveryCommands(session);
226
228
  registerSessionLocationSubcommands(session);
229
+ registerSessionBudgetCommands(session);
227
230
 
228
231
  // session list
229
232
  session
@@ -347,22 +350,25 @@ export function registerSessionCommand(program) {
347
350
  sourceErrors.local = error?.message || String(error);
348
351
  }
349
352
  try {
350
- const { listBackgroundAgents } =
351
- await import("../lib/background-agent-supervisor.js");
353
+ const { listBackgroundAgents } = await import(
354
+ "../lib/background-agent-supervisor.js"
355
+ );
352
356
  background = listBackgroundAgents({ all: true });
353
357
  } catch (error) {
354
358
  sourceErrors.background = error?.message || String(error);
355
359
  }
356
360
  try {
357
- const { readRemoteControlStates } =
358
- await import("../lib/remote-control.js");
361
+ const { readRemoteControlStates } = await import(
362
+ "../lib/remote-control.js"
363
+ );
359
364
  remote = readRemoteControlStates();
360
365
  } catch (error) {
361
366
  sourceErrors.remote = error?.message || String(error);
362
367
  }
363
368
  try {
364
- const { listCollaborationRuns } =
365
- await import("../lib/collaboration-run-store.js");
369
+ const { listCollaborationRuns } = await import(
370
+ "../lib/collaboration-run-store.js"
371
+ );
366
372
  team = listCollaborationRuns({ limit }).filter(
367
373
  (run) => run?.kind === "team",
368
374
  );
@@ -387,8 +393,9 @@ export function registerSessionCommand(program) {
387
393
  // engine proves that the exact worktree is supported. Copy-mode
388
394
  // checkpoints need explicit paths and therefore cannot truthfully be
389
395
  // offered as a one-click session action.
390
- const { isCheckpointAvailable } =
391
- await import("../lib/checkpoint-store.js");
396
+ const { isCheckpointAvailable } = await import(
397
+ "../lib/checkpoint-store.js"
398
+ );
392
399
  const capability = new Map();
393
400
  const decorate = (items, pathFor, sessionFor) =>
394
401
  items.map((item) => {
@@ -431,8 +438,10 @@ export function registerSessionCommand(program) {
431
438
  // checkpoint action unavailable with its explicit reason.
432
439
  }
433
440
  try {
434
- const { ArtifactStore } = await import("../lib/artifact-store.js");
435
- artifacts = new ArtifactStore().list();
441
+ const { ArtifactStore, publicArtifactMetadata } = await import(
442
+ "../lib/artifact-store.js"
443
+ );
444
+ artifacts = new ArtifactStore().list().map(publicArtifactMetadata);
436
445
  } catch {
437
446
  // Summaries are optional; absence never removes a session.
438
447
  }
@@ -443,8 +452,9 @@ export function registerSessionCommand(program) {
443
452
  // Summaries are optional; absence never removes a session.
444
453
  }
445
454
 
446
- const { buildSessionProjection } =
447
- await import("../lib/session-projection.js");
455
+ const { buildSessionProjection } = await import(
456
+ "../lib/session-projection.js"
457
+ );
448
458
  const projection = buildSessionProjection({
449
459
  local,
450
460
  background,
@@ -468,8 +478,9 @@ export function registerSessionCommand(program) {
468
478
  }
469
479
  }
470
480
  } catch (error) {
471
- const { disconnectedSessionProjection } =
472
- await import("../lib/session-projection.js");
481
+ const { disconnectedSessionProjection } = await import(
482
+ "../lib/session-projection.js"
483
+ );
473
484
  if (options.json) {
474
485
  jsonPayload = JSON.stringify(
475
486
  disconnectedSessionProjection(error?.message || String(error)),
@@ -519,8 +530,9 @@ export function registerSessionCommand(program) {
519
530
  } else {
520
531
  // Live path: resolve the session's linked PR and fetch via gh.
521
532
  const { getPrLinks } = await import("../lib/pr-link-ledger.js");
522
- const { getLastSessionId } =
523
- await import("../harness/jsonl-session-store.js");
533
+ const { getLastSessionId } = await import(
534
+ "../harness/jsonl-session-store.js"
535
+ );
524
536
  const sid = !id || id === "last" ? getLastSessionId() : id;
525
537
  const links = sid ? getPrLinks(sid) : [];
526
538
  if (links.length === 0) {
@@ -598,8 +610,9 @@ export function registerSessionCommand(program) {
598
610
  // (single / non-TTY / Ctrl-C). Same helper as `cc agent --resume`.
599
611
  if (!id) {
600
612
  ctx = await bootstrap({ verbose: program.opts().verbose });
601
- const { pickRecentSession } =
602
- await import("../lib/session-picker.js");
613
+ const { pickRecentSession } = await import(
614
+ "../lib/session-picker.js"
615
+ );
603
616
  const picked = await pickRecentSession(ctx);
604
617
  if (!picked.id) {
605
618
  logger.error(
@@ -629,8 +642,9 @@ export function registerSessionCommand(program) {
629
642
  if (jsonlId) {
630
643
  // Tamper gate: a broken hash chain means the transcript was edited
631
644
  // outside the store — never silently rebuild it as trusted context.
632
- const { verifySession } =
633
- await import("../harness/jsonl-session-store.js");
645
+ const { verifySession } = await import(
646
+ "../harness/jsonl-session-store.js"
647
+ );
634
648
  const trust = verifySession(jsonlId);
635
649
  if (["missing", "conflict"].includes(trust.status)) {
636
650
  logger.error(
@@ -743,8 +757,9 @@ export function registerSessionCommand(program) {
743
757
  );
744
758
  }
745
759
  if (sid) {
746
- const { renderAgentSessionMarkdown } =
747
- await import("../lib/agent-session-export.js");
760
+ const { renderAgentSessionMarkdown } = await import(
761
+ "../lib/agent-session-export.js"
762
+ );
748
763
  markdown = renderAgentSessionMarkdown(sid, store.readEvents(sid), {
749
764
  exportedAt: new Date().toISOString(),
750
765
  });
@@ -997,8 +1012,9 @@ export function registerSessionCommand(program) {
997
1012
  }
998
1013
  let result;
999
1014
  if (jsonlId) {
1000
- const { renameSession } =
1001
- await import("../harness/jsonl-session-store.js");
1015
+ const { renameSession } = await import(
1016
+ "../harness/jsonl-session-store.js"
1017
+ );
1002
1018
  result = renameSession(jsonlId, normalized);
1003
1019
  } else {
1004
1020
  ctx = await bootstrap({ verbose: program.opts().verbose });
@@ -1037,8 +1053,9 @@ export function registerSessionCommand(program) {
1037
1053
  .option("--json", "Output as JSON")
1038
1054
  .action(async (options) => {
1039
1055
  try {
1040
- const { pruneJsonlSessions } =
1041
- await import("../harness/jsonl-session-store.js");
1056
+ const { pruneJsonlSessions } = await import(
1057
+ "../harness/jsonl-session-store.js"
1058
+ );
1042
1059
  const result = pruneJsonlSessions({
1043
1060
  olderThanDays: Number(options.olderThan),
1044
1061
  keep: options.keep != null ? Number(options.keep) : undefined,
@@ -1416,8 +1433,9 @@ export function registerSessionCommand(program) {
1416
1433
  .option("--json", "Output as JSON")
1417
1434
  .action(async (id, options) => {
1418
1435
  try {
1419
- const { getApprovalGate } =
1420
- await import("../lib/session-core-singletons.js");
1436
+ const { getApprovalGate } = await import(
1437
+ "../lib/session-core-singletons.js"
1438
+ );
1421
1439
  const gate = await getApprovalGate();
1422
1440
  if (options.set) {
1423
1441
  gate.setSessionPolicy(id, options.set);
@@ -1453,8 +1471,9 @@ export function registerSessionCommand(program) {
1453
1471
  .option("--json", "Output as JSON")
1454
1472
  .action(async (options) => {
1455
1473
  try {
1456
- const { getSessionManager } =
1457
- await import("../lib/session-core-singletons.js");
1474
+ const { getSessionManager } = await import(
1475
+ "../lib/session-core-singletons.js"
1476
+ );
1458
1477
  const mgr = getSessionManager();
1459
1478
  const live = mgr.list({
1460
1479
  agentId: options.agent,
@@ -1498,8 +1517,9 @@ export function registerSessionCommand(program) {
1498
1517
  .argument("<id>", "Session ID")
1499
1518
  .action(async (id) => {
1500
1519
  try {
1501
- const { getSessionManager } =
1502
- await import("../lib/session-core-singletons.js");
1520
+ const { getSessionManager } = await import(
1521
+ "../lib/session-core-singletons.js"
1522
+ );
1503
1523
  const mgr = getSessionManager();
1504
1524
  if (!mgr.has(id)) {
1505
1525
  logger.error(`Session ${id} is not active in this process`);
@@ -1524,8 +1544,9 @@ export function registerSessionCommand(program) {
1524
1544
  .argument("<id>", "Session ID")
1525
1545
  .action(async (id) => {
1526
1546
  try {
1527
- const { getSessionManager } =
1528
- await import("../lib/session-core-singletons.js");
1547
+ const { getSessionManager } = await import(
1548
+ "../lib/session-core-singletons.js"
1549
+ );
1529
1550
  const mgr = getSessionManager();
1530
1551
  const ok = await mgr.resume(id);
1531
1552
  if (!ok) {
@@ -1554,12 +1575,14 @@ export function registerSessionCommand(program) {
1554
1575
  .option("--agent-id <id>", "Agent id for scope=agent")
1555
1576
  .action(async (id, options) => {
1556
1577
  try {
1557
- const { getSessionManager } =
1558
- await import("../lib/session-core-singletons.js");
1578
+ const { getSessionManager } = await import(
1579
+ "../lib/session-core-singletons.js"
1580
+ );
1559
1581
  if (options.consolidate) {
1560
1582
  try {
1561
- const { consolidateJsonlSession } =
1562
- await import("../lib/session-consolidator.js");
1583
+ const { consolidateJsonlSession } = await import(
1584
+ "../lib/session-consolidator.js"
1585
+ );
1563
1586
  const res = await consolidateJsonlSession(id, {
1564
1587
  scope: options.scope,
1565
1588
  scopeId: options.scopeId || null,
@@ -1778,8 +1801,9 @@ export function registerSessionCommand(program) {
1778
1801
  );
1779
1802
  process.exit(1);
1780
1803
  }
1781
- const { sessionUsage, allSessionsUsage } =
1782
- await import("../lib/session-usage.js");
1804
+ const { sessionUsage, allSessionsUsage } = await import(
1805
+ "../lib/session-usage.js"
1806
+ );
1783
1807
  const result = id
1784
1808
  ? sessionUsage(id)
1785
1809
  : allSessionsUsage({ limit: parseInt(options.limit, 10) || 1000 });
@@ -1852,8 +1876,9 @@ export function registerSessionCommand(program) {
1852
1876
  .option("--json", "Machine-readable JSON output")
1853
1877
  .action(async (id) => {
1854
1878
  try {
1855
- const { getVerifiedSessionObservabilityAuthority } =
1856
- await import("../harness/jsonl-session-store.js");
1879
+ const { getVerifiedSessionObservabilityAuthority } = await import(
1880
+ "../harness/jsonl-session-store.js"
1881
+ );
1857
1882
  const authority = getVerifiedSessionObservabilityAuthority(id);
1858
1883
  console.log(
1859
1884
  JSON.stringify(
@@ -2291,8 +2316,9 @@ async function mirrorPruneSessions() {
2291
2316
  * (`session.mirror.encryption`). Requires both to be configured.
2292
2317
  */
2293
2318
  async function mirrorRotateKey() {
2294
- const { createMirror, createMirrorCipher, rotateMirrorKey } =
2295
- await import("../harness/session-mirror.js");
2319
+ const { createMirror, createMirrorCipher, rotateMirrorKey } = await import(
2320
+ "../harness/session-mirror.js"
2321
+ );
2296
2322
  const { cfg } = await loadConfiguredMirror();
2297
2323
  if (!cfg || !cfg.kind || cfg.kind === "none") {
2298
2324
  return { target: null };
@@ -1,6 +1,32 @@
1
1
  {
2
2
  "source": "CHANGELOG.md",
3
3
  "releases": [
4
+ {
5
+ "productVersion": null,
6
+ "cliVersion": "0.165.4",
7
+ "cliVersions": ["0.165.3", "0.165.4"],
8
+ "date": "2026-08-20",
9
+ "title": "",
10
+ "sections": [
11
+ {
12
+ "heading": "Fixed - cc CLI 0.165.4: first install without a native build toolchain",
13
+ "body": "> `chainlesschain` **0.165.3 -> 0.165.4** (candidate; not yet published,\n> 2026-08-20).\n> CLI release includes `@chainlesschain/personal-data-hub` **0.4.59**;\n> `@chainlesschain/agent-sdk` remains **0.1.7**.\n\n- **Portable first install**: Personal Data Hub now declares\n `better-sqlite3-multiple-ciphers` as an optional dependency. If a prebuilt\n binary cannot be downloaded, npm may skip the failed `node-gyp` fallback\n instead of aborting `npm install -g chainlesschain`; the CLI remains usable\n through its bundled `sql.js` WASM fallback.\n- **No-toolchain install gate**: the Windows and Linux global-install smoke\n deliberately disables native prebuilds and points node-gyp at a nonexistent\n Python executable. The packed candidate must still install and both `cc` and\n `chainlesschain` must start without `--ignore-scripts`.\n- **Release status**: this is source-level candidate evidence only. Publication\n still requires the exact release commit to pass the complete Linux, Windows,\n and macOS `CLI CI` and `CLI Strict Sandbox` matrices before the coordinated\n PDH and CLI packages are published and independently read back."
14
+ }
15
+ ]
16
+ },
17
+ {
18
+ "productVersion": null,
19
+ "cliVersion": "0.165.3",
20
+ "cliVersions": ["0.165.2", "0.165.3"],
21
+ "date": "2026-08-19",
22
+ "title": "",
23
+ "sections": [
24
+ {
25
+ "heading": "Fixed — cc CLI 0.165.3: durable background keeper retirement",
26
+ "body": "> `chainlesschain` **0.165.2 -> 0.165.3** (candidate; not yet published,\n> 2026-08-19).\n> CLI-only candidate; `@chainlesschain/personal-data-hub` remains **0.4.58**\n> and `@chainlesschain/agent-sdk` remains **0.1.7**.\n\n- **Durable keeper retirement evidence**: a Worker accepts a lost keeper\n response only when the persisted retirement record matches the exact worker\n generation, turn attempt, process identities, start anchors, and cleanup\n confirmation. Ambiguous or partial records continue to fail closed.\n- **Bounded keeper health probes**: Windows process-identity checks are delayed\n until the application heartbeat is actually silent, avoiding synchronized\n helper-process storms while preserving an exact-identity backstop before\n cleanup.\n- **Recoverable lock publication**: a lock owned by a provably dead process can\n be reclaimed even when that owner published its release marker but crashed\n before removing its private staging path. Active or identity-mismatched\n owners remain fenced.\n- **Idempotent bootstrap release**: a matching bootstrap release can be replayed\n after READY, and the Worker retransmits it when READY is repeated. Nonce,\n generation, attempt, wrapper PID, and runtime PID mismatches remain rejected.\n- **Release status**: immutable tag, final source SHA, workflow run IDs, npm\n provenance, package digests, and registry readback remain intentionally\n absent until the exact `0.165.3` candidate passes complete `CLI CI`,\n `CLI Strict Sandbox`, and the dedicated cross-platform keeper soak, followed\n by the npm release and independent public readback workflows."
27
+ }
28
+ ]
29
+ },
4
30
  {
5
31
  "productVersion": null,
6
32
  "cliVersion": "0.165.2",
@@ -11,7 +11,8 @@
11
11
  * mime, encoding, content, size,
12
12
  * truncated, previewable}
13
13
  * artifact-remove {artifactId} → {type:"artifact-remove", removed, found}
14
- * artifact-clean {} → {type:"artifact-clean", removed}
14
+ * artifact-clean {cleanupId?} → {type:"artifact-clean", cleanupId,
15
+ * removed, settled, cleanup}
15
16
  *
16
17
  * Preview policy: text mimes stream as utf8 (capped, `truncated` flagged);
17
18
  * images as base64 (hard cap — an oversized image reports previewable:false
@@ -25,6 +26,10 @@
25
26
 
26
27
  import path from "node:path";
27
28
  import { readFileSync, statSync } from "node:fs";
29
+ import { publicArtifactMetadata } from "../../lib/artifact-store.js";
30
+ import { authorizeArtifactContentAccess } from "../../lib/artifact-access-ledger.js";
31
+ import { settleArtifactDeletion } from "../../lib/artifact-deletion-ledger.js";
32
+ import { settleArtifactCleanup } from "../../lib/artifact-cleanup-ledger.js";
28
33
 
29
34
  /** Text preview cap (utf8 chars ≈ bytes for the common case). */
30
35
  export const TEXT_PREVIEW_CAP = 256 * 1024;
@@ -61,7 +66,11 @@ export async function handleArtifactList(server, id, ws, message) {
61
66
  if (message.kind) {
62
67
  artifacts = artifacts.filter((e) => e.kind === String(message.kind));
63
68
  }
64
- server._send(ws, { id, type: "artifact-list", artifacts });
69
+ server._send(ws, {
70
+ id,
71
+ type: "artifact-list",
72
+ artifacts: artifacts.map(publicArtifactMetadata),
73
+ });
65
74
  } catch (err) {
66
75
  sendError(server, id, ws, "ARTIFACT_LIST_FAILED", err.message);
67
76
  }
@@ -86,7 +95,7 @@ export async function handleArtifactShow(server, id, ws, message) {
86
95
  server._send(ws, {
87
96
  id,
88
97
  type: "artifact-show",
89
- artifact: { ...entry, storedPath: store.storedPath(entry) },
98
+ artifact: publicArtifactMetadata(entry),
90
99
  });
91
100
  } catch (err) {
92
101
  sendError(server, id, ws, "ARTIFACT_SHOW_FAILED", err.message);
@@ -161,9 +170,17 @@ export async function handleArtifactContent(server, id, ws, message) {
161
170
  reason: `image exceeds the ${IMAGE_PREVIEW_CAP} byte preview cap`,
162
171
  });
163
172
  }
164
- const body = readFileSync(storedPath);
173
+ const authorization = authorizeArtifactContentAccess(store, {
174
+ artifactId: entry.id,
175
+ client: "websocket",
176
+ action: "preview",
177
+ accessId: message.accessId,
178
+ });
179
+ const body = readFileSync(authorization.storedPath);
165
180
  return server._send(ws, {
166
181
  ...base,
182
+ access: authorization.access,
183
+ accessRecorded: authorization.recorded,
167
184
  previewable: true,
168
185
  encoding: "base64",
169
186
  truncated: false,
@@ -172,13 +189,23 @@ export async function handleArtifactContent(server, id, ws, message) {
172
189
  }
173
190
  // text
174
191
  const cap = Math.min(
175
- Number(message.maxBytes) > 0 ? Number(message.maxBytes) : TEXT_PREVIEW_CAP,
192
+ Number(message.maxBytes) > 0
193
+ ? Number(message.maxBytes)
194
+ : TEXT_PREVIEW_CAP,
176
195
  TEXT_PREVIEW_CAP,
177
196
  );
178
- const text = readFileSync(storedPath, "utf-8");
197
+ const authorization = authorizeArtifactContentAccess(store, {
198
+ artifactId: entry.id,
199
+ client: "websocket",
200
+ action: "preview",
201
+ accessId: message.accessId,
202
+ });
203
+ const text = readFileSync(authorization.storedPath, "utf-8");
179
204
  const truncated = text.length > cap;
180
205
  server._send(ws, {
181
206
  ...base,
207
+ access: authorization.access,
208
+ accessRecorded: authorization.recorded,
182
209
  previewable: true,
183
210
  encoding: "utf8",
184
211
  truncated,
@@ -195,25 +222,62 @@ export async function handleArtifactRemove(server, id, ws, message) {
195
222
  return sendError(server, id, ws, "NO_ARTIFACT_ID", "artifactId required");
196
223
  }
197
224
  const store = await loadStore();
198
- const found = store.remove(message.artifactId);
225
+ const deletion = settleArtifactDeletion(store, {
226
+ deletionId: message.deletionId,
227
+ artifactId: message.artifactId,
228
+ reason: "explicit",
229
+ client: "websocket",
230
+ });
199
231
  server._send(ws, {
200
232
  id,
201
233
  type: "artifact-remove",
202
234
  artifactId: message.artifactId,
203
- removed: found ? message.artifactId : null,
204
- found,
235
+ deletionId: deletion.deletionId,
236
+ removed: deletion.found ? message.artifactId : null,
237
+ found: deletion.found,
238
+ settled: deletion.settled,
239
+ recorded: deletion.recorded,
240
+ deletion: deletion.deletion,
205
241
  });
206
242
  } catch (err) {
207
- sendError(server, id, ws, "ARTIFACT_REMOVE_FAILED", err.message);
243
+ server._send(ws, {
244
+ id,
245
+ type: "error",
246
+ code: "ARTIFACT_REMOVE_FAILED",
247
+ message: err.message,
248
+ deletionId: err.deletionId || message.deletionId || null,
249
+ });
208
250
  }
209
251
  }
210
252
 
211
253
  export async function handleArtifactClean(server, id, ws, message) {
212
254
  try {
213
255
  const store = await loadStore();
214
- const { removed } = store.cleanupExpired();
215
- server._send(ws, { id, type: "artifact-clean", removed });
256
+ const cleanup = settleArtifactCleanup(store, {
257
+ cleanupId: message.cleanupId,
258
+ client: "websocket",
259
+ });
260
+ server._send(ws, {
261
+ id,
262
+ type: "artifact-clean",
263
+ cleanupId: cleanup.cleanupId,
264
+ removed: cleanup.removed,
265
+ removedNow: cleanup.removedNow,
266
+ alreadyAbsent: cleanup.alreadyAbsent,
267
+ selected: cleanup.selected,
268
+ settled: cleanup.settled,
269
+ recorded: cleanup.recorded,
270
+ cleanup: cleanup.cleanup,
271
+ items: cleanup.items,
272
+ });
216
273
  } catch (err) {
217
- sendError(server, id, ws, "ARTIFACT_CLEAN_FAILED", err.message);
274
+ server._send(ws, {
275
+ id,
276
+ type: "error",
277
+ code: "ARTIFACT_CLEAN_FAILED",
278
+ message: err.message,
279
+ cleanupId: err.cleanupId || message.cleanupId || null,
280
+ ...(err.cleanup ? { cleanup: err.cleanup } : {}),
281
+ });
218
282
  }
219
283
  }