chainlesschain 0.165.9 → 0.166.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 (190) hide show
  1. package/completions/_cc +2 -1
  2. package/completions/cc.bash +2 -2
  3. package/completions/cc.fish +2 -2
  4. package/completions/cc.ps1 +2 -1
  5. package/package.json +2 -2
  6. package/src/assets/web-panel/assets/{AIOps-DxwjrnEA.js → AIOps-D5_pwQ7M.js} +1 -1
  7. package/src/assets/web-panel/assets/{ActionButton-JdbYowzn.js → ActionButton-DgoYO32D.js} +1 -1
  8. package/src/assets/web-panel/assets/{Analytics-C06GCahv.js → Analytics-BIpoZ4QH.js} +3 -3
  9. package/src/assets/web-panel/assets/{AppLayout-BUVEEyi1.js → AppLayout-BJ3XrCEe.js} +3 -3
  10. package/src/assets/web-panel/assets/{Artifacts-D_ORzkJd.js → Artifacts-DUFs_izZ.js} +1 -1
  11. package/src/assets/web-panel/assets/{Audit-8o_Y5ejG.js → Audit-BZdPwwfL.js} +1 -1
  12. package/src/assets/web-panel/assets/{BackgroundAgents-DrkHd5VU.js → BackgroundAgents-DK9Fn-8B.js} +1 -1
  13. package/src/assets/web-panel/assets/{Backup-CKBZCX11.js → Backup-Bd6bOhV_.js} +1 -1
  14. package/src/assets/web-panel/assets/{BaseInput-C8HkI399.js → BaseInput-CRnWlXrd.js} +1 -1
  15. package/src/assets/web-panel/assets/{Chat-zb2H2Wux.js → Chat-D1G_yEl6.js} +6 -6
  16. package/src/assets/web-panel/assets/{ChatBubbleRenderer-BDcNpU_F.js → ChatBubbleRenderer-DDAlEtm-.js} +1 -1
  17. package/src/assets/web-panel/assets/{Checkbox-MwPtQmNz.js → Checkbox-CP35SH7R.js} +1 -1
  18. package/src/assets/web-panel/assets/{Codegen-3p5QCkFK.js → Codegen-DugeL4pj.js} +1 -1
  19. package/src/assets/web-panel/assets/{Col-BPLlhn52.js → Col-DPuJsvKg.js} +1 -1
  20. package/src/assets/web-panel/assets/{Community-C-3dBNOM.js → Community-CZqNjNNp.js} +1 -1
  21. package/src/assets/web-panel/assets/{Compact-BUcy-F_b.js → Compact-eeyIPEAb.js} +1 -1
  22. package/src/assets/web-panel/assets/{Compliance-CI8NxT8m.js → Compliance-MGzTw87k.js} +1 -1
  23. package/src/assets/web-panel/assets/{Cowork-DaDEBS-Q.js → Cowork-D3goVIA5.js} +2 -2
  24. package/src/assets/web-panel/assets/{Cron-BSv9HXu5.js → Cron-9HA8hLLG.js} +2 -2
  25. package/src/assets/web-panel/assets/{Crosschain-yuiKlJmv.js → Crosschain-DCSOX3l6.js} +1 -1
  26. package/src/assets/web-panel/assets/{DID-D6LfldB0.js → DID-ji3lN5Bc.js} +2 -2
  27. package/src/assets/web-panel/assets/{Dashboard-CBhLqG61.js → Dashboard-DlZvF1E5.js} +2 -2
  28. package/src/assets/web-panel/assets/{Dropdown-BG8pIl3O.js → Dropdown-2FyZcow9.js} +1 -1
  29. package/src/assets/web-panel/assets/{EmailListRenderer-CY92VIE6.js → EmailListRenderer-qH2bSpSY.js} +1 -1
  30. package/src/assets/web-panel/assets/{FamilyGuardDashboard-1Q_ehauM.js → FamilyGuardDashboard-Bfx47wZj.js} +1 -1
  31. package/src/assets/web-panel/assets/{Federation-D3XirJIU.js → Federation-DhGcZbIv.js} +1 -1
  32. package/src/assets/web-panel/assets/{FormItemContext-DfI9UuGZ.js → FormItemContext-BMgi9_YQ.js} +1 -1
  33. package/src/assets/web-panel/assets/{GenericCardRenderer-IeCZk2m7.js → GenericCardRenderer-DugMac-4.js} +1 -1
  34. package/src/assets/web-panel/assets/{Git-DzK4IJAZ.js → Git-D943BpH-.js} +2 -2
  35. package/src/assets/web-panel/assets/{Governance-BHf5KfmQ.js → Governance-DZ66a8Aa.js} +1 -1
  36. package/src/assets/web-panel/assets/{Inference-BmaxSALS.js → Inference-B00Mp2tN.js} +1 -1
  37. package/src/assets/web-panel/assets/{KnowledgeGraph-BgePFLA9.js → KnowledgeGraph-BdwXXO2Q.js} +1 -1
  38. package/src/assets/web-panel/assets/{Logs-nqgxpOc4.js → Logs-_MVXyYWc.js} +2 -2
  39. package/src/assets/web-panel/assets/MarkdownRenderer-hOTeNyi7.js +1 -0
  40. package/src/assets/web-panel/assets/{Marketplace-Bu8to-86.js → Marketplace-CxeHRsnO.js} +1 -1
  41. package/src/assets/web-panel/assets/{McpTools-BFWTzEk0.js → McpTools-BOieTxZ4.js} +3 -3
  42. package/src/assets/web-panel/assets/{Memory-B026G2GA.js → Memory-BQD26CM3.js} +2 -2
  43. package/src/assets/web-panel/assets/{MobileBridge-CM2Eeg6I.js → MobileBridge-CPJ8ZlvR.js} +1 -1
  44. package/src/assets/web-panel/assets/{MobileProjects-B79Ob3hy.js → MobileProjects-D7qRVu0y.js} +1 -1
  45. package/src/assets/web-panel/assets/{Mtc-CxevSZuV.js → Mtc-BOyndGuk.js} +2 -2
  46. package/src/assets/web-panel/assets/{MtcAudit-X396cPEX.js → MtcAudit-CXQ_8ZoR.js} +4 -4
  47. package/src/assets/web-panel/assets/{Multisig-HWIB_aZ1.js → Multisig-32Oh9KbH.js} +3 -3
  48. package/src/assets/web-panel/assets/{NLProgramming-gnYD1Xwy.js → NLProgramming-CFAd00CX.js} +1 -1
  49. package/src/assets/web-panel/assets/{Notes-Dn2Gf_J1.js → Notes-BBCY_qJA.js} +3 -3
  50. package/src/assets/web-panel/assets/{NotificationSettings-BRKBQ5rq.js → NotificationSettings-uaQ0PdmW.js} +1 -1
  51. package/src/assets/web-panel/assets/{OrderTableRenderer-Dy___Cgo.js → OrderTableRenderer-kpBxJ-SG.js} +1 -1
  52. package/src/assets/web-panel/assets/{Organization-cqfccxnt.js → Organization-CmFn7Oeo.js} +4 -4
  53. package/src/assets/web-panel/assets/{Overflow-CSX4FHN3.js → Overflow-R_avat3a.js} +1 -1
  54. package/src/assets/web-panel/assets/{P2P-Bwa4aghp.js → P2P-BIhLFmkY.js} +2 -2
  55. package/src/assets/web-panel/assets/{PdhVaultBrowser-Dhszyjig.js → PdhVaultBrowser-DTJjk-_i.js} +3 -3
  56. package/src/assets/web-panel/assets/{Permissions-CXzTyk6e.js → Permissions-CkzYv8Yb.js} +4 -4
  57. package/src/assets/web-panel/assets/{PersonalDataHub-CFCAAJbb.js → PersonalDataHub--0QvN2Nz.js} +4 -4
  58. package/src/assets/web-panel/assets/{Pipeline-BPJbx6xt.js → Pipeline-Bfw5gQCH.js} +1 -1
  59. package/src/assets/web-panel/assets/{Privacy-BbiXvEHz.js → Privacy-DicjKfax.js} +1 -1
  60. package/src/assets/web-panel/assets/{ProjectInit-B-s7-wSD.js → ProjectInit-DUl_ykBp.js} +2 -2
  61. package/src/assets/web-panel/assets/{ProjectSettings-Dyug206y.js → ProjectSettings-CPYDvN8a.js} +2 -2
  62. package/src/assets/web-panel/assets/{Projects-BtAI5Fwo.js → Projects-DnZ9_fAr.js} +1 -1
  63. package/src/assets/web-panel/assets/{Providers-JpIPmz6N.js → Providers-BX1jP31w.js} +1 -1
  64. package/src/assets/web-panel/assets/{QrScannerModal-CZdoN64A.js → QrScannerModal-COab5qUl.js} +1 -1
  65. package/src/assets/web-panel/assets/{QuickAsk-BwvnoRIT.js → QuickAsk-CdKQ_JZ0.js} +1 -1
  66. package/src/assets/web-panel/assets/{Recommend-ASMlMQrD.js → Recommend-BPFHg8pK.js} +1 -1
  67. package/src/assets/web-panel/assets/{RemoteSession-BiJzKFKi.js → RemoteSession-CqrfTJvO.js} +3 -3
  68. package/src/assets/web-panel/assets/{Reputation-C80TWLIO.js → Reputation-DM-l8Pb3.js} +1 -1
  69. package/src/assets/web-panel/assets/{Row-C1VNmjmX.js → Row-CKGBTeCw.js} +1 -1
  70. package/src/assets/web-panel/assets/{RssFeed-T2MyGUlG.js → RssFeed-Wb0YHIkc.js} +3 -3
  71. package/src/assets/web-panel/assets/{Search-DXM6O83L.js → Search-DiBjxKv-.js} +1 -1
  72. package/src/assets/web-panel/assets/{Security-nv69kU7W.js → Security-BAVEmbWP.js} +4 -4
  73. package/src/assets/web-panel/assets/{Services-AyHWe7Qj.js → Services-A_a3TIRn.js} +2 -2
  74. package/src/assets/web-panel/assets/{Skeleton-D6PWLxFI.js → Skeleton-CloHJ-I7.js} +1 -1
  75. package/src/assets/web-panel/assets/{Skills-BqVeOmNQ.js → Skills-CkvV5hKa.js} +1 -1
  76. package/src/assets/web-panel/assets/{Sla-BegIPl9M.js → Sla-BYozxxsV.js} +1 -1
  77. package/src/assets/web-panel/assets/{SpeechSettings-CKJn3xk-.js → SpeechSettings-CWianiZF.js} +1 -1
  78. package/src/assets/web-panel/assets/{SyncSettings-Th4cnAMl.js → SyncSettings-BR4G75do.js} +2 -2
  79. package/src/assets/web-panel/assets/{Tasks-BuKfBroh.js → Tasks-D6gyUVrM.js} +1 -1
  80. package/src/assets/web-panel/assets/{Templates-CMuWN8Ac.js → Templates-DbfYIRzT.js} +1 -1
  81. package/src/assets/web-panel/assets/{Tenant-C4je8E8Q.js → Tenant-BHutvukT.js} +1 -1
  82. package/src/assets/web-panel/assets/{Terminal-agJESOcO.js → Terminal-CYEiy2wJ.js} +2 -2
  83. package/src/assets/web-panel/assets/{TimelineRenderer-D2qDuVZ_.js → TimelineRenderer-D9s1AxfE.js} +1 -1
  84. package/src/assets/web-panel/assets/{Tokens-Cvmn99rH.js → Tokens-ij9vxnoy.js} +1 -1
  85. package/src/assets/web-panel/assets/{Trigger-D_QYIHH8.js → Trigger-Dq_DCVeQ.js} +1 -1
  86. package/src/assets/web-panel/assets/{Trust-BmzvQLnX.js → Trust-Bs6wdfoH.js} +1 -1
  87. package/src/assets/web-panel/assets/{UkeySign-D_LopHwH.js → UkeySign-CLazyr5t.js} +1 -1
  88. package/src/assets/web-panel/assets/{VideoEditing-DoWl3PhQ.js → VideoEditing-viWotIHA.js} +1 -1
  89. package/src/assets/web-panel/assets/{Wallet-5NYcAkxe.js → Wallet-DlZ-A78d.js} +4 -4
  90. package/src/assets/web-panel/assets/{WebAuthn-B-_Q3ewp.js → WebAuthn-DSmOND3Y.js} +3 -3
  91. package/src/assets/web-panel/assets/{WorkflowEditor-CHET-gi2.js → WorkflowEditor-BempLOJi.js} +1 -1
  92. package/src/assets/web-panel/assets/{chat-C6nvb-n6.js → chat-CyJzf4JI.js} +1 -1
  93. package/src/assets/web-panel/assets/{colors-CTDE9LTX.js → colors-C62q7WrL.js} +1 -1
  94. package/src/assets/web-panel/assets/{compact-item-KnemdF8D.js → compact-item-7dYM1KW3.js} +1 -1
  95. package/src/assets/web-panel/assets/{createContext-DUJR3Uek.js → createContext-CYTy7z2Q.js} +1 -1
  96. package/src/assets/web-panel/assets/devWarning-BdTg_AMF.js +1 -0
  97. package/src/assets/web-panel/assets/{hasIn-CFNTaby8.js → hasIn-DHoclUqm.js} +1 -1
  98. package/src/assets/web-panel/assets/{index-65HO56Bv.js → index-2C8Xx2UO.js} +1 -1
  99. package/src/assets/web-panel/assets/{index-ox6mIwE2.js → index-3pI7AfmD.js} +1 -1
  100. package/src/assets/web-panel/assets/{index-JGTiDeOW.js → index-4gWv-Ubg.js} +1 -1
  101. package/src/assets/web-panel/assets/{index-rVDD7AAR.js → index-94ktimZG.js} +1 -1
  102. package/src/assets/web-panel/assets/{index-OmuhFYKE.js → index-9uR7rc9a.js} +1 -1
  103. package/src/assets/web-panel/assets/index-B6WvFV4N.js +1 -0
  104. package/src/assets/web-panel/assets/index-BKgfptzA.js +1 -0
  105. package/src/assets/web-panel/assets/{index-CquKnw5r.js → index-BMRmxFU_.js} +1 -1
  106. package/src/assets/web-panel/assets/{index-DzReoLyh.js → index-BMxvWauP.js} +1 -1
  107. package/src/assets/web-panel/assets/{index-DP-PbO11.js → index-BghdJ87W.js} +1 -1
  108. package/src/assets/web-panel/assets/{index-CSD9_I2_.js → index-Bzz0aJ86.js} +1 -1
  109. package/src/assets/web-panel/assets/{index-DF1Y0Vuw.js → index-C2efftJb.js} +1 -1
  110. package/src/assets/web-panel/assets/{index-B8RtbSkV.js → index-C5YWYlW9.js} +1 -1
  111. package/src/assets/web-panel/assets/{index-CHfUdnJH.js → index-CVTnruDt.js} +1 -1
  112. package/src/assets/web-panel/assets/{index-BwZM1rod.js → index-CW86F2Zw.js} +1 -1
  113. package/src/assets/web-panel/assets/{index-CyEtHvEE.js → index-CZRBvN6i.js} +1 -1
  114. package/src/assets/web-panel/assets/{index-Ceu92a8D.js → index-CjeViaU-.js} +1 -1
  115. package/src/assets/web-panel/assets/{index-DJyPeBBk.js → index-CnEZ4ZHj.js} +3 -3
  116. package/src/assets/web-panel/assets/{index-BdiC4LOs.js → index-D6BC4mmz.js} +1 -1
  117. package/src/assets/web-panel/assets/{index-k6uorYmf.js → index-DA-_807C.js} +1 -1
  118. package/src/assets/web-panel/assets/{index-DqPpJkte.js → index-DAYanuSk.js} +1 -1
  119. package/src/assets/web-panel/assets/{index-NtAcnJYW.js → index-DHgSRimK.js} +1 -1
  120. package/src/assets/web-panel/assets/{index-Wlc7o_C8.js → index-DJzZaPlb.js} +1 -1
  121. package/src/assets/web-panel/assets/{index-CKvBF3Ov.js → index-DK84lAS0.js} +1 -1
  122. package/src/assets/web-panel/assets/{index-CcF0D7UZ.js → index-DKdv8cju.js} +1 -1
  123. package/src/assets/web-panel/assets/{index-CnLpuTAU.js → index-DNLD3nZY.js} +1 -1
  124. package/src/assets/web-panel/assets/{index-DZgCRMxk.js → index-DOFAwpUK.js} +1 -1
  125. package/src/assets/web-panel/assets/{index-v-mtxmWH.js → index-DYKwGrAn.js} +1 -1
  126. package/src/assets/web-panel/assets/{index-Cc7dbl_p.js → index-DghnbMlY.js} +1 -1
  127. package/src/assets/web-panel/assets/{index-BuizJo2E.js → index-DhJjifZe.js} +1 -1
  128. package/src/assets/web-panel/assets/{index-NUR0If7O.js → index-DkczsbiP.js} +1 -1
  129. package/src/assets/web-panel/assets/{index-u0h6QqVV.js → index-DvEtHpLc.js} +1 -1
  130. package/src/assets/web-panel/assets/{index-bxTPfdri.js → index-Dyq9tK5u.js} +1 -1
  131. package/src/assets/web-panel/assets/{index-DfJzS3Qa.js → index-LK1MZoBj.js} +1 -1
  132. package/src/assets/web-panel/assets/{index-DF-fcTvQ.js → index-NuNCstRO.js} +1 -1
  133. package/src/assets/web-panel/assets/{index-BXWg1crv.js → index-QXtrdrub.js} +1 -1
  134. package/src/assets/web-panel/assets/{index-BTetEUWd.js → index-XrsAHHQN.js} +1 -1
  135. package/src/assets/web-panel/assets/{index-BHqSqnW7.js → index-ZXYp76IB.js} +1 -1
  136. package/src/assets/web-panel/assets/{index-C96N9xeL.js → index-lHfNxiB5.js} +1 -1
  137. package/src/assets/web-panel/assets/{initDefaultProps-qEt8dI-t.js → initDefaultProps-CwCl5sFQ.js} +1 -1
  138. package/src/assets/web-panel/assets/{motion-DetKPWy-.js → motion-BFJFy70N.js} +1 -1
  139. package/src/assets/web-panel/assets/{move-BeNYeDV2.js → move-ByrtVGq8.js} +1 -1
  140. package/src/assets/web-panel/assets/{mtc-parser-C0q0MK_T.js → mtc-parser-BFiH1mT3.js} +1 -1
  141. package/src/assets/web-panel/assets/{omit-DLKkrKpE.js → omit-bdvgpivj.js} +1 -1
  142. package/src/assets/web-panel/assets/{pickAttrs-Bw1tWsY8.js → pickAttrs-BlfuuE3s.js} +1 -1
  143. package/src/assets/web-panel/assets/{placementArrow-DeesBLbd.js → placementArrow-t2SC3DMy.js} +1 -1
  144. package/src/assets/web-panel/assets/{responsiveObserve-bqLhxHhn.js → responsiveObserve-CoEXv2Li.js} +1 -1
  145. package/src/assets/web-panel/assets/{slide-DGCXRoQm.js → slide-BfXCf0Fu.js} +1 -1
  146. package/src/assets/web-panel/assets/{statusUtils-H-re3Egl.js → statusUtils-DNsdyOuS.js} +1 -1
  147. package/src/assets/web-panel/assets/{styleChecker-BXg4qGX_.js → styleChecker-9aHukmoG.js} +1 -1
  148. package/src/assets/web-panel/assets/{useFlexGapSupport-CKLb2KA6.js → useFlexGapSupport-dTkPxzHN.js} +1 -1
  149. package/src/assets/web-panel/assets/{useFs-CTAhHeyw.js → useFs-DINwfItP.js} +1 -1
  150. package/src/assets/web-panel/assets/{usePersonalDataHub-BQ4pDh5g.js → usePersonalDataHub-Bj_RriBV.js} +1 -1
  151. package/src/assets/web-panel/assets/{vnode-jrSK6j4j.js → vnode-BzRAZrTc.js} +1 -1
  152. package/src/assets/web-panel/assets/{zoom-fOQE24pw.js → zoom-CamPjkeK.js} +1 -1
  153. package/src/assets/web-panel/index.html +1 -1
  154. package/src/command-help-index.json +4 -4
  155. package/src/command-manifest.json +1 -1
  156. package/src/commands/agent.js +1 -1
  157. package/src/commands/graph.js +100 -0
  158. package/src/commands/mcp.js +49 -21
  159. package/src/commands/orchestrate.js +85 -18
  160. package/src/commands/serve.js +39 -0
  161. package/src/commands/team.js +2 -0
  162. package/src/data/changelog.json +26 -0
  163. package/src/generated/cc-agent-protocol.schema.json +1964 -0
  164. package/src/lib/agent-sandbox.js +4 -7
  165. package/src/lib/app-server/bounded-queue.js +87 -0
  166. package/src/lib/app-server/cli-agent-kernel-adapter.js +309 -0
  167. package/src/lib/app-server/protocol.js +125 -0
  168. package/src/lib/app-server/rollout-store.js +603 -0
  169. package/src/lib/app-server/server.js +922 -0
  170. package/src/lib/app-server/sqlite-rollout-store.js +315 -0
  171. package/src/lib/app-server/stdio-transport.js +118 -0
  172. package/src/lib/codex-app-server-adapter.js +249 -0
  173. package/src/lib/graph-kernel/adapters.js +238 -0
  174. package/src/lib/graph-kernel/compiler.js +911 -0
  175. package/src/lib/graph-kernel/eval.js +207 -0
  176. package/src/lib/graph-kernel/event-store.js +101 -0
  177. package/src/lib/graph-kernel/index.js +7 -0
  178. package/src/lib/graph-kernel/runtime.js +2660 -0
  179. package/src/lib/graph-kernel/trace-reducer.js +315 -0
  180. package/src/lib/graph-kernel/trigger-adapter.js +183 -0
  181. package/src/lib/orchestrator.js +2 -1
  182. package/src/lib/record-replay/index.js +1 -0
  183. package/src/lib/record-replay/skill-recorder.js +386 -0
  184. package/src/lib/webhook-security.js +159 -0
  185. package/src/repl/agent-repl.js +5 -4
  186. package/src/repl/prompt-interactions.js +11 -1
  187. package/src/assets/web-panel/assets/MarkdownRenderer-xkX6izBt.js +0 -1
  188. package/src/assets/web-panel/assets/devWarning-1DqLH1KX.js +0 -1
  189. package/src/assets/web-panel/assets/index-BhJtcPWo.js +0 -1
  190. package/src/assets/web-panel/assets/index-Cq8MWPDT.js +0 -1
@@ -259,13 +259,10 @@ export function normalizeAgentSandbox(value, options = {}) {
259
259
  */
260
260
  export function normalizeAgentSandboxMode(mode, value, options = {}) {
261
261
  if (mode == null || mode === "") {
262
- // Public agent execution defaults to a real, fail-closed workspace
263
- // sandbox. Bare-host execution remains available only through the
264
- // explicit `off` mode below, where managed policy can prohibit it.
265
- return normalizeAgentSandboxMode("workspace-write", value || true, {
266
- ...options,
267
- network: false,
268
- });
262
+ // Keep the container sandbox opt-in unless CLI/settings policy explicitly
263
+ // enables it. The process broker still applies its platform boundary, but
264
+ // starting a normal agent must not require Docker to be installed/running.
265
+ return normalizeAgentSandbox(value, options);
269
266
  }
270
267
  if (!AGENT_SANDBOX_MODES.includes(mode)) {
271
268
  const error = new Error(
@@ -0,0 +1,87 @@
1
+ export class QueueOverloadedError extends Error {
2
+ constructor(message, { retryAfterMs = 100, limit, queued } = {}) {
3
+ super(message);
4
+ this.name = "QueueOverloadedError";
5
+ this.code = "CC_APP_SERVER_OVERLOADED";
6
+ this.retryAfterMs = retryAfterMs;
7
+ this.limit = limit;
8
+ this.queued = queued;
9
+ }
10
+ }
11
+
12
+ export class BoundedAsyncQueue {
13
+ constructor({
14
+ maxItems = 256,
15
+ maxBytes = 4 * 1024 * 1024,
16
+ sizeOf = null,
17
+ } = {}) {
18
+ this.maxItems = Math.max(1, Number(maxItems) || 256);
19
+ this.maxBytes = Math.max(1, Number(maxBytes) || 4 * 1024 * 1024);
20
+ this.sizeOf =
21
+ sizeOf || ((value) => Buffer.byteLength(String(value), "utf8"));
22
+ this.items = [];
23
+ this.bytes = 0;
24
+ this.closed = false;
25
+ this.waiters = [];
26
+ }
27
+
28
+ push(value) {
29
+ if (this.closed) throw new Error("bounded queue is closed");
30
+ const bytes = Math.max(0, Number(this.sizeOf(value)) || 0);
31
+ if (
32
+ this.items.length >= this.maxItems ||
33
+ this.bytes + bytes > this.maxBytes
34
+ ) {
35
+ throw new QueueOverloadedError("App Server queue capacity exceeded", {
36
+ limit: this.maxItems,
37
+ queued: this.items.length,
38
+ });
39
+ }
40
+ const waiter = this.waiters.shift();
41
+ if (waiter) {
42
+ waiter.resolve({ value, done: false });
43
+ return;
44
+ }
45
+ this.items.push({ value, bytes });
46
+ this.bytes += bytes;
47
+ }
48
+
49
+ shift() {
50
+ const entry = this.items.shift();
51
+ if (!entry) return undefined;
52
+ this.bytes -= entry.bytes;
53
+ return entry.value;
54
+ }
55
+
56
+ async next() {
57
+ const value = this.shift();
58
+ if (value !== undefined) return { value, done: false };
59
+ if (this.closed) return { value: undefined, done: true };
60
+ return new Promise((resolve, reject) =>
61
+ this.waiters.push({ resolve, reject }),
62
+ );
63
+ }
64
+
65
+ close(error = null) {
66
+ if (this.closed) return;
67
+ this.closed = true;
68
+ for (const waiter of this.waiters.splice(0)) {
69
+ if (error) waiter.reject(error);
70
+ else waiter.resolve({ value: undefined, done: true });
71
+ }
72
+ }
73
+
74
+ snapshot() {
75
+ return Object.freeze({
76
+ queuedItems: this.items.length,
77
+ queuedBytes: this.bytes,
78
+ maxItems: this.maxItems,
79
+ maxBytes: this.maxBytes,
80
+ closed: this.closed,
81
+ });
82
+ }
83
+
84
+ [Symbol.asyncIterator]() {
85
+ return this;
86
+ }
87
+ }
@@ -0,0 +1,309 @@
1
+ import { PassThrough } from "node:stream";
2
+ import { randomUUID } from "node:crypto";
3
+ import {
4
+ assertSandboxAvailable,
5
+ normalizeAgentSandboxMode,
6
+ } from "../agent-sandbox.js";
7
+
8
+ const PERMISSION_MODES = new Set(["default", "manual", "dontAsk", "plan"]);
9
+
10
+ function adapterError(code, message) {
11
+ const error = new Error(message);
12
+ error.name = "CliAgentKernelAdapterError";
13
+ error.code = code;
14
+ return error;
15
+ }
16
+
17
+ function writeLine(input, value) {
18
+ if (input.destroyed || input.writableEnded) {
19
+ throw adapterError(
20
+ "CC_APP_SERVER_AGENT_SESSION_CLOSED",
21
+ "Agent Kernel input stream is closed",
22
+ );
23
+ }
24
+ input.write(`${JSON.stringify(value)}\n`);
25
+ }
26
+
27
+ function approvalBoolean(decision) {
28
+ return ["acceptOnce", "acceptForTurn", "acceptForSession"].includes(
29
+ decision?.kind,
30
+ );
31
+ }
32
+
33
+ function outputCollector(onEvent, onStderr) {
34
+ let stdout = "";
35
+ let stderr = "";
36
+ return {
37
+ writeOut(chunk) {
38
+ stdout += String(chunk);
39
+ for (;;) {
40
+ const index = stdout.indexOf("\n");
41
+ if (index < 0) break;
42
+ const line = stdout.slice(0, index).trim();
43
+ stdout = stdout.slice(index + 1);
44
+ if (!line) continue;
45
+ let event;
46
+ try {
47
+ event = JSON.parse(line);
48
+ } catch {
49
+ event = { type: "raw", subtype: "invalid_json", text: line };
50
+ }
51
+ onEvent(event);
52
+ }
53
+ return true;
54
+ },
55
+ writeErr(chunk) {
56
+ stderr += String(chunk);
57
+ for (;;) {
58
+ const index = stderr.indexOf("\n");
59
+ if (index < 0) break;
60
+ const line = stderr.slice(0, index).trim();
61
+ stderr = stderr.slice(index + 1);
62
+ if (line) onStderr(line);
63
+ }
64
+ return true;
65
+ },
66
+ flush() {
67
+ if (stdout.trim()) {
68
+ try {
69
+ onEvent(JSON.parse(stdout.trim()));
70
+ } catch {
71
+ onEvent({
72
+ type: "raw",
73
+ subtype: "invalid_json",
74
+ text: stdout.trim(),
75
+ });
76
+ }
77
+ }
78
+ if (stderr.trim()) onStderr(stderr.trim());
79
+ stdout = "";
80
+ stderr = "";
81
+ },
82
+ };
83
+ }
84
+
85
+ export class CliAgentKernelAdapter {
86
+ constructor({
87
+ cwd = process.cwd(),
88
+ sandboxMode = "workspace-write",
89
+ sandboxEngine = null,
90
+ allowedPermissionModes = PERMISSION_MODES,
91
+ sessionOptions = {},
92
+ dependencies = {},
93
+ } = {}) {
94
+ this.cwd = cwd;
95
+ this.sandboxMode = sandboxMode;
96
+ this.sandboxEngine = sandboxEngine;
97
+ this.allowedPermissionModes = new Set(allowedPermissionModes);
98
+ this.sessionOptions = { ...sessionOptions };
99
+ this.dependencies = dependencies;
100
+ this.sessions = new Map();
101
+ }
102
+
103
+ async _createSession(threadId, turnOptions = {}) {
104
+ const { runAgentHeadlessStream } =
105
+ await import("../../runtime/headless-stream.js");
106
+ const permissionMode = String(
107
+ turnOptions.permissionMode ||
108
+ this.sessionOptions.permissionMode ||
109
+ "default",
110
+ );
111
+ if (!this.allowedPermissionModes.has(permissionMode)) {
112
+ throw adapterError(
113
+ "CC_APP_SERVER_PERMISSION_MODE_DENIED",
114
+ `permission mode is not allowed by the App Server: ${permissionMode}`,
115
+ );
116
+ }
117
+ const sandbox = normalizeAgentSandboxMode(
118
+ this.sandboxMode,
119
+ this.sandboxEngine || true,
120
+ {
121
+ cwd: this.cwd,
122
+ network: false,
123
+ settings: {
124
+ enabled: true,
125
+ failIfUnavailable: true,
126
+ allowUnsandboxedCommands: false,
127
+ },
128
+ },
129
+ );
130
+ assertSandboxAvailable(sandbox);
131
+
132
+ const input = new PassThrough();
133
+ const session = {
134
+ threadId,
135
+ input,
136
+ current: null,
137
+ eventChain: Promise.resolve(),
138
+ closed: false,
139
+ failure: null,
140
+ runPromise: null,
141
+ collector: null,
142
+ };
143
+ const queueEvent = (event) => {
144
+ const current = session.current;
145
+ session.eventChain = session.eventChain.then(async () => {
146
+ if (!current) return;
147
+ await current.emit(event);
148
+ if (event.type === "approval_request") {
149
+ let decision = {
150
+ kind: "decline",
151
+ reason: "approval host unavailable",
152
+ };
153
+ try {
154
+ decision = await current.requestApproval(event);
155
+ } catch (error) {
156
+ decision = {
157
+ kind: "decline",
158
+ reason: String(error?.message || error).slice(0, 2048),
159
+ };
160
+ }
161
+ writeLine(input, {
162
+ type: "approval",
163
+ id: event.id,
164
+ approve: approvalBoolean(decision),
165
+ binding: event.binding,
166
+ });
167
+ }
168
+ if (event.type === "result") {
169
+ session.current = null;
170
+ current.resolve(event);
171
+ }
172
+ });
173
+ session.eventChain.catch((error) => {
174
+ if (session.current === current) session.current = null;
175
+ current?.reject(error);
176
+ });
177
+ };
178
+ const collector = outputCollector(queueEvent, (line) => {
179
+ const current = session.current;
180
+ if (!current) return;
181
+ queueEvent({ type: "raw", subtype: "stderr", text: line });
182
+ });
183
+ session.collector = collector;
184
+ session.runPromise = runAgentHeadlessStream(
185
+ {
186
+ ...this.sessionOptions,
187
+ model: turnOptions.model || this.sessionOptions.model,
188
+ provider: turnOptions.provider || this.sessionOptions.provider,
189
+ baseUrl: this.sessionOptions.baseUrl,
190
+ apiKey: this.sessionOptions.apiKey,
191
+ sessionId: threadId,
192
+ cwd: this.cwd,
193
+ permissionMode,
194
+ sandbox,
195
+ interactiveApprovals: true,
196
+ includePartialMessages: true,
197
+ ephemeral: false,
198
+ },
199
+ {
200
+ ...this.dependencies,
201
+ input,
202
+ writeOut: collector.writeOut,
203
+ writeErr: collector.writeErr,
204
+ },
205
+ )
206
+ .then(async (outcome) => {
207
+ collector.flush();
208
+ await session.eventChain;
209
+ session.closed = true;
210
+ if (session.current) {
211
+ session.current.reject(
212
+ adapterError(
213
+ "CC_APP_SERVER_AGENT_SESSION_CLOSED",
214
+ "Agent Kernel session closed before the turn completed",
215
+ ),
216
+ );
217
+ session.current = null;
218
+ }
219
+ return outcome;
220
+ })
221
+ .catch((error) => {
222
+ session.failure = error;
223
+ session.closed = true;
224
+ if (session.current) {
225
+ session.current.reject(error);
226
+ session.current = null;
227
+ }
228
+ throw error;
229
+ });
230
+ session.runPromise.catch(() => {});
231
+ this.sessions.set(threadId, session);
232
+ return session;
233
+ }
234
+
235
+ async _session(threadId, options) {
236
+ const existing = this.sessions.get(threadId);
237
+ if (existing && !existing.closed) return existing;
238
+ if (existing?.failure) throw existing.failure;
239
+ return this._createSession(threadId, options);
240
+ }
241
+
242
+ async startTurn({
243
+ threadId,
244
+ turnId,
245
+ input,
246
+ options = {},
247
+ emit,
248
+ requestApproval,
249
+ }) {
250
+ const session = await this._session(threadId, options);
251
+ if (session.current) {
252
+ throw adapterError(
253
+ "CC_APP_SERVER_TURN_ACTIVE",
254
+ `thread already has an active turn: ${threadId}`,
255
+ );
256
+ }
257
+ const prompt = String(input || "").trim();
258
+ if (!prompt) {
259
+ throw adapterError(
260
+ "CC_APP_SERVER_INVALID_INPUT",
261
+ "turn input must contain non-empty text",
262
+ );
263
+ }
264
+ const terminal = new Promise((resolve, reject) => {
265
+ session.current = {
266
+ turnId,
267
+ emit,
268
+ requestApproval,
269
+ resolve,
270
+ reject,
271
+ };
272
+ });
273
+ writeLine(session.input, {
274
+ type: "user",
275
+ text: prompt,
276
+ images: Array.isArray(options.images) ? options.images : undefined,
277
+ });
278
+ return terminal;
279
+ }
280
+
281
+ async interruptTurn(threadId, turnId) {
282
+ const session = this.sessions.get(threadId);
283
+ if (!session?.current || session.current.turnId !== turnId) return false;
284
+ writeLine(session.input, { type: "interrupt" });
285
+ return true;
286
+ }
287
+
288
+ async forkThread(sourceThreadId, requestId = randomUUID()) {
289
+ const { forkSession, sessionExists } =
290
+ await import("../../harness/jsonl-session-store.js");
291
+ if (!sessionExists(sourceThreadId)) return null;
292
+ return forkSession(sourceThreadId, { requestId });
293
+ }
294
+
295
+ async closeThread(threadId) {
296
+ const session = this.sessions.get(threadId);
297
+ if (!session) return false;
298
+ session.input.end();
299
+ await session.runPromise.catch(() => {});
300
+ this.sessions.delete(threadId);
301
+ return true;
302
+ }
303
+
304
+ async close() {
305
+ await Promise.all(
306
+ [...this.sessions.keys()].map((threadId) => this.closeThread(threadId)),
307
+ );
308
+ }
309
+ }
@@ -0,0 +1,125 @@
1
+ import { readFileSync } from "node:fs";
2
+ import { validate } from "../json-schema-validate.js";
3
+
4
+ const schema = JSON.parse(
5
+ readFileSync(
6
+ new URL("../../generated/cc-agent-protocol.schema.json", import.meta.url),
7
+ "utf8",
8
+ ),
9
+ );
10
+
11
+ export const APP_SERVER_PROTOCOL_VERSION = schema["x-cc-protocol"].version;
12
+ export const APP_SERVER_MIN_PROTOCOL_VERSION =
13
+ schema["x-cc-protocol"].minimumCompatibleVersion;
14
+ export const APP_SERVER_FEATURES = Object.freeze([
15
+ ...schema["x-cc-protocol"].features,
16
+ ]);
17
+ export const APP_SERVER_SCHEMA = schema;
18
+
19
+ export const JSON_RPC_ERROR = Object.freeze({
20
+ PARSE_ERROR: -32700,
21
+ INVALID_REQUEST: -32600,
22
+ METHOD_NOT_FOUND: -32601,
23
+ INVALID_PARAMS: -32602,
24
+ INTERNAL_ERROR: -32603,
25
+ OVERLOADED: -32001,
26
+ NOT_INITIALIZED: -32002,
27
+ NOT_FOUND: -32004,
28
+ CONFLICT: -32009,
29
+ INTERRUPTED: -32010,
30
+ });
31
+
32
+ export class JsonRpcError extends Error {
33
+ constructor(code, message, data = null) {
34
+ super(message);
35
+ this.name = "JsonRpcError";
36
+ this.code = code;
37
+ this.data = data;
38
+ }
39
+ }
40
+
41
+ export function validateAppServerMessage(value) {
42
+ const result = validate(value, APP_SERVER_SCHEMA);
43
+ return Object.freeze({
44
+ ok: result.valid,
45
+ errors: Object.freeze(
46
+ result.errors.map((error) =>
47
+ Object.freeze({
48
+ path: error.instancePath || error.schemaPath || "#",
49
+ message: error.message || error.code || "invalid message",
50
+ }),
51
+ ),
52
+ ),
53
+ });
54
+ }
55
+
56
+ export function rpcResult(id, result) {
57
+ return { jsonrpc: "2.0", id, result: result ?? null };
58
+ }
59
+
60
+ export function rpcError(id, error) {
61
+ const code = Number.isInteger(error?.code)
62
+ ? error.code
63
+ : JSON_RPC_ERROR.INTERNAL_ERROR;
64
+ const output = {
65
+ jsonrpc: "2.0",
66
+ id: id ?? null,
67
+ error: {
68
+ code,
69
+ message:
70
+ code === JSON_RPC_ERROR.INTERNAL_ERROR
71
+ ? "Internal App Server error"
72
+ : String(error?.message || "Request failed").slice(0, 4096),
73
+ },
74
+ };
75
+ if (error?.data != null) output.error.data = error.data;
76
+ return output;
77
+ }
78
+
79
+ export function rpcNotification(method, params) {
80
+ return { jsonrpc: "2.0", method, params: params ?? null };
81
+ }
82
+
83
+ export function negotiateProtocol(params = {}) {
84
+ const clientMax = Number(params.protocolVersion);
85
+ const clientMin = Number(params.minimumProtocolVersion);
86
+ if (
87
+ !Number.isSafeInteger(clientMax) ||
88
+ !Number.isSafeInteger(clientMin) ||
89
+ clientMin > clientMax
90
+ ) {
91
+ throw new JsonRpcError(
92
+ JSON_RPC_ERROR.INVALID_PARAMS,
93
+ "initialize requires a valid protocol version range",
94
+ );
95
+ }
96
+ const minimum = Math.max(clientMin, APP_SERVER_MIN_PROTOCOL_VERSION);
97
+ const maximum = Math.min(clientMax, APP_SERVER_PROTOCOL_VERSION);
98
+ if (minimum > maximum) {
99
+ throw new JsonRpcError(
100
+ JSON_RPC_ERROR.INVALID_PARAMS,
101
+ "client and server protocol ranges do not overlap",
102
+ {
103
+ client: { minimum: clientMin, maximum: clientMax },
104
+ server: {
105
+ minimum: APP_SERVER_MIN_PROTOCOL_VERSION,
106
+ maximum: APP_SERVER_PROTOCOL_VERSION,
107
+ },
108
+ },
109
+ );
110
+ }
111
+ const requested = Array.isArray(params.features)
112
+ ? new Set(params.features.map(String))
113
+ : null;
114
+ const features = requested
115
+ ? APP_SERVER_FEATURES.filter((feature) => requested.has(feature))
116
+ : [...APP_SERVER_FEATURES];
117
+ return Object.freeze({
118
+ protocolVersion: maximum,
119
+ minimumProtocolVersion: APP_SERVER_MIN_PROTOCOL_VERSION,
120
+ features: Object.freeze(features),
121
+ downgraded:
122
+ maximum !== APP_SERVER_PROTOCOL_VERSION ||
123
+ features.length !== APP_SERVER_FEATURES.length,
124
+ });
125
+ }