chainlesschain 0.165.8 → 0.165.9
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.
- package/package.json +1 -1
- package/src/assets/web-panel/.build-hash +1 -1
- package/src/assets/web-panel/assets/{AIOps-B3gWmXjo.js → AIOps-DxwjrnEA.js} +1 -1
- package/src/assets/web-panel/assets/{ActionButton-G9pdT-0e.js → ActionButton-JdbYowzn.js} +1 -1
- package/src/assets/web-panel/assets/{Analytics-Ca30J7m2.js → Analytics-C06GCahv.js} +3 -3
- package/src/assets/web-panel/assets/{AppLayout-BtVTm8PU.js → AppLayout-BUVEEyi1.js} +5 -5
- package/src/assets/web-panel/assets/{Artifacts-BhViNa6u.js → Artifacts-D_ORzkJd.js} +1 -1
- package/src/assets/web-panel/assets/{Audit-DhKq-FnY.js → Audit-8o_Y5ejG.js} +1 -1
- package/src/assets/web-panel/assets/{BackgroundAgents-BL0SVbnE.js → BackgroundAgents-DrkHd5VU.js} +1 -1
- package/src/assets/web-panel/assets/{Backup-BWkblnFi.js → Backup-CKBZCX11.js} +1 -1
- package/src/assets/web-panel/assets/{BaseInput-ClaRNrF8.js → BaseInput-C8HkI399.js} +1 -1
- package/src/assets/web-panel/assets/{Chat-sZE2Z77o.js → Chat-zb2H2Wux.js} +6 -6
- package/src/assets/web-panel/assets/{ChatBubbleRenderer-BAfKOnRe.js → ChatBubbleRenderer-BDcNpU_F.js} +1 -1
- package/src/assets/web-panel/assets/{Checkbox-Cvhay5WM.js → Checkbox-MwPtQmNz.js} +1 -1
- package/src/assets/web-panel/assets/{Codegen-BpejL-4N.js → Codegen-3p5QCkFK.js} +1 -1
- package/src/assets/web-panel/assets/{Col-g2Ki6g_1.js → Col-BPLlhn52.js} +1 -1
- package/src/assets/web-panel/assets/{Community-D2xKbNo9.js → Community-C-3dBNOM.js} +1 -1
- package/src/assets/web-panel/assets/{Compact-DbL1Pds3.js → Compact-BUcy-F_b.js} +1 -1
- package/src/assets/web-panel/assets/{Compliance-DGtZCV4c.js → Compliance-CI8NxT8m.js} +1 -1
- package/src/assets/web-panel/assets/{Cowork-4kQpoNsI.js → Cowork-DaDEBS-Q.js} +3 -3
- package/src/assets/web-panel/assets/{Cron-BxTYXXAN.js → Cron-BSv9HXu5.js} +2 -2
- package/src/assets/web-panel/assets/{Crosschain-k0J0LT2N.js → Crosschain-yuiKlJmv.js} +1 -1
- package/src/assets/web-panel/assets/{DID-BaqhoPgN.js → DID-D6LfldB0.js} +2 -2
- package/src/assets/web-panel/assets/{Dashboard-T4RVPIM1.js → Dashboard-CBhLqG61.js} +2 -2
- package/src/assets/web-panel/assets/{Dropdown-DszOToWq.js → Dropdown-BG8pIl3O.js} +1 -1
- package/src/assets/web-panel/assets/{EmailListRenderer-C9KJU7HF.js → EmailListRenderer-CY92VIE6.js} +1 -1
- package/src/assets/web-panel/assets/{FamilyGuardDashboard-Cmr0JnsA.js → FamilyGuardDashboard-1Q_ehauM.js} +1 -1
- package/src/assets/web-panel/assets/{Federation-BI-_2xZX.js → Federation-D3XirJIU.js} +1 -1
- package/src/assets/web-panel/assets/{FormItemContext-DsnDEPsl.js → FormItemContext-DfI9UuGZ.js} +1 -1
- package/src/assets/web-panel/assets/{GenericCardRenderer-BLncAKKK.js → GenericCardRenderer-IeCZk2m7.js} +1 -1
- package/src/assets/web-panel/assets/{Git-BPQhGXDn.js → Git-DzK4IJAZ.js} +2 -2
- package/src/assets/web-panel/assets/{Governance-CyElbUQW.js → Governance-BHf5KfmQ.js} +1 -1
- package/src/assets/web-panel/assets/{Inference-CcSntBQD.js → Inference-BmaxSALS.js} +1 -1
- package/src/assets/web-panel/assets/{KnowledgeGraph-p6e7HZ2r.js → KnowledgeGraph-BgePFLA9.js} +1 -1
- package/src/assets/web-panel/assets/{Logs-CNEtr-wz.js → Logs-nqgxpOc4.js} +2 -2
- package/src/assets/web-panel/assets/MarkdownRenderer-xkX6izBt.js +1 -0
- package/src/assets/web-panel/assets/{Marketplace-Dd2notAJ.js → Marketplace-Bu8to-86.js} +1 -1
- package/src/assets/web-panel/assets/McpTools-BFWTzEk0.js +4 -0
- package/src/assets/web-panel/assets/{Memory-Dg2uTvwx.js → Memory-B026G2GA.js} +2 -2
- package/src/assets/web-panel/assets/{MobileBridge-r1YMRiJV.js → MobileBridge-CM2Eeg6I.js} +1 -1
- package/src/assets/web-panel/assets/{MobileProjects-C-89kSm4.js → MobileProjects-B79Ob3hy.js} +1 -1
- package/src/assets/web-panel/assets/{Mtc-CrPZcVgf.js → Mtc-CxevSZuV.js} +5 -5
- package/src/assets/web-panel/assets/{MtcAudit-sxi7hqJb.js → MtcAudit-X396cPEX.js} +4 -4
- package/src/assets/web-panel/assets/{Multisig-CAgOMfF1.js → Multisig-HWIB_aZ1.js} +3 -3
- package/src/assets/web-panel/assets/{NLProgramming-DafaPts3.js → NLProgramming-gnYD1Xwy.js} +1 -1
- package/src/assets/web-panel/assets/{Notes-CJM-xUW_.js → Notes-Dn2Gf_J1.js} +3 -3
- package/src/assets/web-panel/assets/{NotificationSettings-L0ZjfAh_.js → NotificationSettings-BRKBQ5rq.js} +1 -1
- package/src/assets/web-panel/assets/{OrderTableRenderer-BB1CvCK0.js → OrderTableRenderer-Dy___Cgo.js} +1 -1
- package/src/assets/web-panel/assets/{Organization-DeLtgAD8.js → Organization-cqfccxnt.js} +4 -4
- package/src/assets/web-panel/assets/{Overflow-CKC2b10z.js → Overflow-CSX4FHN3.js} +1 -1
- package/src/assets/web-panel/assets/{P2P-eyf2rzY1.js → P2P-Bwa4aghp.js} +2 -2
- package/src/assets/web-panel/assets/{PdhVaultBrowser-5upNIOW8.js → PdhVaultBrowser-Dhszyjig.js} +3 -3
- package/src/assets/web-panel/assets/{Permissions-B8p3W6JK.js → Permissions-CXzTyk6e.js} +4 -4
- package/src/assets/web-panel/assets/{PersonalDataHub-BnRMxTq3.js → PersonalDataHub-CFCAAJbb.js} +5 -5
- package/src/assets/web-panel/assets/{Pipeline-DjCNI1li.js → Pipeline-BPJbx6xt.js} +1 -1
- package/src/assets/web-panel/assets/{Privacy-u6gXLbWT.js → Privacy-BbiXvEHz.js} +1 -1
- package/src/assets/web-panel/assets/{ProjectInit-BZAw4tkM.js → ProjectInit-B-s7-wSD.js} +2 -2
- package/src/assets/web-panel/assets/{ProjectSettings-B1Tr72q7.js → ProjectSettings-Dyug206y.js} +2 -2
- package/src/assets/web-panel/assets/{Projects-DO7HFuBQ.js → Projects-BtAI5Fwo.js} +1 -1
- package/src/assets/web-panel/assets/{Providers-BjCztyhj.js → Providers-JpIPmz6N.js} +1 -1
- package/src/assets/web-panel/assets/{QrScannerModal-ZWyCUbR1.js → QrScannerModal-CZdoN64A.js} +1 -1
- package/src/assets/web-panel/assets/{QuickAsk-DhDjeW4G.js → QuickAsk-BwvnoRIT.js} +1 -1
- package/src/assets/web-panel/assets/{Recommend-R_CN2MuU.js → Recommend-ASMlMQrD.js} +1 -1
- package/src/assets/web-panel/assets/{RemoteSession-uxFcujeu.js → RemoteSession-BiJzKFKi.js} +3 -3
- package/src/assets/web-panel/assets/{Reputation-DX8D7rks.js → Reputation-C80TWLIO.js} +1 -1
- package/src/assets/web-panel/assets/{Row-BYahQILD.js → Row-C1VNmjmX.js} +1 -1
- package/src/assets/web-panel/assets/{RssFeed-CUSQ2tm-.js → RssFeed-T2MyGUlG.js} +3 -3
- package/src/assets/web-panel/assets/{Search-CnN_S8Cs.js → Search-DXM6O83L.js} +1 -1
- package/src/assets/web-panel/assets/{Security-DcZlh-O4.js → Security-nv69kU7W.js} +4 -4
- package/src/assets/web-panel/assets/{Services-ZhBOjzIX.js → Services-AyHWe7Qj.js} +2 -2
- package/src/assets/web-panel/assets/{Skeleton-D5Qnq_lI.js → Skeleton-D6PWLxFI.js} +1 -1
- package/src/assets/web-panel/assets/{Skills-BC9cZ3Be.js → Skills-BqVeOmNQ.js} +1 -1
- package/src/assets/web-panel/assets/{Sla-DauJ3E8_.js → Sla-BegIPl9M.js} +1 -1
- package/src/assets/web-panel/assets/SpeechSettings-CKJn3xk-.js +1 -0
- package/src/assets/web-panel/assets/{SyncSettings-DUvJbSct.js → SyncSettings-Th4cnAMl.js} +2 -2
- package/src/assets/web-panel/assets/{Tasks-BXa-5noQ.js → Tasks-BuKfBroh.js} +1 -1
- package/src/assets/web-panel/assets/{Templates-JxaiUt_3.js → Templates-CMuWN8Ac.js} +1 -1
- package/src/assets/web-panel/assets/{Tenant-BW4ERQN8.js → Tenant-C4je8E8Q.js} +1 -1
- package/src/assets/web-panel/assets/{Terminal-DltUbdtv.js → Terminal-agJESOcO.js} +2 -2
- package/src/assets/web-panel/assets/{TimelineRenderer-CMoZz0Tc.js → TimelineRenderer-D2qDuVZ_.js} +1 -1
- package/src/assets/web-panel/assets/{Tokens-D_VEV60K.js → Tokens-Cvmn99rH.js} +1 -1
- package/src/assets/web-panel/assets/{Trigger-CCXTCs0R.js → Trigger-D_QYIHH8.js} +1 -1
- package/src/assets/web-panel/assets/{Trust-lkGRIPcG.js → Trust-BmzvQLnX.js} +1 -1
- package/src/assets/web-panel/assets/{UkeySign-BfGeQ9HX.js → UkeySign-D_LopHwH.js} +1 -1
- package/src/assets/web-panel/assets/{VideoEditing-BEC7pYvc.js → VideoEditing-DoWl3PhQ.js} +1 -1
- package/src/assets/web-panel/assets/{Wallet-BZdG24o0.js → Wallet-5NYcAkxe.js} +4 -4
- package/src/assets/web-panel/assets/{WebAuthn-yoEddedp.js → WebAuthn-B-_Q3ewp.js} +3 -3
- package/src/assets/web-panel/assets/{WorkflowEditor-BXZEprOW.js → WorkflowEditor-CHET-gi2.js} +1 -1
- package/src/assets/web-panel/assets/{chat-gg0bzZal.js → chat-C6nvb-n6.js} +1 -1
- package/src/assets/web-panel/assets/{colors-DjRVRuin.js → colors-CTDE9LTX.js} +1 -1
- package/src/assets/web-panel/assets/{compact-item-su-dieAc.js → compact-item-KnemdF8D.js} +1 -1
- package/src/assets/web-panel/assets/{createContext-Ci3S8oKF.js → createContext-DUJR3Uek.js} +1 -1
- package/src/assets/web-panel/assets/devWarning-1DqLH1KX.js +1 -0
- package/src/assets/web-panel/assets/{hasIn-D8F10heH.js → hasIn-CFNTaby8.js} +1 -1
- package/src/assets/web-panel/assets/{index-CusgZPtc.js → index-65HO56Bv.js} +1 -1
- package/src/assets/web-panel/assets/{index-BbF1IHof.js → index-B8RtbSkV.js} +1 -1
- package/src/assets/web-panel/assets/{index-CEmXRhAE.js → index-BHqSqnW7.js} +1 -1
- package/src/assets/web-panel/assets/{index-DIJ2qFOC.js → index-BTetEUWd.js} +1 -1
- package/src/assets/web-panel/assets/{index-CUmDhC4j.js → index-BXWg1crv.js} +1 -1
- package/src/assets/web-panel/assets/{index-DBAETXft.js → index-BdiC4LOs.js} +1 -1
- package/src/assets/web-panel/assets/index-BhJtcPWo.js +1 -0
- package/src/assets/web-panel/assets/{index-Tu8eWqh-.js → index-BuizJo2E.js} +1 -1
- package/src/assets/web-panel/assets/{index-BzPB6kGZ.js → index-BwZM1rod.js} +1 -1
- package/src/assets/web-panel/assets/{index-DkMEF5VT.js → index-C96N9xeL.js} +1 -1
- package/src/assets/web-panel/assets/{index-BTFpdBtt.js → index-CHfUdnJH.js} +1 -1
- package/src/assets/web-panel/assets/{index-DkfQR3hM.js → index-CKvBF3Ov.js} +1 -1
- package/src/assets/web-panel/assets/{index-T6_6ygJZ.js → index-CSD9_I2_.js} +1 -1
- package/src/assets/web-panel/assets/{index-CR0h6seT.js → index-Cc7dbl_p.js} +1 -1
- package/src/assets/web-panel/assets/{index-Dbq4NMET.js → index-CcF0D7UZ.js} +1 -1
- package/src/assets/web-panel/assets/{index-C6ygzplr.js → index-Ceu92a8D.js} +1 -1
- package/src/assets/web-panel/assets/{index-11wtYQiF.js → index-CnLpuTAU.js} +1 -1
- package/src/assets/web-panel/assets/index-Cq8MWPDT.js +1 -0
- package/src/assets/web-panel/assets/{index-1IgxgALJ.js → index-CquKnw5r.js} +1 -1
- package/src/assets/web-panel/assets/{index-CMPqd5Cv.js → index-CyEtHvEE.js} +1 -1
- package/src/assets/web-panel/assets/{index-BMMOVoLD.js → index-DF-fcTvQ.js} +1 -1
- package/src/assets/web-panel/assets/{index-W7XUgdVL.js → index-DF1Y0Vuw.js} +1 -1
- package/src/assets/web-panel/assets/{index-DyLUarhZ.js → index-DJyPeBBk.js} +3 -3
- package/src/assets/web-panel/assets/{index-BDJntYmJ.js → index-DP-PbO11.js} +1 -1
- package/src/assets/web-panel/assets/{index-COWd8uGx.js → index-DZgCRMxk.js} +1 -1
- package/src/assets/web-panel/assets/{index-8Z-8BIlN.js → index-DfJzS3Qa.js} +1 -1
- package/src/assets/web-panel/assets/{index-dHZinfko.js → index-DqPpJkte.js} +1 -1
- package/src/assets/web-panel/assets/{index-BCI5v0yB.js → index-DzReoLyh.js} +1 -1
- package/src/assets/web-panel/assets/{index-CPIYSp4H.js → index-JGTiDeOW.js} +1 -1
- package/src/assets/web-panel/assets/{index-jyNgp5FI.js → index-NUR0If7O.js} +1 -1
- package/src/assets/web-panel/assets/{index-6Tniqk1s.js → index-NtAcnJYW.js} +1 -1
- package/src/assets/web-panel/assets/{index-BgT9su_e.js → index-OmuhFYKE.js} +1 -1
- package/src/assets/web-panel/assets/{index-DugB_aKa.js → index-Wlc7o_C8.js} +1 -1
- package/src/assets/web-panel/assets/{index-Ba_HyPnE.js → index-bxTPfdri.js} +1 -1
- package/src/assets/web-panel/assets/{index-CC3ZDjzY.js → index-k6uorYmf.js} +1 -1
- package/src/assets/web-panel/assets/{index-5JqhujnR.js → index-ox6mIwE2.js} +1 -1
- package/src/assets/web-panel/assets/{index-1agckWSq.js → index-rVDD7AAR.js} +1 -1
- package/src/assets/web-panel/assets/{index-BGzixOGZ.js → index-u0h6QqVV.js} +1 -1
- package/src/assets/web-panel/assets/{index-DnLucOn9.js → index-v-mtxmWH.js} +1 -1
- package/src/assets/web-panel/assets/{initDefaultProps-Cv4p8e4w.js → initDefaultProps-qEt8dI-t.js} +1 -1
- package/src/assets/web-panel/assets/{motion-B8EwmMOw.js → motion-DetKPWy-.js} +1 -1
- package/src/assets/web-panel/assets/{move-B8R9F8TK.js → move-BeNYeDV2.js} +1 -1
- package/src/assets/web-panel/assets/{mtc-parser-DoFYz5Bp.js → mtc-parser-C0q0MK_T.js} +1 -1
- package/src/assets/web-panel/assets/{omit-CHWYLBjI.js → omit-DLKkrKpE.js} +1 -1
- package/src/assets/web-panel/assets/{pickAttrs-CXuPDO77.js → pickAttrs-Bw1tWsY8.js} +1 -1
- package/src/assets/web-panel/assets/{placementArrow-BaAtUUon.js → placementArrow-DeesBLbd.js} +1 -1
- package/src/assets/web-panel/assets/{responsiveObserve-DCc4zcDD.js → responsiveObserve-bqLhxHhn.js} +1 -1
- package/src/assets/web-panel/assets/{slide-B_lx89oZ.js → slide-DGCXRoQm.js} +1 -1
- package/src/assets/web-panel/assets/{statusUtils-DE8DPmR0.js → statusUtils-H-re3Egl.js} +1 -1
- package/src/assets/web-panel/assets/{styleChecker-1ktXOsL_.js → styleChecker-BXg4qGX_.js} +1 -1
- package/src/assets/web-panel/assets/{useFlexGapSupport-xH89-wjh.js → useFlexGapSupport-CKLb2KA6.js} +1 -1
- package/src/assets/web-panel/assets/{useFs-DscvfW5p.js → useFs-CTAhHeyw.js} +1 -1
- package/src/assets/web-panel/assets/{usePersonalDataHub-RdMKQta7.js → usePersonalDataHub-BQ4pDh5g.js} +1 -1
- package/src/assets/web-panel/assets/{vnode-Z3wTni2T.js → vnode-jrSK6j4j.js} +1 -1
- package/src/assets/web-panel/assets/{zoom-B0iChCsm.js → zoom-fOQE24pw.js} +1 -1
- package/src/assets/web-panel/index.html +1 -1
- package/src/data/changelog.json +13 -0
- package/src/gateways/ws/mcp-topic-handlers.js +167 -0
- package/src/lib/agent-network.js +166 -29
- package/src/lib/agent-router.js +62 -6
- package/src/lib/agent-sandbox.js +7 -1
- package/src/lib/claude-code-bridge.js +159 -54
- package/src/lib/cowork-workflow.js +69 -6
- package/src/lib/external-agent-adapters.js +269 -0
- package/src/lib/ipfs-storage.js +127 -25
- package/src/lib/orchestrator.js +47 -0
- package/src/lib/shell-approval.js +7 -5
- package/src/lib/workflow-engine.js +42 -11
- package/src/runtime/agent-runtime.js +12 -1
- package/src/assets/web-panel/assets/MarkdownRenderer-Bj9xI0YH.js +0 -1
- package/src/assets/web-panel/assets/McpTools-BBsN2CSW.js +0 -7
- package/src/assets/web-panel/assets/SpeechSettings-DbNeZ_fh.js +0 -1
- package/src/assets/web-panel/assets/devWarning-CxbFX9uH.js +0 -1
- package/src/assets/web-panel/assets/index-CJGOlduY.js +0 -1
- package/src/assets/web-panel/assets/index-CkBCN5yH.js +0 -1
|
@@ -14,7 +14,44 @@
|
|
|
14
14
|
*/
|
|
15
15
|
|
|
16
16
|
import { EventEmitter } from "events";
|
|
17
|
+
import crypto from "crypto";
|
|
18
|
+
import runtimeClaimsContract from "@chainlesschain/session-core/runtime-claims";
|
|
17
19
|
import executionBroker from "./process-execution-broker/index.js";
|
|
20
|
+
import {
|
|
21
|
+
createExternalAgentAdapter,
|
|
22
|
+
EXTERNAL_AGENT_ERROR,
|
|
23
|
+
} from "./external-agent-adapters.js";
|
|
24
|
+
|
|
25
|
+
const {
|
|
26
|
+
RUNTIME_MODE,
|
|
27
|
+
TERMINAL_EVIDENCE_KIND,
|
|
28
|
+
createRuntimeClaims,
|
|
29
|
+
hasTerminalSuccessEvidence,
|
|
30
|
+
} = runtimeClaimsContract;
|
|
31
|
+
|
|
32
|
+
const REAL_EXECUTION_CLAIMS = createRuntimeClaims({
|
|
33
|
+
mode: RUNTIME_MODE.REAL_EXECUTION,
|
|
34
|
+
durable: false,
|
|
35
|
+
crashSafe: false,
|
|
36
|
+
isolatedWrites: false,
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
const VALIDATION_ONLY_CLAIMS = createRuntimeClaims({
|
|
40
|
+
mode: RUNTIME_MODE.VALIDATE_ONLY,
|
|
41
|
+
});
|
|
42
|
+
|
|
43
|
+
function transcriptReceipt(rawOutput) {
|
|
44
|
+
return `sha256:${crypto.createHash("sha256").update(rawOutput).digest("hex")}`;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
export {
|
|
48
|
+
ExternalAgentAdapter,
|
|
49
|
+
ClaudeAdapter,
|
|
50
|
+
CodexAdapter,
|
|
51
|
+
createExternalAgentAdapter,
|
|
52
|
+
EXTERNAL_AGENT_ERROR,
|
|
53
|
+
EXTERNAL_AGENT_PROTOCOL,
|
|
54
|
+
} from "./external-agent-adapters.js";
|
|
18
55
|
|
|
19
56
|
/* ---------- _deps injection (Vitest CJS mock pattern) ---------- */
|
|
20
57
|
export const _deps = {
|
|
@@ -30,6 +67,7 @@ export const AGENT_STATUS = {
|
|
|
30
67
|
COMPLETED: "completed",
|
|
31
68
|
FAILED: "failed",
|
|
32
69
|
TIMEOUT: "timeout",
|
|
70
|
+
CANCELLED: "cancelled",
|
|
33
71
|
};
|
|
34
72
|
|
|
35
73
|
// Bound how much of a child's stdout/stderr we retain in memory. A verbose or
|
|
@@ -68,7 +106,7 @@ export function detectClaudeCode() {
|
|
|
68
106
|
}
|
|
69
107
|
|
|
70
108
|
/**
|
|
71
|
-
* Check if the
|
|
109
|
+
* Check if the OpenAI Codex CLI is installed.
|
|
72
110
|
* Returns { found: boolean, version?: string }.
|
|
73
111
|
*/
|
|
74
112
|
export function detectCodex() {
|
|
@@ -83,8 +121,9 @@ export function detectCodex() {
|
|
|
83
121
|
// ─── Single Agent ─────────────────────────────────────────────────
|
|
84
122
|
|
|
85
123
|
/**
|
|
86
|
-
* A single
|
|
87
|
-
*
|
|
124
|
+
* A single external coding-agent CLI process. The historical class name is
|
|
125
|
+
* retained for API compatibility; provider-specific argv and JSONL parsing are
|
|
126
|
+
* delegated to ClaudeAdapter or CodexAdapter.
|
|
88
127
|
*/
|
|
89
128
|
export class ClaudeCodeAgent extends EventEmitter {
|
|
90
129
|
constructor(options = {}) {
|
|
@@ -94,9 +133,18 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
94
133
|
`cc-agent-${Date.now()}-${Math.random().toString(36).slice(2, 6)}`;
|
|
95
134
|
this.cliCommand = options.cliCommand || "claude"; // "claude" or "codex"
|
|
96
135
|
this.model = options.model || null;
|
|
136
|
+
this.sandbox = options.sandbox || null;
|
|
137
|
+
this.adapter =
|
|
138
|
+
options.adapter ||
|
|
139
|
+
createExternalAgentAdapter({
|
|
140
|
+
cliCommand: this.cliCommand,
|
|
141
|
+
model: this.model,
|
|
142
|
+
sandbox: this.sandbox,
|
|
143
|
+
});
|
|
97
144
|
this.status = AGENT_STATUS.IDLE;
|
|
98
145
|
this.currentTask = null;
|
|
99
146
|
this._proc = null;
|
|
147
|
+
this._cancelRequested = false;
|
|
100
148
|
}
|
|
101
149
|
|
|
102
150
|
/**
|
|
@@ -128,14 +176,33 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
128
176
|
this.currentTask = taskDescription;
|
|
129
177
|
this.emit("task:start", { agentId: this.id, task: taskDescription });
|
|
130
178
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
args.
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
|
|
179
|
+
let args;
|
|
180
|
+
try {
|
|
181
|
+
args = this.adapter.buildArgs({ prompt: fullPrompt, allowedTools });
|
|
182
|
+
} catch (err) {
|
|
183
|
+
this.status = AGENT_STATUS.FAILED;
|
|
184
|
+
this.currentTask = null;
|
|
185
|
+
const result = {
|
|
186
|
+
success: false,
|
|
187
|
+
status: "validation-failed",
|
|
188
|
+
output: "",
|
|
189
|
+
exitCode: -1,
|
|
190
|
+
duration: 0,
|
|
191
|
+
timedOut: false,
|
|
192
|
+
cancelled: false,
|
|
193
|
+
agentId: this.id,
|
|
194
|
+
error: err.message,
|
|
195
|
+
errorCode: err.code || EXTERNAL_AGENT_ERROR.UNSUPPORTED_OPTION,
|
|
196
|
+
protocol: this.adapter.capabilities().protocol,
|
|
197
|
+
runtimeClaims: VALIDATION_ONLY_CLAIMS,
|
|
198
|
+
terminalEvidence: [],
|
|
199
|
+
};
|
|
200
|
+
this.emit("task:complete", result);
|
|
201
|
+
return result;
|
|
137
202
|
}
|
|
138
203
|
|
|
204
|
+
this._cancelRequested = false;
|
|
205
|
+
|
|
139
206
|
return new Promise((resolve) => {
|
|
140
207
|
const startTime = Date.now();
|
|
141
208
|
const outputChunks = [];
|
|
@@ -160,7 +227,7 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
160
227
|
return bytes;
|
|
161
228
|
};
|
|
162
229
|
|
|
163
|
-
const proc = _deps.spawn(this.
|
|
230
|
+
const proc = _deps.spawn(this.adapter.command, args, {
|
|
164
231
|
cwd,
|
|
165
232
|
env: { ...process.env },
|
|
166
233
|
windowsHide: true,
|
|
@@ -220,28 +287,93 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
220
287
|
this._proc = null;
|
|
221
288
|
const duration = Date.now() - startTime;
|
|
222
289
|
const rawOutput = outputChunks.join("");
|
|
290
|
+
const cancelled = this._cancelRequested && !timedOut;
|
|
291
|
+
const projection = this.adapter.parseTranscript(rawOutput);
|
|
292
|
+
const missingTerminal =
|
|
293
|
+
this.adapter.capabilities().requiresTerminalEvent &&
|
|
294
|
+
projection.terminal === null;
|
|
295
|
+
const protocolFailed =
|
|
296
|
+
projection.terminal === "failed" || missingTerminal;
|
|
223
297
|
const status = timedOut
|
|
224
298
|
? AGENT_STATUS.TIMEOUT
|
|
225
|
-
:
|
|
226
|
-
? AGENT_STATUS.
|
|
227
|
-
:
|
|
299
|
+
: cancelled
|
|
300
|
+
? AGENT_STATUS.CANCELLED
|
|
301
|
+
: protocolFailed
|
|
302
|
+
? AGENT_STATUS.FAILED
|
|
303
|
+
: code === 0
|
|
304
|
+
? AGENT_STATUS.COMPLETED
|
|
305
|
+
: AGENT_STATUS.FAILED;
|
|
228
306
|
|
|
229
307
|
this.status = status;
|
|
230
308
|
this.currentTask = null;
|
|
231
309
|
|
|
232
|
-
|
|
233
|
-
|
|
310
|
+
const terminalEvidence = [
|
|
311
|
+
...(projection.terminal
|
|
312
|
+
? [
|
|
313
|
+
{
|
|
314
|
+
kind: TERMINAL_EVIDENCE_KIND.RUNTIME_EVENT,
|
|
315
|
+
outcome: projection.terminal,
|
|
316
|
+
source: this.adapter.capabilities().protocol,
|
|
317
|
+
},
|
|
318
|
+
]
|
|
319
|
+
: []),
|
|
320
|
+
...(rawOutput
|
|
321
|
+
? [
|
|
322
|
+
{
|
|
323
|
+
kind: TERMINAL_EVIDENCE_KIND.OUTPUT_RECEIPT,
|
|
324
|
+
digest: transcriptReceipt(rawOutput),
|
|
325
|
+
},
|
|
326
|
+
]
|
|
327
|
+
: []),
|
|
328
|
+
];
|
|
329
|
+
const success =
|
|
330
|
+
code === 0 &&
|
|
331
|
+
!timedOut &&
|
|
332
|
+
!cancelled &&
|
|
333
|
+
!protocolFailed &&
|
|
334
|
+
hasTerminalSuccessEvidence(REAL_EXECUTION_CLAIMS, terminalEvidence);
|
|
335
|
+
const errorCode = timedOut
|
|
336
|
+
? EXTERNAL_AGENT_ERROR.TIMEOUT
|
|
337
|
+
: cancelled
|
|
338
|
+
? EXTERNAL_AGENT_ERROR.CANCELLED
|
|
339
|
+
: code !== 0
|
|
340
|
+
? EXTERNAL_AGENT_ERROR.EXIT_NONZERO
|
|
341
|
+
: protocolFailed
|
|
342
|
+
? EXTERNAL_AGENT_ERROR.PROTOCOL_FAILED
|
|
343
|
+
: null;
|
|
234
344
|
|
|
235
345
|
const result = {
|
|
236
|
-
success
|
|
237
|
-
|
|
346
|
+
success,
|
|
347
|
+
status: success ? "completed" : status,
|
|
348
|
+
output: projection.output || rawOutput.slice(-4000),
|
|
238
349
|
rawOutput,
|
|
239
350
|
outputTruncated, // true when the child exceeded maxOutputBytes
|
|
240
351
|
exitCode: code,
|
|
241
352
|
duration,
|
|
242
353
|
timedOut,
|
|
354
|
+
cancelled,
|
|
243
355
|
agentId: this.id,
|
|
244
356
|
stderr: errorChunks.join("").slice(-2000),
|
|
357
|
+
error: success
|
|
358
|
+
? undefined
|
|
359
|
+
: projection.error ||
|
|
360
|
+
(missingTerminal
|
|
361
|
+
? "External agent JSONL stream ended without a terminal event"
|
|
362
|
+
: null) ||
|
|
363
|
+
(timedOut
|
|
364
|
+
? "External agent timed out"
|
|
365
|
+
: cancelled
|
|
366
|
+
? "External agent was cancelled"
|
|
367
|
+
: `External agent exited with code ${code}`),
|
|
368
|
+
errorCode,
|
|
369
|
+
protocol: this.adapter.capabilities().protocol,
|
|
370
|
+
terminalEvent: projection.terminal,
|
|
371
|
+
usage: projection.usage,
|
|
372
|
+
unknownEventTypes: projection.unknownEventTypes,
|
|
373
|
+
unknownItemTypes: projection.unknownItemTypes,
|
|
374
|
+
malformedLineCount: projection.malformedLineCount,
|
|
375
|
+
runtimeClaims: REAL_EXECUTION_CLAIMS,
|
|
376
|
+
terminalEvidence,
|
|
245
377
|
};
|
|
246
378
|
|
|
247
379
|
this.emit("task:complete", result);
|
|
@@ -256,12 +388,18 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
256
388
|
this.currentTask = null;
|
|
257
389
|
const result = {
|
|
258
390
|
success: false,
|
|
391
|
+
status: "failed",
|
|
259
392
|
output: "",
|
|
260
393
|
exitCode: -1,
|
|
261
394
|
duration: Date.now() - startTime,
|
|
262
395
|
timedOut: false,
|
|
396
|
+
cancelled: false,
|
|
263
397
|
agentId: this.id,
|
|
264
398
|
error: err.message,
|
|
399
|
+
errorCode: EXTERNAL_AGENT_ERROR.SPAWN_FAILED,
|
|
400
|
+
protocol: this.adapter.capabilities().protocol,
|
|
401
|
+
runtimeClaims: REAL_EXECUTION_CLAIMS,
|
|
402
|
+
terminalEvidence: [],
|
|
265
403
|
};
|
|
266
404
|
this.emit("task:complete", result);
|
|
267
405
|
resolve(result);
|
|
@@ -272,6 +410,7 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
272
410
|
/** Abort the currently running task. */
|
|
273
411
|
abort() {
|
|
274
412
|
if (this._proc) {
|
|
413
|
+
this._cancelRequested = true;
|
|
275
414
|
this._proc.kill("SIGTERM");
|
|
276
415
|
}
|
|
277
416
|
}
|
|
@@ -281,6 +420,7 @@ export class ClaudeCodeAgent extends EventEmitter {
|
|
|
281
420
|
id: this.id,
|
|
282
421
|
status: this.status,
|
|
283
422
|
cliCommand: this.cliCommand,
|
|
423
|
+
protocol: this.adapter.capabilities().protocol,
|
|
284
424
|
currentTask: this.currentTask,
|
|
285
425
|
};
|
|
286
426
|
}
|
|
@@ -304,6 +444,7 @@ export class ClaudeCodePool extends EventEmitter {
|
|
|
304
444
|
this.maxParallel = options.maxParallel || 3;
|
|
305
445
|
this.cliCommand = options.cliCommand || "claude";
|
|
306
446
|
this.model = options.model || null;
|
|
447
|
+
this.sandbox = options.sandbox || null;
|
|
307
448
|
this.agentTimeout = options.agentTimeout || 300_000;
|
|
308
449
|
|
|
309
450
|
// Bound retained completion history. dispatch() returns results directly,
|
|
@@ -359,6 +500,7 @@ export class ClaudeCodePool extends EventEmitter {
|
|
|
359
500
|
id: `agent-${task.id}`,
|
|
360
501
|
cliCommand: this.cliCommand,
|
|
361
502
|
model: this.model,
|
|
503
|
+
sandbox: this.sandbox,
|
|
362
504
|
});
|
|
363
505
|
|
|
364
506
|
this._agents.set(agent.id, agent);
|
|
@@ -400,43 +542,6 @@ export class ClaudeCodePool extends EventEmitter {
|
|
|
400
542
|
}
|
|
401
543
|
}
|
|
402
544
|
|
|
403
|
-
// ─── Helpers ──────────────────────────────────────────────────────
|
|
404
|
-
|
|
405
|
-
/**
|
|
406
|
-
* Parse Claude Code stream-json output and extract the last assistant text.
|
|
407
|
-
* Stream-json lines look like: {"type":"assistant","message":{...}}
|
|
408
|
-
*/
|
|
409
|
-
function _parseStreamJson(raw) {
|
|
410
|
-
if (!raw) return "";
|
|
411
|
-
const lines = raw.split("\n").filter(Boolean);
|
|
412
|
-
let lastText = "";
|
|
413
|
-
|
|
414
|
-
for (const line of lines) {
|
|
415
|
-
try {
|
|
416
|
-
const obj = JSON.parse(line);
|
|
417
|
-
// stream-json: result message has type "result"
|
|
418
|
-
if (obj.type === "result" && obj.result) {
|
|
419
|
-
return typeof obj.result === "string"
|
|
420
|
-
? obj.result
|
|
421
|
-
: JSON.stringify(obj.result);
|
|
422
|
-
}
|
|
423
|
-
// assistant message blocks
|
|
424
|
-
if (obj.type === "assistant" && obj.message?.content) {
|
|
425
|
-
const blocks = obj.message.content;
|
|
426
|
-
const textBlocks = blocks
|
|
427
|
-
.filter((b) => b.type === "text")
|
|
428
|
-
.map((b) => b.text)
|
|
429
|
-
.join("\n");
|
|
430
|
-
if (textBlocks) lastText = textBlocks;
|
|
431
|
-
}
|
|
432
|
-
} catch (_err) {
|
|
433
|
-
// Non-JSON line (progress text) — ignore
|
|
434
|
-
}
|
|
435
|
-
}
|
|
436
|
-
|
|
437
|
-
return lastText;
|
|
438
|
-
}
|
|
439
|
-
|
|
440
545
|
// =====================================================================
|
|
441
546
|
// claude-code-bridge V2 governance overlay (iter17)
|
|
442
547
|
// =====================================================================
|
|
@@ -131,6 +131,9 @@ const ADMITTED_STEP_STATUSES = new Set([
|
|
|
131
131
|
"failed",
|
|
132
132
|
"partial",
|
|
133
133
|
"skipped",
|
|
134
|
+
"exhausted",
|
|
135
|
+
"upstream_failed",
|
|
136
|
+
"cancelled",
|
|
134
137
|
]);
|
|
135
138
|
const MAX_ADMITTED_RUN_STEPS = 64;
|
|
136
139
|
const MAX_ADMITTED_SNAPSHOT_NODES = 25_000;
|
|
@@ -948,6 +951,23 @@ export function validateWorkflow(wf) {
|
|
|
948
951
|
errors.push(`steps[${i}].maxIterations must be a positive integer`);
|
|
949
952
|
}
|
|
950
953
|
}
|
|
954
|
+
// forEach expands `stepId` into concrete runtime ids such as
|
|
955
|
+
// `stepId[0]`. A declarative step with the same id would overwrite the
|
|
956
|
+
// child result and make dependency/evidence accounting ambiguous.
|
|
957
|
+
for (const parent of wf.steps) {
|
|
958
|
+
if (parent?.forEach === undefined || typeof parent.id !== "string") {
|
|
959
|
+
continue;
|
|
960
|
+
}
|
|
961
|
+
const escapedParentId = parent.id.replace(/[.*+?^${}()|[\]\\]/gu, "\\$&");
|
|
962
|
+
const childIdPattern = new RegExp(`^${escapedParentId}\\[\\d+\\]$`, "u");
|
|
963
|
+
for (const id of ids) {
|
|
964
|
+
if (childIdPattern.test(id)) {
|
|
965
|
+
errors.push(
|
|
966
|
+
`step id '${id}' collides with dynamic children of '${parent.id}'`,
|
|
967
|
+
);
|
|
968
|
+
}
|
|
969
|
+
}
|
|
970
|
+
}
|
|
951
971
|
// Check dependsOn references exist
|
|
952
972
|
for (const s of wf.steps) {
|
|
953
973
|
for (const dep of s.dependsOn || []) {
|
|
@@ -1682,7 +1702,7 @@ export async function runLoopStep({
|
|
|
1682
1702
|
}
|
|
1683
1703
|
const outcome = {
|
|
1684
1704
|
id: recordId,
|
|
1685
|
-
status: last ? last.status : "skipped",
|
|
1705
|
+
status: stopReason === "cap" ? "exhausted" : last ? last.status : "skipped",
|
|
1686
1706
|
taskId: last?.taskId ?? null,
|
|
1687
1707
|
result: {
|
|
1688
1708
|
...(last?.result || {}),
|
|
@@ -1694,6 +1714,35 @@ export async function runLoopStep({
|
|
|
1694
1714
|
return admitted ? normalizeAdmittedOutcome(outcome) : outcome;
|
|
1695
1715
|
}
|
|
1696
1716
|
|
|
1717
|
+
function dependencyBlock(step, resultsById) {
|
|
1718
|
+
const blocked = (step.dependsOn || [])
|
|
1719
|
+
.map((id) => resultsById.get(id))
|
|
1720
|
+
.filter((outcome) => outcome && outcome.status !== "completed");
|
|
1721
|
+
if (blocked.length === 0) return null;
|
|
1722
|
+
|
|
1723
|
+
const blockedRootCut = [
|
|
1724
|
+
...new Set(
|
|
1725
|
+
blocked.flatMap((outcome) =>
|
|
1726
|
+
Array.isArray(outcome.result?.blockedRootCut)
|
|
1727
|
+
? outcome.result.blockedRootCut
|
|
1728
|
+
: [outcome.id],
|
|
1729
|
+
),
|
|
1730
|
+
),
|
|
1731
|
+
];
|
|
1732
|
+
const allSkipped = blocked.every((outcome) => outcome.status === "skipped");
|
|
1733
|
+
return {
|
|
1734
|
+
id: step.id,
|
|
1735
|
+
status: allSkipped ? "skipped" : "upstream_failed",
|
|
1736
|
+
taskId: null,
|
|
1737
|
+
result: {
|
|
1738
|
+
summary: allSkipped
|
|
1739
|
+
? "skipped because an upstream dependency was skipped"
|
|
1740
|
+
: "blocked by an unsuccessful upstream dependency",
|
|
1741
|
+
blockedRootCut,
|
|
1742
|
+
},
|
|
1743
|
+
};
|
|
1744
|
+
}
|
|
1745
|
+
|
|
1697
1746
|
// ─── Step node + no-barrier pipeline ──────────────────────────────────────────
|
|
1698
1747
|
|
|
1699
1748
|
/**
|
|
@@ -1726,6 +1775,12 @@ export async function runStepNode(step, ctx) {
|
|
|
1726
1775
|
};
|
|
1727
1776
|
};
|
|
1728
1777
|
|
|
1778
|
+
const blocked = dependencyBlock(step, resultsById);
|
|
1779
|
+
if (blocked) {
|
|
1780
|
+
resultsById.set(recordId, blocked);
|
|
1781
|
+
return { outcomes: [blocked], failed: blocked.status !== "skipped" };
|
|
1782
|
+
}
|
|
1783
|
+
|
|
1729
1784
|
let runThis;
|
|
1730
1785
|
try {
|
|
1731
1786
|
runThis = shouldRunStep(step, resultsById);
|
|
@@ -1834,9 +1889,10 @@ export async function runStepNode(step, ctx) {
|
|
|
1834
1889
|
* No-barrier pipeline scheduler: start each step the instant *its own*
|
|
1835
1890
|
* dependencies finish, rather than waiting for the whole dependency level.
|
|
1836
1891
|
* Up to `maxParallel` step nodes run concurrently. On failure with
|
|
1837
|
-
* `continueOnError` off, no new steps are scheduled (in-flight ones finish)
|
|
1838
|
-
*
|
|
1839
|
-
*
|
|
1892
|
+
* `continueOnError` off, no new steps are scheduled (in-flight ones finish).
|
|
1893
|
+
* Unscheduled descendants receive the same dependency-derived terminal state
|
|
1894
|
+
* as the batch executor; unrelated work is marked skipped. Only the wall-clock
|
|
1895
|
+
* idle between levels differs.
|
|
1840
1896
|
*/
|
|
1841
1897
|
export async function runPipeline({
|
|
1842
1898
|
steps,
|
|
@@ -1886,9 +1942,9 @@ export async function runPipeline({
|
|
|
1886
1942
|
reject(fatalError);
|
|
1887
1943
|
return;
|
|
1888
1944
|
}
|
|
1889
|
-
for (const s of steps) {
|
|
1945
|
+
for (const s of topoSort(steps)) {
|
|
1890
1946
|
if (scheduled.has(s.id)) continue;
|
|
1891
|
-
const o = {
|
|
1947
|
+
const o = dependencyBlock(s, resultsById) || {
|
|
1892
1948
|
id: s.id,
|
|
1893
1949
|
status: "skipped",
|
|
1894
1950
|
taskId: null,
|
|
@@ -2196,6 +2252,13 @@ export async function executeWorkflow(options = {}) {
|
|
|
2196
2252
|
const runnable = []; // { step, message, recordId, parentId }
|
|
2197
2253
|
const preOutcomes = []; // outcomes produced synchronously (skipped)
|
|
2198
2254
|
for (const step of chunk) {
|
|
2255
|
+
const blocked = dependencyBlock(step, resultsById);
|
|
2256
|
+
if (blocked) {
|
|
2257
|
+
if (blocked.status !== "skipped") anyFailure = true;
|
|
2258
|
+
resultsById.set(step.id, blocked);
|
|
2259
|
+
preOutcomes.push(blocked);
|
|
2260
|
+
continue;
|
|
2261
|
+
}
|
|
2199
2262
|
if (anyFailure && !continueOnError) {
|
|
2200
2263
|
const outcome = {
|
|
2201
2264
|
id: step.id,
|