@tencent-ai/agent-harness 0.2.0-beta.3 → 0.2.0-beta.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.
- package/CHANGELOG.md +14 -0
- package/cli/dist-server/shared.cjs +267 -210
- package/cli/dist-server/types/node/acp/acp-protocol.d.ts +8 -0
- package/cli/dist-server/types/node/loopback/server-protocol.d.ts +5 -0
- package/cli/dist-server/types/node/tools/tool-protocol.d.ts +23 -22
- package/cli/dist-server/types/vendor/cbc-core/node/agent/runner-factory.d.ts +18 -0
- package/cli/dist-server/types/vendor/cbc-core/node/context/index.d.ts +1 -0
- package/cli/dist-server/types/vendor/cbc-core/node/context/mods-bridge.d.ts +115 -0
- package/cli/dist-server/types/vendor/cbc-core/node/message-queue/followup-queue-protocol.d.ts +3 -2
- package/cli/dist-server/types/vendor/cbc-core/node/message-queue/followup-queue.d.ts +1 -1
- package/cli/dist-server/types/vendor/cbc-core/node/message-queue/steer-input-buffer-protocol.d.ts +4 -0
- package/cli/dist-server/types/vendor/cbc-core/node/session/can-use-tool.d.ts +4 -0
- package/cli/dist-server/types/vendor/cbc-core/node/session/session-manager.d.ts +30 -0
- package/cli/dist-server/types/vendor/cbc-core/node/session/session-protocol.d.ts +12 -0
- package/cli/dist-server/types/vendor/cbc-core/node/utils/input-item-utils.d.ts +1 -1
- package/cli/dist-server/types/workspace/agent-client-protocol/lib/common/prompt-codec.d.ts +4 -0
- package/cli/dist-server/types/workspace/agent-client-protocol/lib/common/types.d.ts +15 -1
- package/cli/dist-server/types/workspace/cbc-core/lib/node/agent/runner-factory.d.ts +18 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/context/index.d.ts +1 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/context/mods-bridge.d.ts +115 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/message-queue/followup-queue-protocol.d.ts +3 -2
- package/cli/dist-server/types/workspace/cbc-core/lib/node/message-queue/followup-queue.d.ts +1 -1
- package/cli/dist-server/types/workspace/cbc-core/lib/node/message-queue/steer-input-buffer-protocol.d.ts +4 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/session/can-use-tool.d.ts +4 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/session/session-manager.d.ts +30 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/session/session-protocol.d.ts +12 -0
- package/cli/dist-server/types/workspace/cbc-core/lib/node/utils/input-item-utils.d.ts +1 -1
- package/cli/dist-server/types/workspace/product/lib/common/types/features.d.ts +16 -0
- package/cli/dist-server/types/workspace/prompts/lib/common/product-prompt-provider.d.ts +3 -1
- package/cli/dist-server/types/workspace/prompts/lib/common/prompt-protocol.d.ts +6 -0
- package/cli/product.cloudhosted.json +1 -803
- package/cli/product.internal.json +1 -1061
- package/cli/product.ioa.json +1 -1523
- package/cli/product.json +1 -2217
- package/cli/product.selfhosted.json +1 -364
- package/docs/acp-v2.md +19 -0
- package/docs/client.md +7 -0
- package/docs/product.md +4 -0
- package/docs/protocol.md +3 -1
- package/lib/agent/v2.js +1 -1
- package/lib/application/services.js +1 -1
- package/lib/auth/module.d.ts +3 -1
- package/lib/auth/module.js +1 -1
- package/lib/client/client.js +1 -1
- package/lib/components/sandbox.d.mts +2 -0
- package/lib/components/sandbox.mjs +1 -0
- package/lib/components/session-replay.d.mts +2 -0
- package/lib/components/session-replay.mjs +1 -1
- package/lib/effect-runtime/concurrency.d.mts +2 -4
- package/lib/effect-runtime/concurrency.mjs +1 -1
- package/lib/effect-runtime/process-runtime-context.d.ts +5 -1
- package/lib/protocol/acp-v2-credits.d.ts +10 -0
- package/lib/protocol/acp-v2-credits.js +1 -0
- package/lib/protocol/acp-v2-private-client.d.ts +1 -10
- package/lib/runtime/codebuddy-auth.d.ts +5 -3
- package/lib/runtime/codebuddy-auth.js +1 -1
- package/lib/session/replay.d.ts +1 -1
- package/lib/session/replay.js +1 -1
- package/lib/session/server-events.js +1 -1
- package/lib/session/server-interactions.js +1 -1
- package/lib/subagent/history.js +1 -1
- package/package.json +14 -9
|
@@ -1 +1 @@
|
|
|
1
|
-
var Ve=Object.defineProperty;var t=(E,H)=>Ve(E,"name",{value:H,configurable:!0});import{homedir as we}from"node:os";import*as k from"node:path";import{isDeepStrictEqual as Xe}from"node:util";import{WORKBUDDY_ENABLE_LINUX_SANDBOX_CLI as Ae}from"@genie/product";import{Context as d,Effect as m,Exit as y,Layer as s,Logger as u,Option as Qe,Scope as h}from"effect";import{createAgentProtocolModule as Je}from"../agent/router.js";import{createAgentV2Facade as Ze}from"../agent/v2.js";import{ManagedAuthLocal as $e}from"../auth/local.js";import{ManagedAuth as er}from"../auth/managed.js";import{createAuthProtocolModule as rr}from"../auth/module.js";import{Checkpoints as _e}from"../checkpoint/service.js";import{ConfigFiles as re}from"../config/files.js";import{createDefaultAgentMcpIntegration as tr}from"../integration/agent-integration.js";import{PluginMcp as be}from"../integration/plugin-mcp.js";import{UserMcp as ke}from"../integration/user-mcp.js";import{requestWithEnvironment as or}from"../internal/http.js";import{createMcpServerProtocolModule as nr}from"../mcp-server/module.js";import{composeAgentHarnessModules as ir}from"../module/compose.js";import{PluginComponents as te}from"../plugin/components.js";import{createProductProtocolModule as ar}from"../product/module.js";import{preflightCodeBuddyCode as sr}from"../runtime/agent-runtime.js";import{buildAgentHarnessClientIdentityEnv as cr,buildAgentHarnessClientIdentityHeaders as dr}from"../runtime/client-identity.js";import{createCodeBuddyAuthRuntime as ur}from"../runtime/codebuddy-auth.js";import{createCodeBuddyProductLifecycle as pr}from"../runtime/codebuddy-product.js";import{DEFAULT_HOST_HEALTH_TIMEOUT_MS as mr,DEFAULT_READY_TIMEOUT_MS as lr}from"../runtime/codebuddy-resource-timeouts.js";import{CodeBuddyProcessContainment as fr}from"../runtime/process-containment.js";import{parseAgentHarnessProductConfig as hr,parseHarnessProductInput as gr}from"../runtime/product-config.js";import{ProductManager as yr}from"../runtime/product-manager.js";import{ProductResolver as De}from"../runtime/product-resolver.js";import{ProductResolverRequestError as Er}from"../runtime/product-resolver-error.js";import{loadProductSource as Sr}from"../runtime/product-source.js";import{HarnessSandboxCenter as vr}from"../runtime/sandbox-center.js";import{AgentHarnessServer as Cr,DEFAULT_LIFECYCLE_HOOK_TIMEOUT_MS as Pr}from"../server/index.js";import{makeServiceRpcs as wr}from"../server/rpc-services.js";import{AgentBackend as Ar,workspaceQueryOptions as _r}from"../session/agent-backend.js";import{AgentServer as Ie}from"../session/agent-server.js";import{readSessionConfigDefaults as br}from"../session/config-defaults.js";import{SessionConfigStore as kr}from"../session/config-store.js";import{SessionFiles as Dr}from"../session/files.js";import{localFs as Me}from"../session/local-fs.js";import{SessionReplay as Le}from"../session/replay.js";import{SessionRuntime as Ir}from"../session/runtime.js";import{Sessions as Te}from"../session/service.js";import{toExecutorPrivateProxyPolicy as Oe}from"../settings/proxy-policy.js";import{createHarnessSettingsRuntime as Mr}from"../settings/runtime.js";import{Settings as Lr}from"../settings/service.js";import{createSubagentProtocolModule as Tr}from"../subagent/module.js";import{createEffectTelemetryMetricAggregator as Or}from"../telemetry/effect-metric-aggregation.js";import{createTelemetry as xr}from"../telemetry/runtime.js";import{measureStartup as oe,startupProfiler as i}from"../telemetry/startup-profile.js";import{closeInPhases as ne,closeTelemetry as Rr,createCloseOnce as _,DEFAULT_TELEMETRY_CLOSE_TIMEOUT_MS as Fr}from"./lifecycle.js";export async function createApplicationServices({clientIdentity:E,clientIdentityEnv:H,dependencies:v,packageVersion:xe,processRuntime:g,productConfig:O,sandboxCenter:Re,tools:ie,strictMcpConfig:Fe,mcp:Ue,shutdown:B,telemetryOptions:ae,signal:p}){p?.throwIfAborted();const C=t(r=>m.runPromise(r,{signal:p}),"runStartupEffect"),z=B,se={name:"@genie/agent-harness",title:"Agent Harness",version:xe},ce=(v.preflightCodeBuddyCode??sr)(),D=new fr,x=new AbortController,l=xr(ae),W=_(()=>Rr(l,g,Math.max(1,Math.min(B.remainingMs(),ae.flushTimeoutMs??Fr))));B.registerTelemetryCloser(W);const de=Or(r=>l.recordEffectMetrics(r));try{g.addFinalizer(W)}catch(r){throw await W(),r}try{g.setTelemetryObserver({log:t(r=>l.recordEffectLog(r),"log"),metrics:t(r=>de.record("harness",r),"metrics"),span:t(r=>l.recordEffectSpan(r),"span")})}catch{}const b=t(r=>l.recordLifecycle(r),"recordLifecycle"),R=new vr(process.env.CODEBUDDY_CONFIG_DIR?.trim()?k.resolve(process.env.CODEBUDDY_CONFIG_DIR.trim()):k.join(we(),".codebuddy"),Re,process.env.SANDBOX_CENTER_IPC_ADDRESS?.trim()),N=_(()=>R.close());g.addFinalizer(N);let ue=!1;const Y=t((r,c,T)=>{ue||(ue=!0,b({component:"server",error:r,phase:"runtime",process:{pid:process.pid},reason:T,state:c}))},"recordRootFailure");D.signal.addEventListener("abort",()=>{Y(D.signal.reason,"containment_tripped","containment_failed")},{once:!0});const He={log(r){try{l.recordEffectLog(r)}catch{}},metrics(r){de.record("executor",r)},span(r){try{l.recordEffectSpan(r)}catch{}}};let P,n,F,I,a,A,M,w;const L=h.makeUnsafe(),G=_(r=>m.runPromise(h.close(L,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>G(void 0));const j=t(()=>{F&&m.runPromise(m.forkIn(F.prepare,L,{startImmediately:!0})).catch(()=>{})},"prepareRuntime"),pe=h.makeUnsafe(),q=_(async r=>{try{await a?.close(r)}finally{await m.runPromise(h.close(pe,r===void 0?y.void:y.fail(r)))}});g.addFinalizer(()=>q(void 0));const K=h.makeUnsafe(),V=_(r=>m.runPromise(h.close(K,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>V(void 0));const me=h.makeUnsafe(),X=_(r=>m.runPromise(h.close(me,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>X(void 0));const le=h.makeUnsafe(),Q=_(async r=>{try{await n?.close(r)}finally{await m.runPromise(h.close(le,r===void 0?y.void:y.fail(r)))}});g.addFinalizer(()=>Q(void 0));try{const r={...process.env},c={...H,...R.environment},T=typeof O=="object"?gr(O):Sr(O,{parse:hr});p?.throwIfAborted(),i()?.markStart("harness.product");const Be=await C(s.buildWithScope(De.layer({projection:T.projection,baseConfiguration:O===void 0?void 0:{},packageRoot:ce.productRoot??k.dirname(ce.packageJsonPath),clientIdentity:{ideName:E.ideName,ideType:E.ideType,ideVersion:E.ideVersion,...E.userAgent===void 0?{}:{userAgent:E.userAgent}},environment:t(()=>({...r,...c}),"environment")}),pe));a=await(v.createProductManager??((e,o)=>yr.create(e,o)))({bootstrap:T.bootstrap,projection:T.projection,resolver:d.get(Be,De)},p),i()?.markEnd("harness.product");const ze=t(()=>{if(!a)throw new Error("Product manager is not ready");return a.getLaunchSnapshot()},"productLaunch");p?.throwIfAborted(),i()?.markStart("harness.config");const We=await C(s.buildWithScope(re.layer.pipe(s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),K));i()?.markEnd("harness.config");const J=d.get(We,re),he=t((e,o)=>br(J,e,o),"sessionConfigDefaults");p?.throwIfAborted(),i()?.markStart("harness.settings"),A=await(v.createSettingsRuntime??Mr)({ambientEnvironment:r,config:J,environment:c,observe:t(e=>l.recordEffectLog({annotations:{component:"harness",operation:"refresh",reason:e.reason,resource:"policy","runtime.role":"harness",status:e.status,...e.policy===void 0?{}:{mode:e.policy.mode,noProxyCount:e.policy.noProxyCount,proxyConfigured:e.policy.proxyConfigured,proxySupport:e.policy.proxySupport,revision:e.policy.revision}},level:e.status==="failed"?"warn":"info",message:"harness.settings.proxy"}),"observe"),processRuntime:g}),i()?.markEnd("harness.settings");const ge=kr.layer(k.join(r.CODEBUDDY_CONFIG_DIR?.trim()?k.resolve(r.CODEBUDDY_CONFIG_DIR.trim()):k.join(we(),".codebuddy"),"harness","sessions"));p?.throwIfAborted(),i()?.markStart("harness.session-runtime");const ye=process.platform==="linux"?r[Ae]??((await import("#agent-harness-components/session-config")).isLinuxSandboxCLIInstalled()?"1":"0"):void 0,Ee=await C(s.buildWithScope(v.sessionRuntimeLayer??Ar({checkpoints:!0,headers:dr(E),prepareSandboxCenter:t((e,o)=>R.prepare(e.account?.uid,o),"prepareSandboxCenter"),resolveOptions:t(e=>m.map(_r(e),o=>({...o,...ie===void 0?{}:{tools:ie}})),"resolveOptions"),resolveConfigDefaults:t(e=>m.tryPromise({try:t(()=>he(e.workspace?.canonicalCwd??e.cwd??process.cwd(),e.signal),"try"),catch:t(o=>o,"catch")}),"resolveConfigDefaults")}).pipe(s.provideMerge(Ie.layer({product:{},fs:Me,settingSources:["user","project","local"],env:{...cr(E),CODEBUDDY_API_KEY_DISABLED:"1",CODEBUDDY_REMOTE_CONFIG_DISABLED:"1",CODEBUDDY_INCLUDE_TOPIC_MESSAGE:"true",...ye===void 0?{}:{[Ae]:ye},...R.environment,CODEBUDDY_CODE_DISABLE_FILE_CHECKPOINTING:r.CODEBUDDY_CODE_DISABLE_FILE_CHECKPOINTING??"0"}})),s.provide(ge)),L));i()?.markEnd("harness.session-runtime"),F=d.get(Ee,Ir),p?.throwIfAborted(),i()?.markStart("harness.replay");const Ne=d.get(await C(s.buildWithScope(Le.layer({},e=>Me.readFileBuffer(e),he).pipe(s.provide(ge)),L)),Le);i()?.markEnd("harness.replay"),p?.throwIfAborted(),i()?.markStart("harness.storage");const Se=await C(s.buildWithScope(s.mergeAll(Te.layer,_e.layer).pipe(s.provide(Dr.layer),s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),L));i()?.markEnd("harness.storage");const Ye=d.get(Se,Te),Ge=d.get(Se,_e);I=(v.createMcpIntegration??(e=>tr({containment:e.containment,recordEffectTelemetry:e.recordEffectTelemetry,recordLifecycle:e.recordLifecycle,supervisor:{environment:e.environment,toolsSyncTtlMs:Ue?.toolsSyncTtlMs,proxyPolicy:e.proxyPolicy}})))({containment:D,environment:c,proxyPolicy:Oe(A.currentProxyPolicy,c),recordEffectTelemetry:He,recordLifecycle:b}),M=A.subscribe(e=>{const o=Oe(e,c);I?.configureProxy?.(o).catch(()=>{l.recordEffectLog({annotations:{component:"harness",operation:"update",resource:"policy","runtime.role":"harness",status:"failed"},level:"warn",message:"harness.settings.proxy"})})});const ve=Qe.getOrUndefined(d.getOption(Ee,Ie));p?.throwIfAborted(),i()?.markStart("harness.mcp-services");const Z=await C(s.buildWithScope(s.mergeAll(ke.layer({environment:t(()=>({...r,...c}),"environment")}),be.layer).pipe(s.provideMerge(te.layer({environment:t(()=>({...r,...c}),"environment"),product:t(()=>a.getConfiguration(),"product"),writeContext:t(async()=>{await n?.prepareHostExecution(x.signal);const e=t(()=>({environment:{...r,...c},product:structuredClone(a.getConfiguration()),authentication:n?.currentSessionAuthentication()}),"capture");return n?n.runConsistentRead(e):e()},"writeContext"),onConfigChange:ve?async(e,o)=>{const f=o.authentication;ve.notifyConfigChange({source:e.source,filePath:e.file_path,cwd:e.cwd},{product:o.product,environment:o.environment,fetch:t((ee,U)=>or(ee,U,o.environment),"fetch"),auth:f?{accessToken:f.credential.accessToken,method:f.credential.type,refresh:t(async({signal:ee})=>{if(!n||!a)throw new Error("Hook authentication is unavailable");const U=t(()=>{if(!Xe(o.product,a.getConfiguration()))throw new Error("Hook Product changed")},"checkProduct");await n.runConsistentRead(U);const Pe=await n.refreshHostAuthentication(f,ee);return await n.runConsistentRead(U),{accessToken:Pe.credential.accessToken,method:Pe.credential.type}},"refresh")}:void 0,account:f?{uid:f.account.id,enterpriseId:f.account.organization?.id}:void 0}).catch(()=>m.runSync(m.logWarning("harness.config-change.failed").pipe(m.provide(u.layer([u.withConsoleError(u.formatLogFmt)])))))}:void 0,reloadUserConfig:t(e=>P?.reloadUserConfig(e)??Promise.resolve(),"reloadUserConfig")})),s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),me));i()?.markEnd("harness.mcp-services"),p?.throwIfAborted(),i()?.markStart("harness.agent-facade"),P=await(v.createAgentFacade??Ze)({userMcp:d.get(Z,ke),pluginMcp:d.get(Z,be),checkpoints:Ge,sessions:Ye,initialProductGeneration:ze().productGeneration,mcpIntegration:I,strictMcpConfig:Fe,onPermanentFailure:t(e=>{Y(e,"fused","recovery_failed"),x.abort(e)},"onPermanentFailure"),prepareSessionRuntime:t((e,o)=>{if(!n)throw new Error("Authentication runtime is not ready");return n.prepareSessionRuntime(e,o.connectionSignal)},"prepareSessionRuntime"),prepareSessionWorkspace:t(async(e,o)=>{if(!n||!a)throw new Error("Product manager is not ready");try{return await a.prepareWorkspace(e,{signal:o})}catch(f){if(!(f instanceof Er&&f.code==="AUTH_REFRESH_REQUIRED"))throw f;return await n.refreshProductAuthentication(o),a.prepareWorkspace(e,{force:!0,signal:o})}},"prepareSessionWorkspace"),releaseSessionWorkspace:t((e,o)=>a?a.releaseWorkspace(e,o):Promise.resolve(),"releaseSessionWorkspace"),refreshAuthentication:t((e,o)=>{if(!n)throw new Error("Authentication runtime is not ready");return n.refreshAuthentication(e,{signal:o?.signal??AbortSignal.abort(new Error("Authentication refresh has no operation signal"))})},"refreshAuthentication"),serverInfo:se,sessionRuntime:F,sessionReplay:Ne}),i()?.markEnd("harness.agent-facade");const Ce=pr({facade:P,onExecutionProductCommitted:j,product:a});p?.throwIfAborted(),i()?.markStart("harness.auth-service");const je=await C(s.buildWithScope(v.managedAuthLayer??$e({...a.resolveLoginProduct?{resolveLoginProduct:t((e,o)=>a.resolveLoginProduct(e,o),"resolveLoginProduct")}:{},environment:t(()=>({...r,...c}),"environment"),product:t(()=>a.getConfiguration(),"product")}).pipe(s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),le));i()?.markEnd("harness.auth-service"),n=ur({consumer:P,getAuthMethods:t(()=>a.getAuthMethods(),"getAuthMethods"),managedAuth:d.get(je,er),onRuntimePreparing:j,onRuntimePrepared:j,productLifecycle:Ce});const S=await rr(n);n.bindProtocolBridge(S.bridge);const $=ar({selectConnectionProductProfile:t((e,o)=>n.selectConnectionProductProfile(e,o),"selectConnectionProductProfile"),provisionProduct:t((e,o)=>S.runAuthMutation(()=>n.provisionProduct(e,o)),"provisionProduct"),readProduct:t((e,o)=>n.readProduct(e,o),"readProduct"),provisionWorkspaceProduct:t((e,o)=>S.runAuthMutation(()=>n.provisionWorkspaceProduct(e,o)),"provisionWorkspaceProduct"),readWorkspaceProduct:t((e,o)=>a.readWorkspaceProduct(e,o),"readWorkspaceProduct")});a.bindPublisher({notifyProductUpdated:t(()=>$.publisher.notifyProductUpdated(Ce.currentProductSnapshot()),"notifyProductUpdated"),notifyWorkspaceProductUpdated:t(e=>$.publisher.notifyWorkspaceProductUpdated(e),"notifyWorkspaceProductUpdated")});const qe=d.empty().pipe(d.add(Lr,A),d.add(re,J),d.add(te,d.get(Z,te)));p?.throwIfAborted(),i()?.markStart("harness.rpc-services");const Ke=await C(m.provide(wr.pipe(h.provide(K)),qe));i()?.markEnd("harness.rpc-services"),w=ir([{name:"private-runtime-lifecycle",capabilities:{},initialize:t(async(e,o)=>{await oe("harness.initialize.settings",()=>A?.initialize(o.connectionSignal))},"initialize"),close:t(async e=>{M?.(),M=void 0,await X(e),await A?.close(e),await ne([[()=>G(e),()=>I?.close(e)??Promise.resolve()],[()=>N()],[()=>q(e)]],z,"private runtime shutdown")},"close")},Je({v2:P}),nr({backend:P}),Tr({backend:P}),$,{name:S.name,capabilities:S.capabilities,initialize:t(async(e,o)=>oe("harness.initialize.auth",()=>S.initialize(e,o)),"initialize"),initialized:S.initialized,notificationHandlers:S.notificationHandlers,requestHandlers:S.requestHandlers,close:Q},{...Ke,close:V}])}catch(r){throw M?.(),M=void 0,b({component:"server",error:r,phase:"startup",process:{pid:process.pid},reason:"startup_failed",state:"startup_failed"}),await ne([[()=>V(r)],[()=>Q(r)],[()=>P?.close(r)??Promise.resolve(),()=>G(r)],[()=>I?.close(r)??Promise.resolve()],[()=>X(r)],[()=>A?.close(r)??Promise.resolve()],[()=>N()],[()=>q(r)]],z,"module startup cleanup").catch(()=>{}),r}let fe;try{p?.throwIfAborted(),fe=(v.createServer??(r=>new Cr(r)))({serverInfo:se,capabilities:w.capabilities,initializeHookTimeoutMs:lr+mr+Pr,initialize:t(async(r,c)=>(i()?.markEnd("harness.wait-initialize"),oe("harness.initialize",()=>w.initialize(r,c))),"initialize"),initialized:w.initialized,notificationHandlers:w.notificationHandlers,onContainmentFailure:t(r=>{Y(r,"containment_tripped","containment_failed"),x.abort(r)},"onContainmentFailure"),readinessSignal:D.signal,requestHandlers:w.requestHandlers,telemetryRuntime:l})}catch(r){b({component:"server",error:r,phase:"startup",process:{pid:process.pid},reason:"startup_failed",state:"startup_failed"});try{await ne([[()=>w.close(r)]],z,"server construction cleanup")}catch(c){b({component:"server",error:c,phase:"cleanup",process:{pid:process.pid},reason:"cleanup_failed",state:"shutdown_failed"})}throw r}return{server:fe,modules:w,telemetry:l,containment:D,runtimeShutdown:x,recordLifecycle:b}}t(createApplicationServices,"createApplicationServices");
|
|
1
|
+
var Ve=Object.defineProperty;var t=(E,H)=>Ve(E,"name",{value:H,configurable:!0});import{homedir as we}from"node:os";import*as k from"node:path";import{isDeepStrictEqual as Xe}from"node:util";import{Context as d,Effect as m,Exit as y,Layer as s,Logger as u,Option as Qe,Scope as h}from"effect";import{WORKBUDDY_ENABLE_LINUX_SANDBOX_CLI as Ae}from"#agent-harness-components/sandbox";import{createAgentProtocolModule as Je}from"../agent/router.js";import{createAgentV2Facade as Ze}from"../agent/v2.js";import{ManagedAuthLocal as $e}from"../auth/local.js";import{ManagedAuth as er}from"../auth/managed.js";import{createAuthProtocolModule as rr}from"../auth/module.js";import{Checkpoints as _e}from"../checkpoint/service.js";import{ConfigFiles as re}from"../config/files.js";import{createDefaultAgentMcpIntegration as tr}from"../integration/agent-integration.js";import{PluginMcp as be}from"../integration/plugin-mcp.js";import{UserMcp as ke}from"../integration/user-mcp.js";import{requestWithEnvironment as or}from"../internal/http.js";import{createMcpServerProtocolModule as nr}from"../mcp-server/module.js";import{composeAgentHarnessModules as ir}from"../module/compose.js";import{PluginComponents as te}from"../plugin/components.js";import{createProductProtocolModule as ar}from"../product/module.js";import{preflightCodeBuddyCode as sr}from"../runtime/agent-runtime.js";import{buildAgentHarnessClientIdentityEnv as cr,buildAgentHarnessClientIdentityHeaders as dr}from"../runtime/client-identity.js";import{createCodeBuddyAuthRuntime as ur}from"../runtime/codebuddy-auth.js";import{createCodeBuddyProductLifecycle as pr}from"../runtime/codebuddy-product.js";import{DEFAULT_HOST_HEALTH_TIMEOUT_MS as mr,DEFAULT_READY_TIMEOUT_MS as lr}from"../runtime/codebuddy-resource-timeouts.js";import{CodeBuddyProcessContainment as fr}from"../runtime/process-containment.js";import{parseAgentHarnessProductConfig as hr,parseHarnessProductInput as gr}from"../runtime/product-config.js";import{ProductManager as yr}from"../runtime/product-manager.js";import{ProductResolver as De}from"../runtime/product-resolver.js";import{ProductResolverRequestError as Er}from"../runtime/product-resolver-error.js";import{loadProductSource as Sr}from"../runtime/product-source.js";import{HarnessSandboxCenter as vr}from"../runtime/sandbox-center.js";import{AgentHarnessServer as Cr,DEFAULT_LIFECYCLE_HOOK_TIMEOUT_MS as Pr}from"../server/index.js";import{makeServiceRpcs as wr}from"../server/rpc-services.js";import{AgentBackend as Ar,workspaceQueryOptions as _r}from"../session/agent-backend.js";import{AgentServer as Ie}from"../session/agent-server.js";import{readSessionConfigDefaults as br}from"../session/config-defaults.js";import{SessionConfigStore as kr}from"../session/config-store.js";import{SessionFiles as Dr}from"../session/files.js";import{localFs as Me}from"../session/local-fs.js";import{SessionReplay as Le}from"../session/replay.js";import{SessionRuntime as Ir}from"../session/runtime.js";import{Sessions as Te}from"../session/service.js";import{toExecutorPrivateProxyPolicy as Oe}from"../settings/proxy-policy.js";import{createHarnessSettingsRuntime as Mr}from"../settings/runtime.js";import{Settings as Lr}from"../settings/service.js";import{createSubagentProtocolModule as Tr}from"../subagent/module.js";import{createEffectTelemetryMetricAggregator as Or}from"../telemetry/effect-metric-aggregation.js";import{createTelemetry as Rr}from"../telemetry/runtime.js";import{measureStartup as oe,startupProfiler as i}from"../telemetry/startup-profile.js";import{closeInPhases as ne,closeTelemetry as Fr,createCloseOnce as _,DEFAULT_TELEMETRY_CLOSE_TIMEOUT_MS as xr}from"./lifecycle.js";export async function createApplicationServices({clientIdentity:E,clientIdentityEnv:H,dependencies:v,packageVersion:Re,processRuntime:g,productConfig:O,sandboxCenter:Fe,tools:ie,strictMcpConfig:xe,mcp:Ue,shutdown:B,telemetryOptions:ae,signal:p}){p?.throwIfAborted();const C=t(r=>m.runPromise(r,{signal:p}),"runStartupEffect"),z=B,se={name:"@genie/agent-harness",title:"Agent Harness",version:Re},ce=(v.preflightCodeBuddyCode??sr)(),D=new fr,R=new AbortController,l=Rr(ae),W=_(()=>Fr(l,g,Math.max(1,Math.min(B.remainingMs(),ae.flushTimeoutMs??xr))));B.registerTelemetryCloser(W);const de=Or(r=>l.recordEffectMetrics(r));try{g.addFinalizer(W)}catch(r){throw await W(),r}try{g.setTelemetryObserver({log:t(r=>l.recordEffectLog(r),"log"),metrics:t(r=>de.record("harness",r),"metrics"),span:t(r=>l.recordEffectSpan(r),"span")})}catch{}const b=t(r=>l.recordLifecycle(r),"recordLifecycle"),F=new vr(process.env.CODEBUDDY_CONFIG_DIR?.trim()?k.resolve(process.env.CODEBUDDY_CONFIG_DIR.trim()):k.join(we(),".codebuddy"),Fe,process.env.SANDBOX_CENTER_IPC_ADDRESS?.trim()),N=_(()=>F.close());g.addFinalizer(N);let ue=!1;const Y=t((r,c,T)=>{ue||(ue=!0,b({component:"server",error:r,phase:"runtime",process:{pid:process.pid},reason:T,state:c}))},"recordRootFailure");D.signal.addEventListener("abort",()=>{Y(D.signal.reason,"containment_tripped","containment_failed")},{once:!0});const He={log(r){try{l.recordEffectLog(r)}catch{}},metrics(r){de.record("executor",r)},span(r){try{l.recordEffectSpan(r)}catch{}}};let P,n,x,I,a,A,M,w;const L=h.makeUnsafe(),G=_(r=>m.runPromise(h.close(L,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>G(void 0));const j=t(()=>{x&&m.runPromise(m.forkIn(x.prepare,L,{startImmediately:!0})).catch(()=>{})},"prepareRuntime"),pe=h.makeUnsafe(),q=_(async r=>{try{await a?.close(r)}finally{await m.runPromise(h.close(pe,r===void 0?y.void:y.fail(r)))}});g.addFinalizer(()=>q(void 0));const K=h.makeUnsafe(),V=_(r=>m.runPromise(h.close(K,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>V(void 0));const me=h.makeUnsafe(),X=_(r=>m.runPromise(h.close(me,r===void 0?y.void:y.fail(r))));g.addFinalizer(()=>X(void 0));const le=h.makeUnsafe(),Q=_(async r=>{try{await n?.close(r)}finally{await m.runPromise(h.close(le,r===void 0?y.void:y.fail(r)))}});g.addFinalizer(()=>Q(void 0));try{const r={...process.env},c={...H,...F.environment},T=typeof O=="object"?gr(O):Sr(O,{parse:hr});p?.throwIfAborted(),i()?.markStart("harness.product");const Be=await C(s.buildWithScope(De.layer({projection:T.projection,baseConfiguration:O===void 0?void 0:{},packageRoot:ce.productRoot??k.dirname(ce.packageJsonPath),clientIdentity:{ideName:E.ideName,ideType:E.ideType,ideVersion:E.ideVersion,...E.userAgent===void 0?{}:{userAgent:E.userAgent}},environment:t(()=>({...r,...c}),"environment")}),pe));a=await(v.createProductManager??((e,o)=>yr.create(e,o)))({bootstrap:T.bootstrap,projection:T.projection,resolver:d.get(Be,De)},p),i()?.markEnd("harness.product");const ze=t(()=>{if(!a)throw new Error("Product manager is not ready");return a.getLaunchSnapshot()},"productLaunch");p?.throwIfAborted(),i()?.markStart("harness.config");const We=await C(s.buildWithScope(re.layer.pipe(s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),K));i()?.markEnd("harness.config");const J=d.get(We,re),he=t((e,o)=>br(J,e,o),"sessionConfigDefaults");p?.throwIfAborted(),i()?.markStart("harness.settings"),A=await(v.createSettingsRuntime??Mr)({ambientEnvironment:r,config:J,environment:c,observe:t(e=>l.recordEffectLog({annotations:{component:"harness",operation:"refresh",reason:e.reason,resource:"policy","runtime.role":"harness",status:e.status,...e.policy===void 0?{}:{mode:e.policy.mode,noProxyCount:e.policy.noProxyCount,proxyConfigured:e.policy.proxyConfigured,proxySupport:e.policy.proxySupport,revision:e.policy.revision}},level:e.status==="failed"?"warn":"info",message:"harness.settings.proxy"}),"observe"),processRuntime:g}),i()?.markEnd("harness.settings");const ge=kr.layer(k.join(r.CODEBUDDY_CONFIG_DIR?.trim()?k.resolve(r.CODEBUDDY_CONFIG_DIR.trim()):k.join(we(),".codebuddy"),"harness","sessions"));p?.throwIfAborted(),i()?.markStart("harness.session-runtime");const ye=process.platform==="linux"?r[Ae]??((await import("#agent-harness-components/session-config")).isLinuxSandboxCLIInstalled()?"1":"0"):void 0,Ee=await C(s.buildWithScope(v.sessionRuntimeLayer??Ar({checkpoints:!0,headers:dr(E),prepareSandboxCenter:t((e,o)=>F.prepare(e.account?.uid,o),"prepareSandboxCenter"),resolveOptions:t(e=>m.map(_r(e),o=>({...o,...ie===void 0?{}:{tools:ie}})),"resolveOptions"),resolveConfigDefaults:t(e=>m.tryPromise({try:t(()=>he(e.workspace?.canonicalCwd??e.cwd??process.cwd(),e.signal),"try"),catch:t(o=>o,"catch")}),"resolveConfigDefaults")}).pipe(s.provideMerge(Ie.layer({product:{},fs:Me,settingSources:["user","project","local"],env:{...cr(E),CODEBUDDY_API_KEY_DISABLED:"1",CODEBUDDY_REMOTE_CONFIG_DISABLED:"1",CODEBUDDY_INCLUDE_TOPIC_MESSAGE:"true",...ye===void 0?{}:{[Ae]:ye},...F.environment,CODEBUDDY_CODE_DISABLE_FILE_CHECKPOINTING:r.CODEBUDDY_CODE_DISABLE_FILE_CHECKPOINTING??"0"}})),s.provide(ge)),L));i()?.markEnd("harness.session-runtime"),x=d.get(Ee,Ir),p?.throwIfAborted(),i()?.markStart("harness.replay");const Ne=d.get(await C(s.buildWithScope(Le.layer({},e=>Me.readFileBuffer(e),he).pipe(s.provide(ge)),L)),Le);i()?.markEnd("harness.replay"),p?.throwIfAborted(),i()?.markStart("harness.storage");const Se=await C(s.buildWithScope(s.mergeAll(Te.layer,_e.layer).pipe(s.provide(Dr.layer),s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),L));i()?.markEnd("harness.storage");const Ye=d.get(Se,Te),Ge=d.get(Se,_e);I=(v.createMcpIntegration??(e=>tr({containment:e.containment,recordEffectTelemetry:e.recordEffectTelemetry,recordLifecycle:e.recordLifecycle,supervisor:{environment:e.environment,toolsSyncTtlMs:Ue?.toolsSyncTtlMs,proxyPolicy:e.proxyPolicy}})))({containment:D,environment:c,proxyPolicy:Oe(A.currentProxyPolicy,c),recordEffectTelemetry:He,recordLifecycle:b}),M=A.subscribe(e=>{const o=Oe(e,c);I?.configureProxy?.(o).catch(()=>{l.recordEffectLog({annotations:{component:"harness",operation:"update",resource:"policy","runtime.role":"harness",status:"failed"},level:"warn",message:"harness.settings.proxy"})})});const ve=Qe.getOrUndefined(d.getOption(Ee,Ie));p?.throwIfAborted(),i()?.markStart("harness.mcp-services");const Z=await C(s.buildWithScope(s.mergeAll(ke.layer({environment:t(()=>({...r,...c}),"environment")}),be.layer).pipe(s.provideMerge(te.layer({environment:t(()=>({...r,...c}),"environment"),product:t(()=>a.getConfiguration(),"product"),writeContext:t(async()=>{await n?.prepareHostExecution(R.signal);const e=t(()=>({environment:{...r,...c},product:structuredClone(a.getConfiguration()),authentication:n?.currentSessionAuthentication()}),"capture");return n?n.runConsistentRead(e):e()},"writeContext"),onConfigChange:ve?async(e,o)=>{const f=o.authentication;ve.notifyConfigChange({source:e.source,filePath:e.file_path,cwd:e.cwd},{product:o.product,environment:o.environment,fetch:t((ee,U)=>or(ee,U,o.environment),"fetch"),auth:f?{accessToken:f.credential.accessToken,method:f.credential.type,refresh:t(async({signal:ee})=>{if(!n||!a)throw new Error("Hook authentication is unavailable");const U=t(()=>{if(!Xe(o.product,a.getConfiguration()))throw new Error("Hook Product changed")},"checkProduct");await n.runConsistentRead(U);const Pe=await n.refreshHostAuthentication(f,ee);return await n.runConsistentRead(U),{accessToken:Pe.credential.accessToken,method:Pe.credential.type}},"refresh")}:void 0,account:f?{uid:f.account.id,enterpriseId:f.account.organization?.id}:void 0}).catch(()=>m.runSync(m.logWarning("harness.config-change.failed").pipe(m.provide(u.layer([u.withConsoleError(u.formatLogFmt)])))))}:void 0,reloadUserConfig:t(e=>P?.reloadUserConfig(e)??Promise.resolve(),"reloadUserConfig")})),s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),me));i()?.markEnd("harness.mcp-services"),p?.throwIfAborted(),i()?.markStart("harness.agent-facade"),P=await(v.createAgentFacade??Ze)({userMcp:d.get(Z,ke),pluginMcp:d.get(Z,be),checkpoints:Ge,sessions:Ye,initialProductGeneration:ze().productGeneration,mcpIntegration:I,strictMcpConfig:xe,onPermanentFailure:t(e=>{Y(e,"fused","recovery_failed"),R.abort(e)},"onPermanentFailure"),prepareSessionRuntime:t((e,o)=>{if(!n)throw new Error("Authentication runtime is not ready");return n.prepareSessionRuntime(e,o.connectionSignal)},"prepareSessionRuntime"),prepareSessionWorkspace:t(async(e,o)=>{if(!n||!a)throw new Error("Product manager is not ready");try{return await a.prepareWorkspace(e,{signal:o})}catch(f){if(!(f instanceof Er&&f.code==="AUTH_REFRESH_REQUIRED"))throw f;return await n.refreshProductAuthentication(o),a.prepareWorkspace(e,{force:!0,signal:o})}},"prepareSessionWorkspace"),releaseSessionWorkspace:t((e,o)=>a?a.releaseWorkspace(e,o):Promise.resolve(),"releaseSessionWorkspace"),refreshAuthentication:t((e,o)=>{if(!n)throw new Error("Authentication runtime is not ready");return n.refreshAuthentication(e,{signal:o?.signal??AbortSignal.abort(new Error("Authentication refresh has no operation signal"))})},"refreshAuthentication"),serverInfo:se,sessionRuntime:x,sessionReplay:Ne}),i()?.markEnd("harness.agent-facade");const Ce=pr({facade:P,onExecutionProductCommitted:j,product:a});p?.throwIfAborted(),i()?.markStart("harness.auth-service");const je=await C(s.buildWithScope(v.managedAuthLayer??$e({...a.resolveLoginProduct?{resolveLoginProduct:t((e,o)=>a.resolveLoginProduct(e,o),"resolveLoginProduct")}:{},environment:t(()=>({...r,...c}),"environment"),product:t(()=>a.getConfiguration(),"product")}).pipe(s.provide(u.layer([u.withConsoleError(u.formatLogFmt)]))),le));i()?.markEnd("harness.auth-service"),n=ur({consumer:P,getAuthMethods:t(()=>a.getAuthMethods(),"getAuthMethods"),managedAuth:d.get(je,er),onRuntimePreparing:j,onRuntimePrepared:j,productLifecycle:Ce});const S=await rr(n);n.bindProtocolBridge(S.bridge);const $=ar({selectConnectionProductProfile:t((e,o)=>n.selectConnectionProductProfile(e,o),"selectConnectionProductProfile"),provisionProduct:t((e,o)=>S.runAuthMutation(()=>n.provisionProduct(e,o),{signal:o.signal}),"provisionProduct"),readProduct:t((e,o)=>n.readProduct(e,o),"readProduct"),provisionWorkspaceProduct:t((e,o)=>S.runAuthMutation(()=>n.provisionWorkspaceProduct(e,o),{signal:o.signal}),"provisionWorkspaceProduct"),readWorkspaceProduct:t((e,o)=>a.readWorkspaceProduct(e,o),"readWorkspaceProduct")});a.bindPublisher({notifyProductUpdated:t(()=>$.publisher.notifyProductUpdated(Ce.currentProductSnapshot()),"notifyProductUpdated"),notifyWorkspaceProductUpdated:t(e=>$.publisher.notifyWorkspaceProductUpdated(e),"notifyWorkspaceProductUpdated")});const qe=d.empty().pipe(d.add(Lr,A),d.add(re,J),d.add(te,d.get(Z,te)));p?.throwIfAborted(),i()?.markStart("harness.rpc-services");const Ke=await C(m.provide(wr.pipe(h.provide(K)),qe));i()?.markEnd("harness.rpc-services"),w=ir([{name:"private-runtime-lifecycle",capabilities:{},initialize:t(async(e,o)=>{await oe("harness.initialize.settings",()=>A?.initialize(o.connectionSignal))},"initialize"),close:t(async e=>{M?.(),M=void 0,await X(e),await A?.close(e),await ne([[()=>G(e),()=>I?.close(e)??Promise.resolve()],[()=>N()],[()=>q(e)]],z,"private runtime shutdown")},"close")},Je({v2:P}),nr({backend:P}),Tr({backend:P}),$,{name:S.name,capabilities:S.capabilities,initialize:t(async(e,o)=>oe("harness.initialize.auth",()=>S.initialize(e,o)),"initialize"),initialized:S.initialized,notificationHandlers:S.notificationHandlers,requestHandlers:S.requestHandlers,close:Q},{...Ke,close:V}])}catch(r){throw M?.(),M=void 0,b({component:"server",error:r,phase:"startup",process:{pid:process.pid},reason:"startup_failed",state:"startup_failed"}),await ne([[()=>V(r)],[()=>Q(r)],[()=>P?.close(r)??Promise.resolve(),()=>G(r)],[()=>I?.close(r)??Promise.resolve()],[()=>X(r)],[()=>A?.close(r)??Promise.resolve()],[()=>N()],[()=>q(r)]],z,"module startup cleanup").catch(()=>{}),r}let fe;try{p?.throwIfAborted(),fe=(v.createServer??(r=>new Cr(r)))({serverInfo:se,capabilities:w.capabilities,initializeHookTimeoutMs:lr+mr+Pr,initialize:t(async(r,c)=>(i()?.markEnd("harness.wait-initialize"),oe("harness.initialize",()=>w.initialize(r,c))),"initialize"),initialized:w.initialized,notificationHandlers:w.notificationHandlers,onContainmentFailure:t(r=>{Y(r,"containment_tripped","containment_failed"),R.abort(r)},"onContainmentFailure"),readinessSignal:D.signal,requestHandlers:w.requestHandlers,telemetryRuntime:l})}catch(r){b({component:"server",error:r,phase:"startup",process:{pid:process.pid},reason:"startup_failed",state:"startup_failed"});try{await ne([[()=>w.close(r)]],z,"server construction cleanup")}catch(c){b({component:"server",error:c,phase:"cleanup",process:{pid:process.pid},reason:"cleanup_failed",state:"shutdown_failed"})}throw r}return{server:fe,modules:w,telemetry:l,containment:D,runtimeShutdown:R,recordLifecycle:b}}t(createApplicationServices,"createApplicationServices");
|
package/lib/auth/module.d.ts
CHANGED
|
@@ -119,7 +119,9 @@ export interface AuthProtocolModule extends Omit<AgentHarnessProtocolModule, 'in
|
|
|
119
119
|
* Serializes another process-wide state mutation with Auth ownership.
|
|
120
120
|
* This is an in-process composition seam, never a public protocol method.
|
|
121
121
|
*/
|
|
122
|
-
runAuthMutation<Value>(operation: () => Promise<Value
|
|
122
|
+
runAuthMutation<Value>(operation: () => Promise<Value>, options?: {
|
|
123
|
+
readonly signal?: AbortSignal;
|
|
124
|
+
}): Promise<Value>;
|
|
123
125
|
}
|
|
124
126
|
/**
|
|
125
127
|
* Creates the process-wide authentication module.
|
package/lib/auth/module.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var V=Object.defineProperty;var
|
|
1
|
+
var V=Object.defineProperty;var o=(e,a)=>V(e,"name",{value:a,configurable:!0});import{currentHarnessProcessRuntime as W}from"../effect-runtime/process-runtime-context.js";import{clientManagementCapabilityBranch as Q}from"../module/capabilities.js";import{createUpdatedSubscriberRegistry as F}from"../module/updated-subscribers.js";import{validateParams as _,validateResult as R}from"../module/validation.js";import{ACP_V2_METHODS as K}from"../protocol/acp-v2.js";import{validateAcpV2AuthMethod as X,validateAcpV2CoreSchema as U}from"../protocol/acp-v2-schema.js";import{HARNESS_METHODS as Y}from"../protocol/methods.js";import{accountBinding as q,sameBinding as Z}from"../runtime/external-product-binding.js";import{AGENT_HARNESS_JSON_RPC_ERROR_CODES as S,AgentHarnessInvalidParamsError as N,AgentHarnessJsonRpcError as m}from"../server/errors.js";import{AUTH_STATUS_METHOD as k}from"./rpcs.js";import{accountProvisionParamsSchema as ee,accountProvisionResponseSchema as te,accountReadParamsSchema as ne,accountReadResponseSchema as D,accountRefreshParamsSchema as ae,accountRefreshResponseSchema as oe,accountUpdatedNotificationSchema as ce,authStatusRequestSchema as re,authStatusResponseSchema as ie}from"./schemas.js";const E=-32e3,ue=Object.freeze({account:null,mode:null,state:"unauthenticated"});export const AUTH_PROTOCOL_METHODS=Object.freeze({auth:Object.freeze({status:k}),account:Y.account}),AUTH_PROTOCOL_CAPABILITIES=Object.freeze({agent:Object.freeze({auth:Object.freeze({status:!0})}),account:Object.freeze({mode:"managed"})});function v(e,a){return Z(q(e,null),q(a,null))}o(v,"sameAccountBinding");function L(e,a,c){const g=U(a,c);if(g)throw new N(`Invalid ${e} params: ${g.message}`);return c}o(L,"validateAcpParams");function B(e,a,c){if(U(a,c))throw new m(S.internalError,`Invalid ${e} result`,{boundary:"result",method:e});return c}o(B,"validateAcpBackendResult");function se(e){if(!Array.isArray(e)||!e.every(X))throw new m(S.internalError,"Invalid authentication method catalog",{boundary:"result",method:"initialize"});const a=new Set;for(const c of e){if(a.has(c.methodId))throw new m(S.internalError,"Invalid authentication method catalog",{boundary:"result",method:"initialize"});a.add(c.methodId)}return Object.freeze([...e])}o(se,"validateAuthMethods");function de(e,a){if(e.state==="authenticated"&&e.mode!=="external"||e.state==="unauthenticated"&&e.mode!==null)throw new m(S.internalError,`Invalid ${a} result`,{boundary:"result",method:a})}o(de,"assertExternalSnapshot");function le(e){return Q(e,"account")}o(le,"accountCapability");function he(e){return Object.freeze({agent:Object.freeze({auth:Object.freeze({status:!0})}),account:Object.freeze({mode:e})})}o(he,"selectedCapabilities");function fe(e){return async(a,c)=>{const g=_(AUTH_PROTOCOL_METHODS.account.read,ne,a);return R(AUTH_PROTOCOL_METHODS.account.read,D,await e.readAccount(g,c))}}o(fe,"accountReadHandler");function me(e,a){return async(c,g)=>{const y=_(AUTH_PROTOCOL_METHODS.auth.status,re,c);return await e.prepareAuthStatus?.(y,g),a(async()=>R(AUTH_PROTOCOL_METHODS.auth.status,ie,await e.readAuthStatus(y,g)),{signal:g.signal})}}o(me,"authStatusHandler");export async function createAuthProtocolModule(e,a=W()){const c=K,g=e.accountUpdatePublication==="backend",y=fe(e);let u,P;const T=new WeakSet,C=new WeakMap,z=F();let A=0;const x=a.createSerialGate("Auth ownership mutation"),O=o((r,t={})=>x.run(()=>r(),{...t,uninterruptible:!0}),"runOwnershipMutation"),$=me(e,O),G=o((r,t)=>{u={account:structuredClone(r),context:t};const n=t.connectionSignal,l=o(()=>{if(u?.context.connectionSignal!==n)return;const p=A;u=void 0,O(async()=>{if(A!==p)return;let s,h=!1;try{h=await e.detachExternalAccount(t,n.reason)}catch(d){s=d,h=!0}if(A===p&&h&&(A+=1,g||await H(ue),s!==void 0))throw s}).catch(s=>{t.closeConnection?.(s).catch(()=>{})})},"detach");T.has(t.connectionSignal)||(T.add(t.connectionSignal),t.connectionSignal.addEventListener("abort",l,{once:!0})),n.aborted&&l()},"bindExternalOwner"),M=o(r=>{r.committed||(r.committed=!0,A+=1,G(r.account,r.context))},"commitExternalHandoff"),H=o(async(r,t={})=>{const i=R(AUTH_PROTOCOL_METHODS.account.updated,ce,r);if(i.mode==="external"&&i.state==="authenticated"){const n=P;if(n){const l=v(i.account,n.account),p=u!==void 0&&v(i.account,u.account),s=t.sourceOwner===n.context.connectionSignal,h=t.sourceOwner!==void 0&&t.sourceOwner===u?.context.connectionSignal,d=s&&l,f=h&&p;if(!(t.sourceOwner===void 0?l||p:d||f))throw new m(S.internalError,"Account update changed pending external identity");d&&!f&&M(n)}else if(u&&(!v(i.account,u.account)||t.sourceOwner!==void 0&&t.sourceOwner!==u.context.connectionSignal))throw new m(S.internalError,"Account update changed external identity")}else u=void 0;await z.broadcast(AUTH_PROTOCOL_METHODS.account.updated,i)},"broadcastAccountUpdated"),I=o(async r=>{if(g)return;const t=R(AUTH_PROTOCOL_METHODS.account.read,D,await e.readAccount({},{...r,signal:a.shutdownSignal}));await H(t)},"readAndBroadcastAccount"),J=Object.freeze({notifyAccountUpdated:H,async requestAccountRefresh(r,t){const i=_(AUTH_PROTOCOL_METHODS.account.refresh,ae,r),n=u;if(!n)throw new m(E,"Authentication required");if(n.context.connectionSignal.aborted)throw new m(E,"Authentication required",{reason:"owner_disconnected"});if(n.account.id!==i.accountId||n.context.connectionSignal!==t.expectedOwner)throw new m(E,"Authentication required",{reason:"account_changed"});let l;try{l=await n.context.request(AUTH_PROTOCOL_METHODS.account.refresh,i,t.signal===void 0?void 0:{signal:t.signal})}catch(s){throw n.context.connectionSignal.aborted?new m(E,"Authentication required",{reason:"owner_disconnected"}):s}const p=R(AUTH_PROTOCOL_METHODS.account.refresh,oe,l);if(!v(p.account,n.account))throw new m(E,"Authentication required",{reason:"account_changed"});return p}});return Object.freeze({bridge:J,capabilities:AUTH_PROTOCOL_CAPABILITIES,initialize:o(async(r,t)=>{const i=le(r),n=Object.freeze({mode:i.mode}),l=n.mode==="managed"?se(await e.listAuthMethods(r,t)):Object.freeze([]),p=new Set(l.map(h=>h.methodId));C.set(t.connectionSignal,n),e.selectConnectionAuthProfile?.(n,t),z.register(t);const s=new Map([[AUTH_PROTOCOL_METHODS.auth.status,$],[AUTH_PROTOCOL_METHODS.account.read,y]]);if(n.mode==="managed"&&l.length>0&&(s.set(c.agent.auth.login,async(h,d)=>{const f=L(c.agent.auth.login,"LoginAuthRequest",h);if(!p.has(f.methodId))throw new N(`Authentication method was not advertised: ${f.methodId}`);return O(async()=>{const w=B(c.agent.auth.login,"LoginAuthResponse",await e.login(f,d)??{});return A+=1,u=void 0,await I(d),w},{signal:d.signal})}),s.set(c.agent.auth.logout,async(h,d)=>{const f=L(c.agent.auth.logout,"LogoutAuthRequest",h);return O(async()=>{const w=B(c.agent.auth.logout,"LogoutAuthResponse",await e.logout(f,d)??{});return A+=1,u=void 0,await I(d),w},{signal:d.signal})})),n.mode==="external"){const h=o(async(d,f)=>{const w=_(AUTH_PROTOCOL_METHODS.account.provision,ee,d);return O(async()=>{const j=w.state==="authenticated"?{account:structuredClone(w.account),committed:!1,context:f}:void 0;P=j;try{const b=R(AUTH_PROTOCOL_METHODS.account.provision,te,await e.provisionAccount(w,f));if(de(b,AUTH_PROTOCOL_METHODS.account.provision),w.state!==b.state||w.state==="authenticated"&&b.state==="authenticated"&&!v(w.account,b.account))throw new m(S.internalError,`Invalid ${AUTH_PROTOCOL_METHODS.account.provision} result`,{boundary:"result",method:AUTH_PROTOCOL_METHODS.account.provision});return b.state==="authenticated"?M(j):(A+=1,u=void 0),await I(f),b}finally{P===j&&(P=void 0)}},{signal:f.signal})},"provisionHandler");s.set(AUTH_PROTOCOL_METHODS.account.provision,h)}return{capabilities:he(n.mode),registry:Object.freeze({inboundRequestHandlers:s,outboundNotificationMethods:Object.freeze([AUTH_PROTOCOL_METHODS.account.updated]),outboundRequestMethods:Object.freeze(n.mode==="external"?[AUTH_PROTOCOL_METHODS.account.refresh]:[])}),...l.length>0?{authMethods:l}:{}}},"initialize"),runAuthMutation:O,initialized:o((r,t)=>{z.promote(t);const i=C.get(t.connectionSignal);i&&e.markConnectionInitialized?.(i,t)},"initialized"),name:"auth"})}o(createAuthProtocolModule,"createAuthProtocolModule");
|
package/lib/client/client.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
var
|
|
1
|
+
var C=Object.defineProperty;var h=(f,e)=>C(f,"name",{value:e,configurable:!0});import{client as E,methods as c,PROTOCOL_VERSION as g,RequestError as M}from"@agentclientprotocol/sdk/experimental/v2";import{Effect as b,Stream as S}from"effect";import{isRecord as p}from"../internal/guards.js";import{normalizeAcpV2CreditsForSdk as y,restoreCodeBuddyCreditsFromSdk as v}from"../protocol/acp-v2-credits.js";import{toAcpStream as P}from"../transport/effect.js";import{CLIENT_MCP_METHODS as A,ClientMcp as I,isSessionMcpMethod as z}from"./mcp.js";import{clientMethods as j,notificationDecoders as O,notificationMethods as T,peerRequestDecoders as R,requestDecoders as N,requestMethods as _,reverseMethods as k,sendNotificationMethods as V}from"./rpc.js";import{isInMemoryEndpoint as D,openTransport as L}from"./transport.js";class F{static{h(this,"ClientLifecycle")}constructor(e){this.options=e,this.state="disconnected",this.cleanup=Promise.resolve(),this.handlers=new Map,this.listeners=new Map,this.mcp=new I({request:h((i,o)=>this.requireConnected().request(c.agent.mcp.message,i,{cancellationSignal:o?.signal}),"request"),notify:h(i=>this.requireConnected().notify(c.agent.mcp.message,i),"notify")})}on(e,i){if(this.assertOpen(),A.has(e))throw new TypeError("Client owns MCP handlers; configure mcpServers on the session instead");if(typeof i!="function")throw new TypeError("Client.on requires a function");if(k.has(e))return this.register(e,i);if(T.has(e))return this.subscribe(e,i);throw new TypeError(`${e} is not an incoming Client method`)}register(e,i){if(this.handlers.has(e))throw new Error(`${e} already has a request handler`);return this.handlers.set(e,i),()=>{this.handlers.get(e)===i&&this.handlers.delete(e)}}subscribe(e,i){let o=this.listeners.get(e);return o||this.listeners.set(e,o=new Set),o.add(i),()=>{o.delete(i)}}assertOpen(){if(this.state==="closed"||this.state==="closing")throw new Error("Client is closed")}async publish(e,i){const t=(await Promise.allSettled([...this.listeners.get(e)??[]].map(async n=>{await n(i)}))).filter(n=>n.status==="rejected").map(n=>n.reason);if(t.length>0)throw new AggregateError(t,`Notification listener failed for ${e}`)}handle(e,i,o){const t=this.handlers.get(e);if(t)return t(i,o);if(e===c.client.session.requestPermission)return{outcome:{outcome:"cancelled"}};throw M.methodNotFound(e)}async request(e,i={},o){const t=this.requireConnected(),n=N[e],l=z(e)?this.mcp.prepare(i):void 0;let a;try{const r=l?.params??i,d=await t.request(e,n?n.params(r):r,o);a=n?n.result(d):d}catch(r){throw await l?.rollback(),r}return await l?.commit(a),e===c.agent.session.close&&p(i)&&typeof i.sessionId=="string"&&await this.mcp.closeSession(i.sessionId),a}async notify(e,i){await this.requireConnected().notify(e,i)}requireConnected(){if(this.state!=="connected"||!this.agent)throw new Error("Await client.connect() before making requests");return this.agent}connect(e,i){if(this.state!=="disconnected")return Promise.reject(new Error(`Client is ${this.state}`));if(!p(e))return Promise.reject(new TypeError("connect requires a Server or connection options"));const o=D(e);if(i!==void 0&&!o)return Promise.reject(new TypeError("Separate connection settings require a Server"));const t=o?i??{}:e,n=this.options.capabilities?.elicitation;return(n?.form||n?.url)&&!this.handlers.has(c.client.elicitation.create)?Promise.reject(new Error("Register client.on('elicitation/create', handler) before advertising elicitation capabilities")):t.timeoutMs!==void 0&&(!Number.isFinite(t.timeoutMs)||t.timeoutMs<=0)?Promise.reject(new TypeError("timeoutMs must be positive")):(this.state="connecting",this.initialization=void 0,this.connectAbort=new AbortController,this.connecting=this.open(e,t,this.connectAbort),this.connecting)}async open(e,i,o){const t=setTimeout(()=>o.abort(new Error("Client connect timed out")),i.timeoutMs??3e4),n=i.signal?AbortSignal.any([i.signal,o.signal]):o.signal;let l;try{n.throwIfAborted(),await this.cleanup;const a=await L(e);this.stream=a,n.throwIfAborted();const r=E();r.onConnect(({agent:s})=>{this.agent=s}),r.onRequest(c.client.session.requestPermission,async s=>await this.handle(c.client.session.requestPermission,s.params,s)),r.onRequest(c.client.elicitation.create,async s=>await this.handle(c.client.elicitation.create,s.params,s)),r.onNotification(c.client.session.update,({params:s})=>this.publish(c.client.session.update,v(s))),r.onNotification(c.client.elicitation.complete,({params:s})=>this.publish(c.client.elicitation.complete,s));for(const[s,u]of Object.entries(R))r.onRequest(s,u.params,async m=>u.result(await this.handle(s,m.params,m)));for(const[s,u]of Object.entries(O))r.onNotification(s,u,({params:m})=>this.publish(s,m));r.onRequest(c.client.mcp.connect,s=>this.mcp.connect(s.params,s.signal)),r.onRequest(c.client.mcp.disconnect,s=>this.mcp.disconnect(s.params)),r.onRequest(c.client.mcp.message,s=>this.mcp.message(s.params,s.signal)),r.onNotification(c.client.mcp.message,s=>this.mcp.notify(s.params));const d=r.connect(P(this.adaptInitialize(a)));this.connection=d,this.cleanup=d.closed.then(async()=>{this.connection===d&&(this.connection=void 0,this.agent=void 0,this.state==="connected"&&(this.state="disconnected")),await this.mcp.close(),await b.runPromise(a.close())}),this.cleanup.catch(()=>{});const w=this.agent;if(!w)throw new Error("ACP SDK did not create its client context");const q=w.request(c.agent.initialize,{protocolVersion:g,info:this.options.clientInfo??{name:"agent-harness-client",version:"0.1.0"},capabilities:this.options.capabilities??{}});if(await Promise.race([q,new Promise((s,u)=>{l=h(()=>{d.close(n.reason),u(n.reason)},"onAbort"),n.addEventListener("abort",l,{once:!0}),n.aborted&&l()})]),await w.notify("initialized",{}),n.throwIfAborted(),d.signal.aborted)throw d.signal.reason;this.state="connected"}catch(a){throw this.connection?.close(a),await this.releaseStream(a),this.agent=void 0,this.connection=void 0,this.initialization=void 0,this.state==="connecting"&&(this.state="disconnected"),a}finally{clearTimeout(t),l&&n.removeEventListener("abort",l)}}adaptInitialize(e){let i;const o=h(t=>{if("id"in t&&t.id===i&&"result"in t){const n=t.result;if(!p(n)||n.protocolVersion!==1||!p(n.serverInfo)||!p(n.capabilities))throw new TypeError("Invalid Harness initialize response");return this.initialization=n,{...t,result:{protocolVersion:g,info:n.serverInfo,capabilities:n.capabilities.agent??{},...n.authMethods===void 0?{}:{authMethods:n.authMethods},...n._meta===void 0?{}:{_meta:n._meta}}}}return t},"project");return{...e,incoming:S.map(e.incoming,t=>Array.isArray(t)?y(t.map(o)):y(o(t))),send:h(t=>!Array.isArray(t)&&"method"in t&&"id"in t&&t.method===c.agent.initialize?(i=t.id,e.send({...t,params:{protocolVersion:1,clientInfo:this.options.clientInfo??{name:"agent-harness-client",version:"0.1.0"},capabilities:{agent:this.options.capabilities??{},...this.options.account===void 0?{}:{account:this.options.account},...this.options.product===void 0?{}:{product:this.options.product}}}})):e.send(t),"send")}}async releaseStream(e){this.stream&&await b.runPromise(this.stream.close(e)).catch(()=>{}),await this.cleanup.catch(()=>{}),this.stream=void 0}close(){return this.closing??=(async()=>{this.state="closing",this.connectAbort?.abort(new Error("Client closed")),this.connection?.close(),await this.connecting?.catch(()=>{}),await this.releaseStream(),await this.mcp.close(),this.handlers.clear(),this.listeners.clear(),this.state="closed"})()}}export function createClient(f={}){const e=new F(structuredClone(f));function i(o){const t={};for(const[n,l]of Object.entries(o))if(typeof l!="string"){const a=i(l);Object.keys(a).length>0&&(t[n]=a)}else V.has(l)?t[n]=a=>e.notify(l,a):_.has(l)&&(t[n]=(a,r)=>e.request(l,a,r));return Object.freeze(t)}return h(i,"project"),Object.freeze(Object.defineProperties({...i(j)},{state:{get:h(()=>e.state,"get")},initialization:{get:h(()=>e.initialization,"get")},on:{value:h((o,t)=>e.on(o,t),"value")},connect:{value:h((o,t)=>e.connect(o,t),"value")},close:{value:h(()=>e.close(),"value")}}))}h(createClient,"createClient");
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
export { FILE_DIRECTORY_APPROVAL_OPTION_ID, parseSandboxPermissionMetadata } from '../../cli/dist-server/types/workspace/agent-client-protocol/lib/common/index.js';
|
|
2
|
+
export { WORKBUDDY_ENABLE_LINUX_SANDBOX_CLI } from '../../cli/dist-server/types/workspace/product/lib/common/index.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import o from"#agent-harness-runtime";const a=o["component-sandbox"]();export const{FILE_DIRECTORY_APPROVAL_OPTION_ID,parseSandboxPermissionMetadata,WORKBUDDY_ENABLE_LINUX_SANDBOX_CLI}=a;
|
|
@@ -18,6 +18,8 @@ export declare function projectAgentFailure(error: unknown): ReturnType<typeof p
|
|
|
18
18
|
/** The durable assistant error carries its original HTTP/category fields. */
|
|
19
19
|
export declare function projectAgentItemError(item: AgentInputItem): ReturnType<typeof projectAgentError> | undefined;
|
|
20
20
|
export { projectAgentItem, projectAgentEvent } from '../../cli/dist-server/types/node/server/formats/acp/projection.js';
|
|
21
|
+
/** Per-model-request measurements, shared by live delivery and durable replay. */
|
|
22
|
+
export declare function readItemUsageMeta(item: AgentInputItem, origin?: Record<string, unknown>): Record<string, unknown> | undefined;
|
|
21
23
|
/** Storage-only ACP projection: no Cell container or execution services. */
|
|
22
24
|
export declare const projectSessionReplay: SessionReplayProjector;
|
|
23
25
|
/** Per-transcript billing stages and context; tree edges come from live lifecycle or SessionStore. */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import e from"#agent-harness-runtime";const t=e["component-session-replay"]();export const{selectRewindMessage,createToolInputParser,projectAgentError,projectAgentFailure,projectAgentItemError,createSessionUsage,AcpSessionFormatter,acpPromptInput,projectAgentItem,projectAgentEvent,projectSessionReplay}=t;
|
|
1
|
+
import e from"#agent-harness-runtime";const t=e["component-session-replay"]();export const{selectRewindMessage,createToolInputParser,projectAgentError,projectAgentFailure,projectAgentItemError,readItemUsageMeta,createSessionUsage,AcpSessionFormatter,acpPromptInput,projectAgentItem,projectAgentEvent,projectSessionReplay}=t;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { Effect } from 'effect';
|
|
2
2
|
import type { HarnessProcessRuntime } from './process-runtime.mjs';
|
|
3
|
-
import type { HarnessPolicyDeadlineHandle, HarnessPolicyDeadlineOptions } from './process-runtime-context.js';
|
|
3
|
+
import type { HarnessPolicyDeadlineHandle, HarnessPolicyDeadlineOptions, HarnessSerialGateRunOptions } from './process-runtime-context.js';
|
|
4
4
|
declare const HarnessConcurrencyClosedError_base: new <A extends Record<string, any> = {}>(args: import("effect/Types").VoidIfEmpty<{ readonly [P in keyof A as P extends "_tag" ? never : P]: A[P]; }>) => import("effect/Cause").YieldableError & {
|
|
5
5
|
readonly _tag: "HarnessConcurrencyClosedError";
|
|
6
6
|
} & Readonly<A>;
|
|
@@ -47,9 +47,7 @@ export declare class HarnessSerialGate {
|
|
|
47
47
|
private readonly semaphore;
|
|
48
48
|
private readonly state;
|
|
49
49
|
constructor(component: string, processRuntime: HarnessProcessRuntime);
|
|
50
|
-
run<Value>(operation: (signal: AbortSignal) => Promise<Value>, options?:
|
|
51
|
-
readonly signal?: AbortSignal;
|
|
52
|
-
}): Promise<Value>;
|
|
50
|
+
run<Value>(operation: (signal: AbortSignal) => Promise<Value>, options?: HarnessSerialGateRunOptions): Promise<Value>;
|
|
53
51
|
close(reason: unknown): Promise<void>;
|
|
54
52
|
private closeInternal;
|
|
55
53
|
/** @internal Root-Scope finalizer used by the process runtime. */
|
|
@@ -1 +1 @@
|
|
|
1
|
-
var U=Object.defineProperty;var l=(n,t)=>U(n,"name",{value:t,configurable:!0});import{Clock as C,Data as y,Deferred as d,Effect as a,Semaphore as v,SynchronizedRef as c}from"effect";export class HarnessConcurrencyClosedError extends y.TaggedError("HarnessConcurrencyClosedError"){static{l(this,"HarnessConcurrencyClosedError")}constructor(t,e){super({component:t,message:`${t} is closed`,reason:e}),this.code="HARNESS_CONCURRENCY_CLOSED"}}export class HarnessOperationTimeoutError extends y.TaggedError("HarnessOperationTimeoutError"){static{l(this,"HarnessOperationTimeoutError")}constructor(t,e){super({message:`${t} timed out after ${e}ms`,operation:t,timeoutMs:e}),this.code="HARNESS_OPERATION_TIMEOUT"}}export class HarnessConcurrencyOperationError extends y.TaggedError("HarnessConcurrencyOperationError"){static{l(this,"HarnessConcurrencyOperationError")}constructor(t,e){super({cause:e,component:t,message:`${t} operation failed`}),this.code="HARNESS_CONCURRENCY_OPERATION_FAILED"}}export class HarnessSerialGate{static{l(this,"HarnessSerialGate")}constructor(t,e){this.component=t,this.processRuntime=e,this.semaphore=v.makeUnsafe(1),this.state=c.makeUnsafe({closed:!1,drained:d.makeUnsafe(),pending:0})}async run(t,e={}){const r=await this.processRuntime.runEffect(c.modify(this.state,o=>o.closed?[{accepted:!1,error:new HarnessConcurrencyClosedError(this.component,o.closedReason)},o]:[{accepted:!0},{...o,pending:o.pending+1}]));if(!r.accepted)throw r.error;const i=b(this.semaphore.withPermit(E(this.component,t)).pipe(a.ensuring(c.update(this.state,o=>{const s=o.pending-1;return s===0&&o.closed&&d.doneUnsafe(o.drained,a.void),{...o,pending:s}}))),this.component);try{return await this.processRuntime.runEffect(i,e)}catch(o){throw e.signal?.aborted?h(e.signal,`${this.component} operation aborted`):R(o)}}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>{if(r.closed)return[r.drained,r];const i={...r,closed:!0,closedReason:t};return i.pending===0&&d.doneUnsafe(i.drained,a.void),[i.drained,i]}));await this.processRuntime.runEffect(d.await(e))}closeEffect(t){return c.modify(this.state,e=>{if(e.closed)return[e.drained,e];const r={...e,closed:!0,closedReason:t};return r.pending===0&&d.doneUnsafe(r.drained,a.void),[r.drained,r]}).pipe(a.flatMap(d.await))}}export class HarnessStateCell{static{l(this,"HarnessStateCell")}constructor(t,e){this.processRuntime=t,this.state=c.makeUnsafe(e)}get current(){return c.getUnsafe(this.state)}set(t){return this.processRuntime.runEffect(c.set(this.state,t))}update(t){return this.processRuntime.runEffect(c.update(this.state,t))}}export class HarnessKeyedSerialGate{static{l(this,"HarnessKeyedSerialGate")}constructor(t,e){this.component=t,this.processRuntime=e,this.state=c.makeUnsafe({closed:!1,entries:new Map})}async run(t,e,r={}){const i=await this.processRuntime.runEffect(c.modify(this.state,s=>{if(s.closed)return[{entry:void 0,error:new HarnessConcurrencyClosedError(this.component,s.closedReason)},s];const u=s.entries.get(t),f=u===void 0?{drained:d.makeUnsafe(),pending:1,semaphore:v.makeUnsafe(1)}:{...u,pending:u.pending+1},m=new Map(s.entries);return m.set(t,f),[{entry:f},{...s,entries:m}]}));if(i.entry===void 0)throw i.error;const o=b(i.entry.semaphore.withPermit(E(this.component,e)).pipe(a.ensuring(c.update(this.state,s=>{const u=s.entries.get(t);if(u===void 0)return s;const f=new Map(s.entries);return u.pending===1?(d.doneUnsafe(u.drained,a.void),f.delete(t)):f.set(t,{...u,pending:u.pending-1}),{...s,entries:f}}))),this.component);try{return await this.processRuntime.runEffect(o,r)}catch(s){throw r.signal?.aborted?h(r.signal,`${this.component} operation aborted`):R(s)}}async waitForIdle(t,e={}){const r=c.getUnsafe(this.state).entries.get(t)?.drained;if(r!==void 0)try{await this.processRuntime.runEffect(d.await(r),e)}catch(i){throw e.signal?.aborted?h(e.signal,`${this.component} wait aborted`):i}}has(t){return c.getUnsafe(this.state).entries.has(t)}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>[[...r.entries.values()],{...r,closed:!0,closedReason:r.closed?r.closedReason:t}]));await Promise.allSettled(e.map(r=>this.processRuntime.runEffect(d.await(r.drained))))}closeEffect(t){return c.modify(this.state,e=>[[...e.entries.values()],{...e,closed:!0,closedReason:e.closed?e.closedReason:t}]).pipe(a.flatMap(e=>a.forEach(e,r=>d.await(r.drained),{concurrency:"unbounded",discard:!0})),a.andThen(c.update(this.state,e=>({...e,entries:new Map}))))}}export class HarnessSingleFlight{static{l(this,"HarnessSingleFlight")}constructor(t,e){this.component=t,this.processRuntime=e,this.state=c.makeUnsafe({closed:!1,flights:new Map})}async run(t,e,r={}){const i=await this.processRuntime.runEffect(c.modify(this.state,o=>{if(o.closed)return[{entry:void 0,error:new HarnessConcurrencyClosedError(this.component,o.closedReason),owner:!1},o];const s=o.flights.get(t);if(s!==void 0)return[{entry:s,owner:!1},o];const u={completed:d.makeUnsafe(),controller:new AbortController,result:d.makeUnsafe()},f=new Map(o.flights);return f.set(t,u),[{entry:u,owner:!0},{...o,flights:f}]}));if(i.entry===void 0)throw i.error;i.owner&&this.runOwner(t,i.entry,e,r.timeoutMs);try{return await this.processRuntime.runEffect(d.await(i.entry.result),{signal:r.signal})}catch(o){throw r.signal?.aborted?h(r.signal,r.abortMessage??`${this.component} wait aborted`):R(o)}}abortAll(t){const e=c.getUnsafe(this.state);for(const r of e.flights.values())r.controller.abort(t)}has(t){return c.getUnsafe(this.state).flights.has(t)}get activeCount(){return c.getUnsafe(this.state).flights.size}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>r.closed?[[...r.flights.values()],r]:[[...r.flights.values()],{...r,closed:!0,closedReason:t}]));for(const r of e)r.controller.abort(t);await Promise.allSettled(e.map(r=>this.processRuntime.runEffect(d.await(r.completed))))}closeEffect(t){return c.modify(this.state,e=>e.closed?[[...e.flights.values()],e]:[[...e.flights.values()],{...e,closed:!0,closedReason:t}]).pipe(a.tap(e=>a.sync(()=>{for(const r of e)r.controller.abort(t)})),a.flatMap(e=>a.forEach(e,r=>d.await(r.completed),{concurrency:"unbounded",discard:!0})),a.andThen(c.update(this.state,e=>({...e,flights:new Map}))))}async runOwner(t,e,r,i){let o=E(this.component,r);i!==void 0&&(o=withOperationTimeout(o,this.component,i)),o=b(o,this.component);try{const s=await this.processRuntime.runEffect(o,{signal:e.controller.signal});d.doneUnsafe(e.result,a.succeed(s))}catch(s){const u=e.controller.signal.aborted?new HarnessConcurrencyOperationError(this.component,h(e.controller.signal,`${this.component} owner aborted`)):s;d.doneUnsafe(e.result,u instanceof HarnessConcurrencyOperationError||u instanceof HarnessOperationTimeoutError?a.fail(u):a.die(u))}finally{await this.processRuntime.runEffect(c.update(this.state,s=>{if(s.flights.get(t)!==e)return s;const u=new Map(s.flights);return u.delete(t),{...s,flights:u}})).catch(()=>{}),d.doneUnsafe(e.completed,a.void)}}}export function policyDelay(n){return a.sleep(n)}l(policyDelay,"policyDelay");export function policyBackoff(n,t,e){return policyDelay(N(n,t,e))}l(policyBackoff,"policyBackoff");export function policyNow(){return C.currentTimeMillis}l(policyNow,"policyNow");export function withOperationTimeout(n,t,e){return n.pipe(a.timeout(e),a.catchTag("TimeoutError",()=>a.fail(new HarnessOperationTimeoutError(t,e))))}l(withOperationTimeout,"withOperationTimeout");export async function runPolicyDelay(n,t,e,r){try{await n.runEffect(policyDelay(t),{signal:e})}catch(i){throw e.aborted?h(e,r):i}}l(runPolicyDelay,"runPolicyDelay");export async function runPolicyBackoff(n,t,e,r,i,o){try{await n.runEffect(policyBackoff(t,e,r),{signal:i})}catch(s){throw i.aborted?h(i,o):s}}l(runPolicyBackoff,"runPolicyBackoff");export function createPolicyDeadline(n,t,e={}){if(!Number.isSafeInteger(t)||t<=0)throw new RangeError("Policy deadline must be a positive integer");const r=new AbortController,i=new AbortController,o=e.signals??[],s=AbortSignal.any([...o,r.signal]),u=[];let f=!1;const m=l(()=>{for(const[p,w]of u)p.removeEventListener("abort",w);u.length=0},"cleanup"),g=l(()=>{f||(f=!0,m(),i.abort(new Error("Policy deadline completed")))},"close");for(const p of o){if(p.aborted){g();break}const w=g;if(u.push([p,w]),p.addEventListener("abort",w,{once:!0}),p.aborted){g();break}}return f||n.runEffect(policyDelay(t),{signal:i.signal}).then(()=>{f||(f=!0,m(),r.abort(e.timeoutReason??new HarnessOperationTimeoutError("policy deadline",t)))}).catch(p=>{f||i.signal.aborted||(f=!0,m(),r.abort(p))}),Object.freeze({close:g,signal:s})}l(createPolicyDeadline,"createPolicyDeadline");function N(n,t,e){if(!Number.isSafeInteger(n)||n<=0||!Number.isSafeInteger(t)||t<=0||!Number.isSafeInteger(e)||e<=0)throw new RangeError("Policy backoff values must be positive integers");return Math.min(e,n*2**(t-1))}l(N,"policyBackoffDuration");function h(n,t){return n.reason??new Error(t)}l(h,"abortReason");function E(n,t){return a.tryPromise({catch:l(e=>new HarnessConcurrencyOperationError(n,e),"catch"),try:t})}l(E,"tryConcurrencyOperation");function R(n){return n instanceof HarnessConcurrencyOperationError?n.cause:n}l(R,"unwrapConcurrencyOperationError");function b(n,t){const e=P(t);if(e===void 0)return n;const r={component:e.component,operation:e.operation};return n.pipe(a.tap(()=>a.logInfo(e.eventName).pipe(a.annotateLogs({...r,outcome:"success"}))),a.tapError(()=>a.logWarning(e.eventName).pipe(a.annotateLogs({...r,outcome:"error"}))),a.withSpan(e.eventName,{attributes:r}))}l(b,"observeConcurrencyEffect");function P(n){switch(n){case"Auth ownership mutation":case"Authentication mutation":return{component:"auth",eventName:"harness.auth.mutation",operation:"update"};case"Authentication refresh":return{component:"auth",eventName:"harness.auth.refresh",operation:"refresh"};case"Product mutation":return{component:"product",eventName:"harness.product.mutation",operation:"update"};case"Workspace Product cleanup":return{component:"product",eventName:"harness.product.mutation",operation:"release"};case"Workspace Product resolution":return{component:"product",eventName:"harness.product.resolve",operation:"resolve"};default:return}}l(P,"concurrencyTelemetrySpec");
|
|
1
|
+
var U=Object.defineProperty;var l=(o,t)=>U(o,"name",{value:t,configurable:!0});import{Clock as C,Data as y,Deferred as d,Effect as s,Semaphore as v,SynchronizedRef as c}from"effect";export class HarnessConcurrencyClosedError extends y.TaggedError("HarnessConcurrencyClosedError"){static{l(this,"HarnessConcurrencyClosedError")}constructor(t,e){super({component:t,message:`${t} is closed`,reason:e}),this.code="HARNESS_CONCURRENCY_CLOSED"}}export class HarnessOperationTimeoutError extends y.TaggedError("HarnessOperationTimeoutError"){static{l(this,"HarnessOperationTimeoutError")}constructor(t,e){super({message:`${t} timed out after ${e}ms`,operation:t,timeoutMs:e}),this.code="HARNESS_OPERATION_TIMEOUT"}}export class HarnessConcurrencyOperationError extends y.TaggedError("HarnessConcurrencyOperationError"){static{l(this,"HarnessConcurrencyOperationError")}constructor(t,e){super({cause:e,component:t,message:`${t} operation failed`}),this.code="HARNESS_CONCURRENCY_OPERATION_FAILED"}}export class HarnessSerialGate{static{l(this,"HarnessSerialGate")}constructor(t,e){this.component=t,this.processRuntime=e,this.semaphore=v.makeUnsafe(1),this.state=c.makeUnsafe({closed:!1,drained:d.makeUnsafe(),pending:0})}async run(t,e={}){const r=c.modify(this.state,n=>n.closed?[{accepted:!1,error:new HarnessConcurrencyClosedError(this.component,n.closedReason)},n]:[{accepted:!0},{...n,pending:n.pending+1}]).pipe(s.flatMap(n=>n.accepted?s.void:s.fail(n.error))),i=E(this.component,t),u=b(s.acquireUseRelease(r,()=>this.semaphore.withPermit(e.uninterruptible?s.uninterruptible(i):i),()=>c.update(this.state,n=>{const a=n.pending-1;return a===0&&n.closed&&d.doneUnsafe(n.drained,s.void),{...n,pending:a}})),this.component);try{return await this.processRuntime.runEffect(u,{signal:e.signal})}catch(n){throw e.signal?.aborted?h(e.signal,`${this.component} operation aborted`):R(n)}}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>{if(r.closed)return[r.drained,r];const i={...r,closed:!0,closedReason:t};return i.pending===0&&d.doneUnsafe(i.drained,s.void),[i.drained,i]}));await this.processRuntime.runEffect(d.await(e))}closeEffect(t){return c.modify(this.state,e=>{if(e.closed)return[e.drained,e];const r={...e,closed:!0,closedReason:t};return r.pending===0&&d.doneUnsafe(r.drained,s.void),[r.drained,r]}).pipe(s.flatMap(d.await))}}export class HarnessStateCell{static{l(this,"HarnessStateCell")}constructor(t,e){this.processRuntime=t,this.state=c.makeUnsafe(e)}get current(){return c.getUnsafe(this.state)}set(t){return this.processRuntime.runEffect(c.set(this.state,t))}update(t){return this.processRuntime.runEffect(c.update(this.state,t))}}export class HarnessKeyedSerialGate{static{l(this,"HarnessKeyedSerialGate")}constructor(t,e){this.component=t,this.processRuntime=e,this.state=c.makeUnsafe({closed:!1,entries:new Map})}async run(t,e,r={}){const i=await this.processRuntime.runEffect(c.modify(this.state,n=>{if(n.closed)return[{entry:void 0,error:new HarnessConcurrencyClosedError(this.component,n.closedReason)},n];const a=n.entries.get(t),f=a===void 0?{drained:d.makeUnsafe(),pending:1,semaphore:v.makeUnsafe(1)}:{...a,pending:a.pending+1},m=new Map(n.entries);return m.set(t,f),[{entry:f},{...n,entries:m}]}));if(i.entry===void 0)throw i.error;const u=b(i.entry.semaphore.withPermit(E(this.component,e)).pipe(s.ensuring(c.update(this.state,n=>{const a=n.entries.get(t);if(a===void 0)return n;const f=new Map(n.entries);return a.pending===1?(d.doneUnsafe(a.drained,s.void),f.delete(t)):f.set(t,{...a,pending:a.pending-1}),{...n,entries:f}}))),this.component);try{return await this.processRuntime.runEffect(u,r)}catch(n){throw r.signal?.aborted?h(r.signal,`${this.component} operation aborted`):R(n)}}async waitForIdle(t,e={}){const r=c.getUnsafe(this.state).entries.get(t)?.drained;if(r!==void 0)try{await this.processRuntime.runEffect(d.await(r),e)}catch(i){throw e.signal?.aborted?h(e.signal,`${this.component} wait aborted`):i}}has(t){return c.getUnsafe(this.state).entries.has(t)}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>[[...r.entries.values()],{...r,closed:!0,closedReason:r.closed?r.closedReason:t}]));await Promise.allSettled(e.map(r=>this.processRuntime.runEffect(d.await(r.drained))))}closeEffect(t){return c.modify(this.state,e=>[[...e.entries.values()],{...e,closed:!0,closedReason:e.closed?e.closedReason:t}]).pipe(s.flatMap(e=>s.forEach(e,r=>d.await(r.drained),{concurrency:"unbounded",discard:!0})),s.andThen(c.update(this.state,e=>({...e,entries:new Map}))))}}export class HarnessSingleFlight{static{l(this,"HarnessSingleFlight")}constructor(t,e){this.component=t,this.processRuntime=e,this.state=c.makeUnsafe({closed:!1,flights:new Map})}async run(t,e,r={}){const i=await this.processRuntime.runEffect(c.modify(this.state,u=>{if(u.closed)return[{entry:void 0,error:new HarnessConcurrencyClosedError(this.component,u.closedReason),owner:!1},u];const n=u.flights.get(t);if(n!==void 0)return[{entry:n,owner:!1},u];const a={completed:d.makeUnsafe(),controller:new AbortController,result:d.makeUnsafe()},f=new Map(u.flights);return f.set(t,a),[{entry:a,owner:!0},{...u,flights:f}]}));if(i.entry===void 0)throw i.error;i.owner&&this.runOwner(t,i.entry,e,r.timeoutMs);try{return await this.processRuntime.runEffect(d.await(i.entry.result),{signal:r.signal})}catch(u){throw r.signal?.aborted?h(r.signal,r.abortMessage??`${this.component} wait aborted`):R(u)}}abortAll(t){const e=c.getUnsafe(this.state);for(const r of e.flights.values())r.controller.abort(t)}has(t){return c.getUnsafe(this.state).flights.has(t)}get activeCount(){return c.getUnsafe(this.state).flights.size}close(t){return this.closePromise??=this.closeInternal(t),this.closePromise}async closeInternal(t){const e=await this.processRuntime.runEffect(c.modify(this.state,r=>r.closed?[[...r.flights.values()],r]:[[...r.flights.values()],{...r,closed:!0,closedReason:t}]));for(const r of e)r.controller.abort(t);await Promise.allSettled(e.map(r=>this.processRuntime.runEffect(d.await(r.completed))))}closeEffect(t){return c.modify(this.state,e=>e.closed?[[...e.flights.values()],e]:[[...e.flights.values()],{...e,closed:!0,closedReason:t}]).pipe(s.tap(e=>s.sync(()=>{for(const r of e)r.controller.abort(t)})),s.flatMap(e=>s.forEach(e,r=>d.await(r.completed),{concurrency:"unbounded",discard:!0})),s.andThen(c.update(this.state,e=>({...e,flights:new Map}))))}async runOwner(t,e,r,i){let u=E(this.component,r);i!==void 0&&(u=withOperationTimeout(u,this.component,i)),u=b(u,this.component);try{const n=await this.processRuntime.runEffect(u,{signal:e.controller.signal});d.doneUnsafe(e.result,s.succeed(n))}catch(n){const a=e.controller.signal.aborted?new HarnessConcurrencyOperationError(this.component,h(e.controller.signal,`${this.component} owner aborted`)):n;d.doneUnsafe(e.result,a instanceof HarnessConcurrencyOperationError||a instanceof HarnessOperationTimeoutError?s.fail(a):s.die(a))}finally{await this.processRuntime.runEffect(c.update(this.state,n=>{if(n.flights.get(t)!==e)return n;const a=new Map(n.flights);return a.delete(t),{...n,flights:a}})).catch(()=>{}),d.doneUnsafe(e.completed,s.void)}}}export function policyDelay(o){return s.sleep(o)}l(policyDelay,"policyDelay");export function policyBackoff(o,t,e){return policyDelay(N(o,t,e))}l(policyBackoff,"policyBackoff");export function policyNow(){return C.currentTimeMillis}l(policyNow,"policyNow");export function withOperationTimeout(o,t,e){return o.pipe(s.timeout(e),s.catchTag("TimeoutError",()=>s.fail(new HarnessOperationTimeoutError(t,e))))}l(withOperationTimeout,"withOperationTimeout");export async function runPolicyDelay(o,t,e,r){try{await o.runEffect(policyDelay(t),{signal:e})}catch(i){throw e.aborted?h(e,r):i}}l(runPolicyDelay,"runPolicyDelay");export async function runPolicyBackoff(o,t,e,r,i,u){try{await o.runEffect(policyBackoff(t,e,r),{signal:i})}catch(n){throw i.aborted?h(i,u):n}}l(runPolicyBackoff,"runPolicyBackoff");export function createPolicyDeadline(o,t,e={}){if(!Number.isSafeInteger(t)||t<=0)throw new RangeError("Policy deadline must be a positive integer");const r=new AbortController,i=new AbortController,u=e.signals??[],n=AbortSignal.any([...u,r.signal]),a=[];let f=!1;const m=l(()=>{for(const[p,w]of a)p.removeEventListener("abort",w);a.length=0},"cleanup"),g=l(()=>{f||(f=!0,m(),i.abort(new Error("Policy deadline completed")))},"close");for(const p of u){if(p.aborted){g();break}const w=g;if(a.push([p,w]),p.addEventListener("abort",w,{once:!0}),p.aborted){g();break}}return f||o.runEffect(policyDelay(t),{signal:i.signal}).then(()=>{f||(f=!0,m(),r.abort(e.timeoutReason??new HarnessOperationTimeoutError("policy deadline",t)))}).catch(p=>{f||i.signal.aborted||(f=!0,m(),r.abort(p))}),Object.freeze({close:g,signal:n})}l(createPolicyDeadline,"createPolicyDeadline");function N(o,t,e){if(!Number.isSafeInteger(o)||o<=0||!Number.isSafeInteger(t)||t<=0||!Number.isSafeInteger(e)||e<=0)throw new RangeError("Policy backoff values must be positive integers");return Math.min(e,o*2**(t-1))}l(N,"policyBackoffDuration");function h(o,t){return o.reason??new Error(t)}l(h,"abortReason");function E(o,t){return s.tryPromise({catch:l(e=>new HarnessConcurrencyOperationError(o,e),"catch"),try:t})}l(E,"tryConcurrencyOperation");function R(o){return o instanceof HarnessConcurrencyOperationError?o.cause:o}l(R,"unwrapConcurrencyOperationError");function b(o,t){const e=P(t);if(e===void 0)return o;const r={component:e.component,operation:e.operation};return o.pipe(s.tap(()=>s.logInfo(e.eventName).pipe(s.annotateLogs({...r,outcome:"success"}))),s.tapError(()=>s.logWarning(e.eventName).pipe(s.annotateLogs({...r,outcome:"error"}))),s.withSpan(e.eventName,{attributes:r}))}l(b,"observeConcurrencyEffect");function P(o){switch(o){case"Auth ownership mutation":case"Authentication mutation":return{component:"auth",eventName:"harness.auth.mutation",operation:"update"};case"Authentication refresh":return{component:"auth",eventName:"harness.auth.refresh",operation:"refresh"};case"Product mutation":return{component:"product",eventName:"harness.product.mutation",operation:"update"};case"Workspace Product cleanup":return{component:"product",eventName:"harness.product.mutation",operation:"release"};case"Workspace Product resolution":return{component:"product",eventName:"harness.product.resolve",operation:"resolve"};default:return}}l(P,"concurrencyTelemetrySpec");
|
|
@@ -2,9 +2,13 @@ declare const harnessProcessRuntimeHandleBrand: unique symbol;
|
|
|
2
2
|
export interface HarnessConcurrencyRunOptions {
|
|
3
3
|
readonly signal?: AbortSignal;
|
|
4
4
|
}
|
|
5
|
+
export interface HarnessSerialGateRunOptions extends HarnessConcurrencyRunOptions {
|
|
6
|
+
/** Cancel queued admission, but join a started operation before releasing its permit. */
|
|
7
|
+
readonly uninterruptible?: boolean;
|
|
8
|
+
}
|
|
5
9
|
export interface HarnessSerialGateHandle {
|
|
6
10
|
close(reason: unknown): Promise<void>;
|
|
7
|
-
run<Value>(operation: (signal: AbortSignal) => Promise<Value>, options?:
|
|
11
|
+
run<Value>(operation: (signal: AbortSignal) => Promise<Value>, options?: HarnessSerialGateRunOptions): Promise<Value>;
|
|
8
12
|
}
|
|
9
13
|
export interface HarnessKeyedSerialGateHandle<Key> {
|
|
10
14
|
close(reason: unknown): Promise<void>;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { AnyWireMessage, UpdateSessionNotification } from '@agentclientprotocol/sdk/experimental/v2';
|
|
2
|
+
/**
|
|
3
|
+
* Keep CodeBuddy's Credit unit intact across the official SDK's
|
|
4
|
+
* lenient v2 parser. The SDK accepts only three uppercase currency characters
|
|
5
|
+
* and otherwise silently drops `cost`, so the transport substitutes a
|
|
6
|
+
* valid placeholder plus a reserved marker before the SDK sees the message.
|
|
7
|
+
*/
|
|
8
|
+
export declare function normalizeAcpV2CreditsForSdk(message: AnyWireMessage): AnyWireMessage;
|
|
9
|
+
/** Restore the product Credit unit and remove the private transport marker. */
|
|
10
|
+
export declare function restoreCodeBuddyCreditsFromSdk(notification: UpdateSessionNotification): UpdateSessionNotification;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
var s=Object.defineProperty;var d=(t,r)=>s(t,"name",{value:r,configurable:!0});import{isRecord as n}from"../internal/guards.js";const a="_codebuddy.ai/privateCreditCurrency",i="XCR";function p(t){if(!n(t))return{changed:!1,value:t};const r=n(t._meta)?t._meta:void 0,e=r?{...r}:void 0,o=e!==void 0&&Object.hasOwn(e,a);if(e&&delete e[a],t.currency!=="credits")return o?{changed:!0,value:{...t,...e&&Object.keys(e).length>0?{_meta:e}:{_meta:void 0}}}:{changed:!1,value:t};if(typeof t.amount!="number"||!Number.isFinite(t.amount)||t.amount<0)throw new Error("ACP peer emitted an invalid Credits cost amount");return{changed:!0,value:{...t,currency:i,_meta:{...e??{},[a]:"credits"}}}}d(p,"normalizedCostForSdk");function u(t){if(!("method"in t)||t.method!=="session/update"||!n(t.params)||!n(t.params.update)||t.params.update.sessionUpdate!=="usage_update")return t;const r=p(t.params.update.cost);return r.changed?{...t,params:{...t.params,update:{...t.params.update,cost:r.value}}}:t}d(u,"normalizeCreditsNotificationForSdk");export function normalizeAcpV2CreditsForSdk(t){return Array.isArray(t)?t.map(r=>u(r)):u(t)}d(normalizeAcpV2CreditsForSdk,"normalizeAcpV2CreditsForSdk");export function restoreCodeBuddyCreditsFromSdk(t){const r=t.update,e=r.cost;if(r.sessionUpdate!=="usage_update"||!n(e))return t;const o=n(e._meta)?e._meta:void 0;if(e.currency!==i||o?.[a]!=="credits")return t;const c={...o};return delete c[a],{...t,update:{...r,cost:{...e,currency:"credits",...Object.keys(c).length>0?{_meta:c}:{_meta:void 0}}}}}d(restoreCodeBuddyCreditsFromSdk,"restoreCodeBuddyCreditsFromSdk");
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { AnyWireMessage, Stream
|
|
1
|
+
import type { AnyWireMessage, Stream } from '@agentclientprotocol/sdk/experimental/v2' with { 'resolution-mode': 'import' };
|
|
2
2
|
import { AGENT_HARNESS_PRIVATE_COMPACT_METHOD } from '../session/compact.js';
|
|
3
3
|
import type { AcpV2SdkModule } from './acp-v2.js';
|
|
4
4
|
export declare const AGENT_HARNESS_PRIVATE_AUTH_METHODS: Readonly<{
|
|
@@ -10,15 +10,6 @@ export interface ProtocolNeutralJsonRpcStream {
|
|
|
10
10
|
readonly readable: ReadableStream<unknown>;
|
|
11
11
|
readonly writable: WritableStream<unknown>;
|
|
12
12
|
}
|
|
13
|
-
/**
|
|
14
|
-
* Keep CodeBuddy's private Credit unit intact across the official SDK's
|
|
15
|
-
* lenient v2 parser. The SDK accepts only three uppercase currency characters
|
|
16
|
-
* and otherwise silently drops `cost`, so the private transport substitutes a
|
|
17
|
-
* valid placeholder plus a reserved marker before the SDK sees the message.
|
|
18
|
-
*/
|
|
19
|
-
export declare function normalizePrivateAcpV2WireMessageForSdk(message: AnyWireMessage): AnyWireMessage;
|
|
20
|
-
/** Restore the product Credit unit and remove the private transport marker. */
|
|
21
|
-
export declare function restoreCodeBuddyCreditsFromSdk(notification: UpdateSessionNotification): UpdateSessionNotification;
|
|
22
13
|
/**
|
|
23
14
|
* Exact ACP v2 registry used between Agent Harness and its private CodeBuddy
|
|
24
15
|
* child. Keeping this object narrower than the SDK-wide method unions prevents
|
|
@@ -220,7 +220,9 @@ export declare class CodeBuddyAuthRuntime implements AuthProtocolBackend {
|
|
|
220
220
|
* tail makes either the old pair or the new pair observable, never the
|
|
221
221
|
* private midpoint.
|
|
222
222
|
*/
|
|
223
|
-
runConsistentRead<Value>(operation: () => Value | PromiseLike<Value
|
|
223
|
+
runConsistentRead<Value>(operation: () => Value | PromiseLike<Value>, options?: {
|
|
224
|
+
readonly signal?: AbortSignal;
|
|
225
|
+
}): Promise<Value>;
|
|
224
226
|
listAuthMethods(_params: AgentHarnessInitializeParams, _context: AgentHarnessHandlerContext): Promise<readonly AcpV2AuthMethod[]>;
|
|
225
227
|
login(params: AcpV2LoginAuthRequest, context: AgentHarnessHandlerContext): Promise<AcpV2LoginAuthResponse>;
|
|
226
228
|
logout(_params: AcpV2LogoutAuthRequest, context: AgentHarnessHandlerContext): Promise<AcpV2LogoutAuthResponse>;
|
|
@@ -238,8 +240,8 @@ export declare class CodeBuddyAuthRuntime implements AuthProtocolBackend {
|
|
|
238
240
|
* Installs or clears one workspace execution Product for the current
|
|
239
241
|
* Account binding. The outer Auth protocol mutation gate keeps
|
|
240
242
|
* owner detach and public Account/Product replacement behind this
|
|
241
|
-
* operation
|
|
242
|
-
*
|
|
243
|
+
* operation. Preparation is cancellable; once started, the atomic commit
|
|
244
|
+
* finishes before releasing that gate, even if the carrier disconnects.
|
|
243
245
|
*/
|
|
244
246
|
provisionWorkspaceProduct(params: ProductWorkspaceProvisionParams, context: AgentHarnessHandlerContext): Promise<ProductWorkspaceProvisionResponse>;
|
|
245
247
|
detachExternalAccount(context: AgentHarnessHandlerContext, _reason: unknown): Promise<boolean>;
|