@assemblyline-agents/runtime 1.0.0 → 3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/dist/a2a-client.d.ts +22 -0
- package/dist/a2a-client.d.ts.map +1 -0
- package/dist/a2a-client.js +211 -0
- package/dist/a2a-client.js.map +1 -0
- package/dist/agent-capability-snapshot.d.ts +32 -0
- package/dist/agent-capability-snapshot.d.ts.map +1 -0
- package/dist/agent-capability-snapshot.js +77 -0
- package/dist/agent-capability-snapshot.js.map +1 -0
- package/dist/agent-event-handlers.d.ts +21 -0
- package/dist/agent-event-handlers.d.ts.map +1 -0
- package/dist/agent-event-handlers.js +64 -0
- package/dist/agent-event-handlers.js.map +1 -0
- package/dist/agent-hook-context.d.ts +8 -0
- package/dist/agent-hook-context.d.ts.map +1 -0
- package/dist/agent-hook-context.js +29 -0
- package/dist/agent-hook-context.js.map +1 -0
- package/dist/agent-hook-evaluation.d.ts +61 -0
- package/dist/agent-hook-evaluation.d.ts.map +1 -0
- package/dist/agent-hook-evaluation.js +197 -0
- package/dist/agent-hook-evaluation.js.map +1 -0
- package/dist/agent-hook-run-lifecycle.d.ts +44 -0
- package/dist/agent-hook-run-lifecycle.d.ts.map +1 -0
- package/dist/agent-hook-run-lifecycle.js +76 -0
- package/dist/agent-hook-run-lifecycle.js.map +1 -0
- package/dist/agent-state.d.ts +31 -0
- package/dist/agent-state.d.ts.map +1 -0
- package/dist/agent-state.js +80 -0
- package/dist/agent-state.js.map +1 -0
- package/dist/agent-surface.d.ts +32 -0
- package/dist/agent-surface.d.ts.map +1 -0
- package/dist/agent-surface.js +85 -0
- package/dist/agent-surface.js.map +1 -0
- package/dist/attachments.d.ts +5 -1
- package/dist/attachments.d.ts.map +1 -1
- package/dist/attachments.js +58 -32
- package/dist/attachments.js.map +1 -1
- package/dist/audience.d.ts +30 -0
- package/dist/audience.d.ts.map +1 -0
- package/dist/audience.js +68 -0
- package/dist/audience.js.map +1 -0
- package/dist/authored-hooks.d.ts +6 -0
- package/dist/authored-hooks.d.ts.map +1 -0
- package/dist/authored-hooks.js +17 -0
- package/dist/authored-hooks.js.map +1 -0
- package/dist/automation-event-match.d.ts +8 -0
- package/dist/automation-event-match.d.ts.map +1 -0
- package/dist/automation-event-match.js +25 -0
- package/dist/automation-event-match.js.map +1 -0
- package/dist/background-review-trigger.d.ts +9 -0
- package/dist/background-review-trigger.d.ts.map +1 -0
- package/dist/background-review-trigger.js +72 -0
- package/dist/background-review-trigger.js.map +1 -0
- package/dist/background-review-types.d.ts +60 -0
- package/dist/background-review-types.d.ts.map +1 -0
- package/dist/background-review-types.js +2 -0
- package/dist/background-review-types.js.map +1 -0
- package/dist/background-review-worker.d.ts +14 -0
- package/dist/background-review-worker.d.ts.map +1 -0
- package/dist/background-review-worker.js +61 -0
- package/dist/background-review-worker.js.map +1 -0
- package/dist/background-review.d.ts +5 -0
- package/dist/background-review.d.ts.map +1 -0
- package/dist/background-review.js +332 -0
- package/dist/background-review.js.map +1 -0
- package/dist/builtin-tool-executors.d.ts +50 -27
- package/dist/builtin-tool-executors.d.ts.map +1 -1
- package/dist/builtin-tool-executors.js +332 -124
- package/dist/builtin-tool-executors.js.map +1 -1
- package/dist/builtin-tools.d.ts +16 -9
- package/dist/builtin-tools.d.ts.map +1 -1
- package/dist/builtin-tools.js +308 -116
- package/dist/builtin-tools.js.map +1 -1
- package/dist/capability-catalog.d.ts +3 -2
- package/dist/capability-catalog.d.ts.map +1 -1
- package/dist/capability-catalog.js +12 -7
- package/dist/capability-catalog.js.map +1 -1
- package/dist/capability-inspection.d.ts +31 -0
- package/dist/capability-inspection.d.ts.map +1 -0
- package/dist/capability-inspection.js +58 -0
- package/dist/capability-inspection.js.map +1 -0
- package/dist/channel-http-util.d.ts.map +1 -1
- package/dist/channel-http-util.js +6 -5
- package/dist/channel-http-util.js.map +1 -1
- package/dist/channel-ingress.d.ts +16 -1
- package/dist/channel-ingress.d.ts.map +1 -1
- package/dist/channel-ingress.js +152 -14
- package/dist/channel-ingress.js.map +1 -1
- package/dist/channel.d.ts +73 -3
- package/dist/channel.d.ts.map +1 -1
- package/dist/checkpoints.d.ts +1 -1
- package/dist/checkpoints.d.ts.map +1 -1
- package/dist/checkpoints.js +6 -6
- package/dist/checkpoints.js.map +1 -1
- package/dist/child-process-env.d.ts +7 -0
- package/dist/child-process-env.d.ts.map +1 -0
- package/dist/child-process-env.js +41 -0
- package/dist/child-process-env.js.map +1 -0
- package/dist/computer-relay-protocol.d.ts.map +1 -1
- package/dist/computer-relay-protocol.js +4 -4
- package/dist/computer-relay-protocol.js.map +1 -1
- package/dist/concurrency.d.ts +1 -1
- package/dist/concurrency.js +1 -1
- package/dist/connection-auth-util.d.ts +1 -0
- package/dist/connection-auth-util.d.ts.map +1 -1
- package/dist/connection-auth-util.js +3 -1
- package/dist/connection-auth-util.js.map +1 -1
- package/dist/connection-clients.d.ts +11 -3
- package/dist/connection-clients.d.ts.map +1 -1
- package/dist/connection-clients.js +71 -8
- package/dist/connection-clients.js.map +1 -1
- package/dist/connection-event-store.d.ts +98 -0
- package/dist/connection-event-store.d.ts.map +1 -0
- package/dist/connection-event-store.js +162 -0
- package/dist/connection-event-store.js.map +1 -0
- package/dist/connection-events.d.ts +51 -0
- package/dist/connection-events.d.ts.map +1 -0
- package/dist/connection-events.js +343 -0
- package/dist/connection-events.js.map +1 -0
- package/dist/connection-stores.d.ts +6 -0
- package/dist/connection-stores.d.ts.map +1 -1
- package/dist/connection-stores.js +20 -1
- package/dist/connection-stores.js.map +1 -1
- package/dist/connection-util.d.ts +3 -2
- package/dist/connection-util.d.ts.map +1 -1
- package/dist/connection-util.js +18 -1
- package/dist/connection-util.js.map +1 -1
- package/dist/connections.d.ts +60 -5
- package/dist/connections.d.ts.map +1 -1
- package/dist/connections.js +390 -57
- package/dist/connections.js.map +1 -1
- package/dist/context-policy-util.d.ts.map +1 -1
- package/dist/context-policy-util.js +1 -3
- package/dist/context-policy-util.js.map +1 -1
- package/dist/conversation-context.d.ts +9 -4
- package/dist/conversation-context.d.ts.map +1 -1
- package/dist/conversation-context.js +65 -19
- package/dist/conversation-context.js.map +1 -1
- package/dist/conversation-transcript.d.ts +8 -5
- package/dist/conversation-transcript.d.ts.map +1 -1
- package/dist/conversation-transcript.js +24 -5
- package/dist/conversation-transcript.js.map +1 -1
- package/dist/conversation-turn-coalescing.d.ts +22 -0
- package/dist/conversation-turn-coalescing.d.ts.map +1 -0
- package/dist/conversation-turn-coalescing.js +121 -0
- package/dist/conversation-turn-coalescing.js.map +1 -0
- package/dist/conversation-turn-dispatch.d.ts +5 -2
- package/dist/conversation-turn-dispatch.d.ts.map +1 -1
- package/dist/conversation-turn-dispatch.js +59 -22
- package/dist/conversation-turn-dispatch.js.map +1 -1
- package/dist/default-outbound-route.d.ts +29 -0
- package/dist/default-outbound-route.d.ts.map +1 -0
- package/dist/default-outbound-route.js +105 -0
- package/dist/default-outbound-route.js.map +1 -0
- package/dist/delivery-artifacts.d.ts +2 -0
- package/dist/delivery-artifacts.d.ts.map +1 -0
- package/dist/delivery-artifacts.js +34 -0
- package/dist/delivery-artifacts.js.map +1 -0
- package/dist/delivery-files.d.ts +5 -0
- package/dist/delivery-files.d.ts.map +1 -0
- package/dist/delivery-files.js +33 -0
- package/dist/delivery-files.js.map +1 -0
- package/dist/delivery-queue.d.ts +21 -1
- package/dist/delivery-queue.d.ts.map +1 -1
- package/dist/delivery-queue.js +144 -1
- package/dist/delivery-queue.js.map +1 -1
- package/dist/delivery-send.d.ts +2 -2
- package/dist/delivery-send.d.ts.map +1 -1
- package/dist/delivery-send.js +256 -100
- package/dist/delivery-send.js.map +1 -1
- package/dist/durable-files.d.ts +37 -0
- package/dist/durable-files.d.ts.map +1 -0
- package/dist/durable-files.js +63 -0
- package/dist/durable-files.js.map +1 -0
- package/dist/harness-loop.d.ts +18 -9
- package/dist/harness-loop.d.ts.map +1 -1
- package/dist/harness-loop.js +245 -50
- package/dist/harness-loop.js.map +1 -1
- package/dist/heic-transcode-worker.d.ts +2 -0
- package/dist/heic-transcode-worker.d.ts.map +1 -0
- package/dist/heic-transcode-worker.js +59 -0
- package/dist/heic-transcode-worker.js.map +1 -0
- package/dist/heic-transcode.d.ts +18 -0
- package/dist/heic-transcode.d.ts.map +1 -0
- package/dist/heic-transcode.js +99 -0
- package/dist/heic-transcode.js.map +1 -0
- package/dist/human-input-routing.d.ts +22 -0
- package/dist/human-input-routing.d.ts.map +1 -0
- package/dist/human-input-routing.js +26 -0
- package/dist/human-input-routing.js.map +1 -0
- package/dist/in-memory-agent-state-store.d.ts +21 -0
- package/dist/in-memory-agent-state-store.d.ts.map +1 -0
- package/dist/in-memory-agent-state-store.js +97 -0
- package/dist/in-memory-agent-state-store.js.map +1 -0
- package/dist/in-memory-conversation-turn-store.d.ts +3 -1
- package/dist/in-memory-conversation-turn-store.d.ts.map +1 -1
- package/dist/in-memory-conversation-turn-store.js +41 -2
- package/dist/in-memory-conversation-turn-store.js.map +1 -1
- package/dist/in-memory-run-store.d.ts +8 -0
- package/dist/in-memory-run-store.d.ts.map +1 -1
- package/dist/in-memory-run-store.js +28 -5
- package/dist/in-memory-run-store.js.map +1 -1
- package/dist/in-memory-sandbox-session-store.d.ts +2 -1
- package/dist/in-memory-sandbox-session-store.d.ts.map +1 -1
- package/dist/in-memory-sandbox-session-store.js +65 -1
- package/dist/in-memory-sandbox-session-store.js.map +1 -1
- package/dist/in-memory-small-stores.d.ts +18 -1
- package/dist/in-memory-small-stores.d.ts.map +1 -1
- package/dist/in-memory-small-stores.js +107 -1
- package/dist/in-memory-small-stores.js.map +1 -1
- package/dist/in-memory-workspace-store.d.ts +40 -0
- package/dist/in-memory-workspace-store.d.ts.map +1 -0
- package/dist/in-memory-workspace-store.js +370 -0
- package/dist/in-memory-workspace-store.js.map +1 -0
- package/dist/index.d.ts +116 -45
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +637 -566
- package/dist/index.js.map +1 -1
- package/dist/json-util.d.ts +8 -0
- package/dist/json-util.d.ts.map +1 -1
- package/dist/json-util.js +8 -0
- package/dist/json-util.js.map +1 -1
- package/dist/learning-store.d.ts +111 -0
- package/dist/learning-store.d.ts.map +1 -0
- package/dist/learning-store.js +193 -0
- package/dist/learning-store.js.map +1 -0
- package/dist/local-sandbox.d.ts +3 -2
- package/dist/local-sandbox.d.ts.map +1 -1
- package/dist/local-sandbox.js +69 -25
- package/dist/local-sandbox.js.map +1 -1
- package/dist/mcp-client.d.ts.map +1 -1
- package/dist/mcp-client.js +3 -2
- package/dist/mcp-client.js.map +1 -1
- package/dist/media-processor.d.ts +42 -0
- package/dist/media-processor.d.ts.map +1 -0
- package/dist/media-processor.js +2 -0
- package/dist/media-processor.js.map +1 -0
- package/dist/model-media.d.ts +13 -1
- package/dist/model-media.d.ts.map +1 -1
- package/dist/model-media.js +81 -18
- package/dist/model-media.js.map +1 -1
- package/dist/model-visible-interrupts.d.ts +10 -0
- package/dist/model-visible-interrupts.d.ts.map +1 -0
- package/dist/model-visible-interrupts.js +41 -0
- package/dist/model-visible-interrupts.js.map +1 -0
- package/dist/operator-controls.d.ts.map +1 -1
- package/dist/operator-controls.js +16 -3
- package/dist/operator-controls.js.map +1 -1
- package/dist/outbound-http-policy.d.ts +7 -0
- package/dist/outbound-http-policy.d.ts.map +1 -0
- package/dist/outbound-http-policy.js +155 -0
- package/dist/outbound-http-policy.js.map +1 -0
- package/dist/principals.d.ts +18 -0
- package/dist/principals.d.ts.map +1 -0
- package/dist/principals.js +90 -0
- package/dist/principals.js.map +1 -0
- package/dist/public-api.d.ts +21 -0
- package/dist/public-api.d.ts.map +1 -0
- package/dist/public-api.js +19 -0
- package/dist/public-api.js.map +1 -0
- package/dist/replay-resume.d.ts +15 -3
- package/dist/replay-resume.d.ts.map +1 -1
- package/dist/replay-resume.js +256 -24
- package/dist/replay-resume.js.map +1 -1
- package/dist/resource-projection-util.d.ts +1 -1
- package/dist/resource-projection-util.d.ts.map +1 -1
- package/dist/resource-projection-util.js +21 -10
- package/dist/resource-projection-util.js.map +1 -1
- package/dist/resource-projection.d.ts +8 -1
- package/dist/resource-projection.d.ts.map +1 -1
- package/dist/resource-projection.js +230 -26
- package/dist/resource-projection.js.map +1 -1
- package/dist/run-heartbeat.d.ts +12 -2
- package/dist/run-heartbeat.d.ts.map +1 -1
- package/dist/run-heartbeat.js +31 -4
- package/dist/run-heartbeat.js.map +1 -1
- package/dist/run-outcome.d.ts +9 -5
- package/dist/run-outcome.d.ts.map +1 -1
- package/dist/run-outcome.js +16 -5
- package/dist/run-outcome.js.map +1 -1
- package/dist/run-recovery.d.ts +31 -2
- package/dist/run-recovery.d.ts.map +1 -1
- package/dist/run-recovery.js +211 -32
- package/dist/run-recovery.js.map +1 -1
- package/dist/run-replay.d.ts +35 -0
- package/dist/run-replay.d.ts.map +1 -0
- package/dist/run-replay.js +193 -0
- package/dist/run-replay.js.map +1 -0
- package/dist/run-result.d.ts +4 -0
- package/dist/run-result.d.ts.map +1 -0
- package/dist/run-result.js +18 -0
- package/dist/run-result.js.map +1 -0
- package/dist/run-timeline-query.d.ts +38 -0
- package/dist/run-timeline-query.d.ts.map +1 -0
- package/dist/run-timeline-query.js +99 -0
- package/dist/run-timeline-query.js.map +1 -0
- package/dist/runs-query.d.ts.map +1 -1
- package/dist/runs-query.js +12 -4
- package/dist/runs-query.js.map +1 -1
- package/dist/runtime-bundle.d.ts.map +1 -1
- package/dist/runtime-bundle.js +2 -0
- package/dist/runtime-bundle.js.map +1 -1
- package/dist/runtime-learning.d.ts +88 -0
- package/dist/runtime-learning.d.ts.map +1 -0
- package/dist/runtime-learning.js +260 -0
- package/dist/runtime-learning.js.map +1 -0
- package/dist/runtime-types.d.ts +79 -10
- package/dist/runtime-types.d.ts.map +1 -1
- package/dist/sandbox-fs.d.ts +9 -5
- package/dist/sandbox-fs.d.ts.map +1 -1
- package/dist/sandbox-fs.js +50 -33
- package/dist/sandbox-fs.js.map +1 -1
- package/dist/sandbox-handle.d.ts +25 -0
- package/dist/sandbox-handle.d.ts.map +1 -0
- package/dist/sandbox-handle.js +120 -0
- package/dist/sandbox-handle.js.map +1 -0
- package/dist/sandbox-session-identity.d.ts +14 -0
- package/dist/sandbox-session-identity.d.ts.map +1 -0
- package/dist/sandbox-session-identity.js +33 -0
- package/dist/sandbox-session-identity.js.map +1 -0
- package/dist/sandbox-session-key.d.ts.map +1 -1
- package/dist/sandbox-session-key.js +14 -10
- package/dist/sandbox-session-key.js.map +1 -1
- package/dist/sandbox-session-lifecycle.d.ts +12 -0
- package/dist/sandbox-session-lifecycle.d.ts.map +1 -0
- package/dist/sandbox-session-lifecycle.js +261 -0
- package/dist/sandbox-session-lifecycle.js.map +1 -0
- package/dist/sandbox-snapshot-policy.js +3 -3
- package/dist/sandbox-snapshot-policy.js.map +1 -1
- package/dist/sandbox-state-sync.d.ts +22 -0
- package/dist/sandbox-state-sync.d.ts.map +1 -0
- package/dist/sandbox-state-sync.js +147 -0
- package/dist/sandbox-state-sync.js.map +1 -0
- package/dist/sandbox-sync-worker.d.ts +11 -2
- package/dist/sandbox-sync-worker.d.ts.map +1 -1
- package/dist/sandbox-sync-worker.js +143 -31
- package/dist/sandbox-sync-worker.js.map +1 -1
- package/dist/schedule-execution.d.ts.map +1 -1
- package/dist/schedule-execution.js +187 -57
- package/dist/schedule-execution.js.map +1 -1
- package/dist/sdk-api-client.d.ts +17 -0
- package/dist/sdk-api-client.d.ts.map +1 -0
- package/dist/sdk-api-client.js +55 -0
- package/dist/sdk-api-client.js.map +1 -0
- package/dist/security.js +2 -2
- package/dist/security.js.map +1 -1
- package/dist/self-improvement.d.ts +34 -6
- package/dist/self-improvement.d.ts.map +1 -1
- package/dist/self-improvement.js +140 -34
- package/dist/self-improvement.js.map +1 -1
- package/dist/skill-bundles.d.ts +55 -0
- package/dist/skill-bundles.d.ts.map +1 -0
- package/dist/skill-bundles.js +134 -0
- package/dist/skill-bundles.js.map +1 -0
- package/dist/source-loader.d.ts +8 -0
- package/dist/source-loader.d.ts.map +1 -1
- package/dist/source-loader.js +41 -10
- package/dist/source-loader.js.map +1 -1
- package/dist/state-store-helpers.d.ts +2 -0
- package/dist/state-store-helpers.d.ts.map +1 -1
- package/dist/state-store-helpers.js +11 -1
- package/dist/state-store-helpers.js.map +1 -1
- package/dist/state-stores.d.ts +2 -0
- package/dist/state-stores.d.ts.map +1 -1
- package/dist/state-stores.js +40 -7
- package/dist/state-stores.js.map +1 -1
- package/dist/state.d.ts +344 -5
- package/dist/state.d.ts.map +1 -1
- package/dist/state.js +44 -2
- package/dist/state.js.map +1 -1
- package/dist/storage.d.ts +59 -2
- package/dist/storage.d.ts.map +1 -1
- package/dist/storage.js +183 -6
- package/dist/storage.js.map +1 -1
- package/dist/subagent-execution.d.ts +7 -6
- package/dist/subagent-execution.d.ts.map +1 -1
- package/dist/subagent-execution.js +58 -19
- package/dist/subagent-execution.js.map +1 -1
- package/dist/target-instructions.d.ts +14 -0
- package/dist/target-instructions.d.ts.map +1 -0
- package/dist/target-instructions.js +18 -0
- package/dist/target-instructions.js.map +1 -0
- package/dist/tool-apis.d.ts.map +1 -1
- package/dist/tool-apis.js +55 -10
- package/dist/tool-apis.js.map +1 -1
- package/dist/tool-execution.d.ts +26 -13
- package/dist/tool-execution.d.ts.map +1 -1
- package/dist/tool-execution.js +368 -239
- package/dist/tool-execution.js.map +1 -1
- package/dist/turn-media.d.ts +29 -0
- package/dist/turn-media.d.ts.map +1 -0
- package/dist/turn-media.js +233 -0
- package/dist/turn-media.js.map +1 -0
- package/dist/usage-reconciliation.d.ts +1 -1
- package/dist/usage-reconciliation.js +1 -1
- package/dist/workspace-id.d.ts +10 -0
- package/dist/workspace-id.d.ts.map +1 -0
- package/dist/workspace-id.js +55 -0
- package/dist/workspace-id.js.map +1 -0
- package/dist/workspace-manifest.d.ts +24 -0
- package/dist/workspace-manifest.d.ts.map +1 -0
- package/dist/workspace-manifest.js +111 -0
- package/dist/workspace-manifest.js.map +1 -0
- package/dist/workspace-operation-limiter.d.ts +16 -0
- package/dist/workspace-operation-limiter.d.ts.map +1 -0
- package/dist/workspace-operation-limiter.js +31 -0
- package/dist/workspace-operation-limiter.js.map +1 -0
- package/dist/workspace-operations.d.ts +145 -0
- package/dist/workspace-operations.d.ts.map +1 -0
- package/dist/workspace-operations.js +420 -0
- package/dist/workspace-operations.js.map +1 -0
- package/dist/workspace-runtime.d.ts +110 -0
- package/dist/workspace-runtime.d.ts.map +1 -0
- package/dist/workspace-runtime.js +240 -0
- package/dist/workspace-runtime.js.map +1 -0
- package/dist/workspace-search.d.ts +55 -0
- package/dist/workspace-search.d.ts.map +1 -0
- package/dist/workspace-search.js +262 -0
- package/dist/workspace-search.js.map +1 -0
- package/dist/workspace-service.d.ts +173 -0
- package/dist/workspace-service.d.ts.map +1 -0
- package/dist/workspace-service.js +619 -0
- package/dist/workspace-service.js.map +1 -0
- package/dist/workspace.d.ts +7 -0
- package/dist/workspace.d.ts.map +1 -0
- package/dist/workspace.js +7 -0
- package/dist/workspace.js.map +1 -0
- package/package.json +7 -4
- package/dist/agent-harness.d.ts +0 -108
- package/dist/agent-harness.d.ts.map +0 -1
- package/dist/agent-harness.js +0 -2
- package/dist/agent-harness.js.map +0 -1
- package/dist/attachments-legacy.d.ts +0 -17
- package/dist/attachments-legacy.d.ts.map +0 -1
- package/dist/attachments-legacy.js +0 -273
- package/dist/attachments-legacy.js.map +0 -1
- package/dist/code-mode.d.ts +0 -20
- package/dist/code-mode.d.ts.map +0 -1
- package/dist/code-mode.js +0 -658
- package/dist/code-mode.js.map +0 -1
- package/dist/hook-dispatch.d.ts +0 -19
- package/dist/hook-dispatch.d.ts.map +0 -1
- package/dist/hook-dispatch.js +0 -37
- package/dist/hook-dispatch.js.map +0 -1
- package/dist/pi-agent-harness.d.ts +0 -40
- package/dist/pi-agent-harness.d.ts.map +0 -1
- package/dist/pi-agent-harness.js +0 -222
- package/dist/pi-agent-harness.js.map +0 -1
- package/dist/pi-harness.d.ts +0 -42
- package/dist/pi-harness.d.ts.map +0 -1
- package/dist/pi-harness.js +0 -142
- package/dist/pi-harness.js.map +0 -1
- package/dist/run-resolver.d.ts +0 -35
- package/dist/run-resolver.d.ts.map +0 -1
- package/dist/run-resolver.js +0 -84
- package/dist/run-resolver.js.map +0 -1
- package/dist/usage-budget.d.ts +0 -29
- package/dist/usage-budget.d.ts.map +0 -1
- package/dist/usage-budget.js +0 -145
- package/dist/usage-budget.js.map +0 -1
package/dist/index.js
CHANGED
|
@@ -1,91 +1,109 @@
|
|
|
1
1
|
import { createHash } from "node:crypto";
|
|
2
2
|
import { join, resolve } from "node:path";
|
|
3
3
|
import { builtInToolDefinition } from "./builtin-tools.js";
|
|
4
|
-
export
|
|
5
|
-
|
|
4
|
+
export * from "./public-api.js";
|
|
5
|
+
export { builtInToolDefaults, FILES_MOUNT_TOOL_NAME, FILES_SEARCH_TOOL_NAME, HISTORY_SEARCH_TOOL_NAME, PAIR_TOOL_NAME } from "./builtin-tools.js";
|
|
6
|
+
export { inspectAgentCapabilities } from "./capability-inspection.js";
|
|
7
|
+
export { CONNECTION_PAIRING_UNAVAILABLE_EVENT, executePairTool } from "./builtin-tool-executors.js";
|
|
6
8
|
import { resolveEvalToolStub, validateEvalRunOptions } from "./eval-run-options.js";
|
|
7
|
-
import {
|
|
9
|
+
import { rememberDefaultOutboundRoute } from "./default-outbound-route.js";
|
|
10
|
+
import { audienceFromRun, audienceUserKey, normalizeAgentAudience } from "./audience.js";
|
|
8
11
|
import { AgentSourceModuleLoader } from "./source-loader.js";
|
|
12
|
+
import { AgentEventHandlerRegistry } from "./agent-event-handlers.js";
|
|
13
|
+
import { immutableAgentRunContext } from "./agent-hook-evaluation.js";
|
|
14
|
+
import { hookCapabilityCatalog } from "./agent-hook-context.js";
|
|
15
|
+
import { flattenSubagents, rootAgentSurface, subagentSurface, surfaceForPath, surfaceForRun, durableAgentSurfaceScope } from "./agent-surface.js";
|
|
16
|
+
import { createRuntimeAgentHookController, recoverAgentHookController, removeTerminalAgentHookState, resolvedInstructionsForRun as resolvedHookInstructionsForRun } from "./agent-hook-run-lifecycle.js";
|
|
9
17
|
import { compiledChannelProvider, providerIngressSecurityError, providerIngressSecurityWarnings, resolveCoreToolPolicy, trustedAttachmentProviderForTurn } from "./security.js";
|
|
10
18
|
export { constantTimeSecretEqual } from "./security.js";
|
|
11
19
|
export { RUN_STREAM_TERMINAL_EVENTS } from "./run-stream.js";
|
|
12
20
|
export { failRun } from "./run-outcome.js";
|
|
13
|
-
|
|
21
|
+
export { MAX_CHANNEL_TURN_COALESCING_WINDOW_MS, QUEUED_CHANNEL_TURN_COALESCING_KEY, QUEUED_CHANNEL_TURN_KEY, QUEUED_CHANNEL_TURN_MERGED_INTO_KEY, QUEUED_CHANNEL_TURN_PARTS_KEY } from "./conversation-turn-coalescing.js";
|
|
22
|
+
import { ARTIFACT_DIR_NAME, ASSEMBLY_LINE_MANIFEST_SCHEMA_VERSION } from "@assemblyline-agents/core";
|
|
14
23
|
import { resolveBooleanEnv, resolveNonNegativeIntegerEnv, resolvePositiveIntegerEnv } from "./env-config.js";
|
|
24
|
+
import { humanInputModeForChannel, withHumanInputMode } from "./human-input-routing.js";
|
|
15
25
|
import { RunEventBus, withRunEventPublishing } from "./run-stream.js";
|
|
16
|
-
import { handleRunExecutionError, logTerminalRunEvent, settleCompletionBoundaryControlImpl } from "./run-outcome.js";
|
|
17
|
-
import { registerRunAbortController, startRunHeartbeatImpl } from "./run-heartbeat.js";
|
|
26
|
+
import { failRun as failRunImpl, handleRunExecutionError, logTerminalRunEvent, settleCompletionBoundaryControlImpl } from "./run-outcome.js";
|
|
27
|
+
import { cacheRunControlSignal, registerRunAbortController, startRunHeartbeatImpl, trackActiveRunHeartbeat } from "./run-heartbeat.js";
|
|
18
28
|
import { redactTruncateJson } from "./content-capture.js";
|
|
29
|
+
import { isJsonObject, safeJson } from "./json-util.js";
|
|
19
30
|
import { sandboxSessionKeyForRun } from "./sandbox-session-key.js";
|
|
20
31
|
export { sandboxSessionKeyForRun } from "./sandbox-session-key.js";
|
|
21
|
-
import {
|
|
22
|
-
import {
|
|
32
|
+
import { conversationInitiator, defaultUserPrincipal, initiatorFromRun, normalizeAgentPrincipal, principalFromRun, principalUserId } from "./principals.js";
|
|
33
|
+
import { InMemoryConnectionEventStore } from "./connection-event-store.js";
|
|
34
|
+
import { acceptConnectionEvent, checkConnectionEvents, drainConnectionEventInbox, reconcileConnectionEvents } from "./connection-events.js";
|
|
35
|
+
import { InMemoryConnectionAuthorizationSessionStore, InMemoryConnectionGrantStore, RuntimeConnectionRegistry } from "./connections.js";
|
|
36
|
+
export { FileConnectionEventStore, InMemoryConnectionEventStore } from "./connection-event-store.js";
|
|
37
|
+
export { connectionEventUrl } from "./connection-events.js";
|
|
38
|
+
import { InMemoryConnectionDefinitionStore, InMemoryScheduleStore, InMemorySkillStore, compiledConnectionFromStored, isHostAllowed, resolveSkillsConfig, resolveSchedulesConfig, resolveConnectionsConfig } from "./self-improvement.js";
|
|
39
|
+
import { InMemoryLearningStore } from "./learning-store.js";
|
|
40
|
+
import { RuntimeLearningManager } from "./runtime-learning.js";
|
|
23
41
|
import { materializeTurnAttachments } from "./attachments.js";
|
|
24
|
-
|
|
42
|
+
import { mergeJsonObjects, processRuntimeTurnMedia } from "./turn-media.js";
|
|
43
|
+
export { mergeJsonObjects, processTurnMedia } from "./turn-media.js";
|
|
25
44
|
export { attachmentFetchTimeoutMs, attachmentRemoteUrl, attachmentTrustedForProvider, firstDownloadableUrl } from "./attachments.js";
|
|
45
|
+
export { assertExternalHttpUrl, fetchExternalHttp, isPublicAddress } from "./outbound-http-policy.js";
|
|
26
46
|
import { LocalSandboxAdapter } from "./local-sandbox.js";
|
|
27
47
|
import { schedulerAdapterForKind } from "./scheduler.js";
|
|
28
48
|
import { isTelemetrySink, telemetrySinkFromSetupResult } from "./telemetry.js";
|
|
29
|
-
import { InMemoryStateAdapter, LocalBlobAdapter, StateMemoryStore,
|
|
49
|
+
import { InMemoryStateAdapter, LocalBlobAdapter, StateMemoryStore, positiveLimit } from "./storage.js";
|
|
30
50
|
import { createJsonConsoleLogger, normalizeLogLevel } from "./logging.js";
|
|
31
51
|
import { runDueDeliveriesImpl, startDeliveryWorkerImpl } from "./delivery-queue.js";
|
|
32
52
|
import { recoverIncompleteRunsImpl, startBackgroundWorkersImpl } from "./run-recovery.js";
|
|
33
53
|
import { captureSandboxSnapshotImpl, disposeSandboxSessionImpl, inspectSandboxSyncJobImpl, retrySandboxSyncJobImpl, runDueSandboxSyncJobsImpl, sandboxSyncDiagnosticsImpl, startSandboxSyncWorkerImpl } from "./sandbox-sync-worker.js";
|
|
34
|
-
import { beginChannelTurnImpl, completeRunImpl,
|
|
35
|
-
import { backfillMemoryDocumentsFromFileIndexesImpl, hydrateLogicalPathForToolImpl, listResourcesForRunImpl, memoryScopeForRunImpl, projectResourcesForRunImpl, projectSkillIntoSandboxImpl, readResourceForRunImpl, readSandboxTombstonesWithMissingProjectedFilesImpl, recordSandboxTombstoneImpl, runMemoryEmbeddingBackfillImpl } from "./resource-projection.js";
|
|
54
|
+
import { beginChannelTurnImpl, completeRunImpl, latestRunFailureMessageImpl, recordChannelTurnStartImpl, sendDeliveryImpl, stopUnclaimedChannelTurnImpl, stopChannelTurnImpl } from "./delivery-send.js";
|
|
55
|
+
import { backfillMemoryDocumentsFromFileIndexesImpl, hydrateLogicalPathForToolImpl, listResourcesForRunImpl, memoryScopeForRunImpl, projectLoadedSkillsIntoSandboxImpl, projectResourcesForRunImpl, projectSkillIntoSandboxImpl, readResourceForRunImpl, readSandboxTombstonesWithMissingProjectedFilesImpl, recordSandboxTombstoneImpl, runMemoryEmbeddingBackfillImpl } from "./resource-projection.js";
|
|
56
|
+
import { createSkillBundleIndex, createSkillResourceReader } from "./skill-bundles.js";
|
|
57
|
+
import { createSandboxHandleImpl } from "./sandbox-handle.js";
|
|
58
|
+
import { RuntimeWorkspaceManager, WorkspaceRuntimeMethods } from "./workspace-runtime.js";
|
|
36
59
|
import { beginConnectionAuthorizationImpl, createConnectionRegistryForRunImpl, createConnectionRegistryForSessionImpl, createConnectionRegistryImpl, executeConnectionToolWithRecordImpl, skillLoadDetailsImpl } from "./builtin-tool-executors.js";
|
|
37
60
|
import { createMemoryToolApiImpl, createResourceToolApiImpl, durableStepImpl } from "./tool-apis.js";
|
|
38
61
|
import { executeToolImpl, executeToolWithRecordImpl, harnessExecuteToolImpl, modelToolsImpl, selectToolImpl, visibleToolSetImpl, wrapSandboxImpl } from "./tool-execution.js";
|
|
39
62
|
import { dispatchAutomationEventImpl, normalizeScheduleTriggerDefinitionImpl, registerManifestSchedulesImpl, runDueSchedulesImpl, startSchedulerPollingLoopImpl } from "./schedule-execution.js";
|
|
40
63
|
import { completeConnectionAuthorizationCallbackImpl, replayImpl, resumeApprovalNowImpl, resumeHarnessLoopImpl, resumeInputNowImpl, resumeRunFromContinuationImpl, resumeSuspendedNowImpl } from "./replay-resume.js";
|
|
64
|
+
import { recordRunReplayStarted, rerunFromSnapshot } from "./run-replay.js";
|
|
65
|
+
export { RunReplayError } from "./run-replay.js";
|
|
66
|
+
import { buildRunAgentResult } from "./run-result.js";
|
|
41
67
|
import { readSubagentImpl, runSubagentImpl, sendSubagentFollowupImpl } from "./subagent-execution.js";
|
|
42
|
-
import { createHarnessContextImpl, DEFAULT_MAX_MODEL_ITERATIONS, DEFAULT_OUTPUT_VALIDATION_MAX_RETRIES, executeHarnessTurnImpl, persistHarnessContinuationImpl,
|
|
68
|
+
import { createHarnessContextImpl, DEFAULT_MAX_MODEL_ITERATIONS, DEFAULT_OUTPUT_VALIDATION_MAX_RETRIES, executeHarnessTurnImpl, persistHarnessContinuationImpl, resolveAgentHarnessImpl, runHarnessLoopImpl } from "./harness-loop.js";
|
|
43
69
|
import { getAgentControlImpl, requestRunControlImpl, setAgentEnabledImpl, setAgentMaintenanceImpl } from "./operator-controls.js";
|
|
44
|
-
import { acceptChannelTurnImpl, channelAttachmentResolverImpl, dispatchHttpChannelImpl, loadChannelModuleImpl, startChannelIngressImpl } from "./channel-ingress.js";
|
|
70
|
+
import { acceptChannelTurnImpl, channelAttachmentResolverImpl, dispatchHttpChannelImpl, loadChannelModuleImpl, observeChannelMessageImpl, startChannelAgentTurnImpl, startChannelIngressImpl } from "./channel-ingress.js";
|
|
45
71
|
import { augmentChannelContextImpl, buildContextBundleImpl, prepareConversationImpl, recentHistoryImpl } from "./conversation-context.js";
|
|
46
72
|
import { loadResumableConversationTranscriptImpl } from "./conversation-transcript.js";
|
|
47
73
|
import { ConversationTurnDispatcher } from "./conversation-turn-dispatch.js";
|
|
48
|
-
import { instructionsForRunTargetImpl } from "./
|
|
74
|
+
import { instructionsForRunTargetImpl } from "./target-instructions.js";
|
|
49
75
|
import { emitTelemetrySpanImpl, runSpanAttributesImpl } from "./telemetry.js";
|
|
50
76
|
import { normalizeRuntimeState } from "./state-stores.js";
|
|
51
77
|
import { COMPACTABLE_ACTIVE_CHECKPOINT_NAMES, checkpointDataForStorage as checkpointDataForBlobStorage, emptyCheckpointRetentionResult, hydrateCheckpointData as hydrateCheckpointDataFromBlob, resolveCheckpointRetentionPolicy } from "./checkpoints.js";
|
|
52
|
-
// State record types, capability facets (RunStore & friends), the
|
|
53
|
-
// StateAdapter intersection, StateStores, and the capability guards.
|
|
54
78
|
export * from "./state.js";
|
|
79
|
+
export * from "./principals.js";
|
|
80
|
+
export * from "./audience.js";
|
|
55
81
|
export { evalRunOptionsForRun, validateEvalRunOptions } from "./eval-run-options.js";
|
|
56
|
-
export { InMemoryConversationStore, InMemoryConversationTurnStore, InMemoryFileIndexStore, InMemoryMemoryStateStore, InMemoryRunStore, InMemorySandboxSessionStore, InMemoryScheduleStateStore, InMemoryUsageStore, composeStateStores, normalizeRuntimeState } from "./state-stores.js";
|
|
82
|
+
export { InMemoryConversationStore, InMemoryConversationTurnStore, InMemoryFileIndexStore, InMemoryMemoryStateStore, InMemoryRunStore, InMemorySandboxSessionStore, InMemoryScheduleStateStore, InMemoryUsageStore, InMemoryWorkspaceStore, composeStateStores, normalizeMemoryPath, normalizeRuntimeState } from "./state-stores.js";
|
|
83
|
+
export * from "./workspace.js";
|
|
57
84
|
export { applyDeliveryPatch, createDeliveryRecord, deliveryQueueRetryDelayMs, isDeliveryDue, normalizeDeliveryRecord, stateSupportsDeliveryQueue } from "./delivery-queue.js";
|
|
58
85
|
export { defaultRunStaleAfterMs } from "./run-recovery.js";
|
|
59
86
|
export { BoundedSemaphore, RunCapacityError, retryAfterSeconds } from "./concurrency.js";
|
|
60
87
|
import { BoundedSemaphore, RunCapacityError } from "./concurrency.js";
|
|
61
88
|
import { DEFAULT_MODEL_OUTPUT_MAX_CHARS } from "@assemblyline-agents/core";
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
export { gatewaySchedulerAdapter, localSchedulerAdapter, postgresSchedulerAdapter, schedulerAdapterForKind } from "./scheduler.js";
|
|
67
|
-
export { createOpenTelemetrySink } from "./telemetry.js";
|
|
68
|
-
export { createJsonConsoleLogger, noopLogger, normalizeLogLevel } from "./logging.js";
|
|
69
|
-
export { capabilityCatalogForManifest, capabilityForModel, capabilityMatchesId, connectionSearchResultForModel, normalizeCapabilityKind, normalizeCapabilityRouterInput, normalizeDeferredToolSearchInput, routerShouldSearchConnections, scoreCapability, searchCapabilityCatalog, tokenizeCapabilityQuery } from "./capability-catalog.js";
|
|
70
|
-
export { fetchJson, fetchWithPolicy, readBodyCapped, retryAfterMs, HttpResponseTooLargeError } from "./http.js";
|
|
71
|
-
import { hydrateSandboxFilesystem, memoryPathFromSandboxRelativePath, scanSandboxFiles, visibleToolsForSkills } from "./sandbox-fs.js";
|
|
72
|
-
export { buildDefaultContextBundle, hydrateSandboxFilesystem, syncSandboxFilesystem, visibleToolsForSkills } from "./sandbox-fs.js";
|
|
73
|
-
export { queryAgentRuns } from "./runs-query.js";
|
|
74
|
-
export { UsageAccountingError, createUsageRecord, matchesUsageQuery, microsToUsd, queryUsageRecords, reconcileUsageRecord, sha256Json, summarizeUsageRecords, usageTokensAreAuthoritative, usageRecordInput, usdToMicros } from "./usage-records.js";
|
|
75
|
-
export { reconcileOpenAIOrganization, reconcileOpenRouterUsage, usageReconciliationReport } from "./usage-reconciliation.js";
|
|
76
|
-
import { isValidSandboxSkillBody, resolveResourceProjectionPolicy, sandboxFileContentsToUtf8, sha256Text, skillNameFromSandboxRelativePath, skillNameFromSkillPath } from "./resource-projection-util.js";
|
|
89
|
+
import { visibleToolsForSkills } from "./sandbox-fs.js";
|
|
90
|
+
import { resolveResourceProjectionPolicy } from "./resource-projection-util.js";
|
|
91
|
+
import { syncMemoryFromSandbox, syncSkillsFromSandbox } from "./sandbox-state-sync.js";
|
|
92
|
+
import { acquireSandboxForRun as acquireSandboxSessionForRun } from "./sandbox-session-lifecycle.js";
|
|
77
93
|
import { resolveSandboxSnapshotPolicy } from "./sandbox-snapshot-policy.js";
|
|
78
94
|
import { inferToolInput } from "./channel-http-util.js";
|
|
79
95
|
import { connectionPrincipalKeyForGrant, durableAgentScopeForManifest, isInstrumentationDefinition, normalizeCapturePolicy, randomHex, stringValue, timestamp, } from "./runtime-util.js";
|
|
80
|
-
export
|
|
81
|
-
export { loadRuntimeBundle } from "./runtime-bundle.js";
|
|
82
|
-
export class AssemblyLineRuntime {
|
|
96
|
+
export class AssemblyLineRuntime extends WorkspaceRuntimeMethods {
|
|
83
97
|
manifest;
|
|
84
98
|
state;
|
|
85
99
|
runEventBus = new RunEventBus();
|
|
100
|
+
eventHandlers;
|
|
101
|
+
agentHookControllers = new Map();
|
|
102
|
+
agentStateHandles = new Map();
|
|
86
103
|
blob;
|
|
87
104
|
sandbox;
|
|
88
105
|
scheduler;
|
|
106
|
+
mediaProcessors;
|
|
89
107
|
deliveryMode;
|
|
90
108
|
toolStubs;
|
|
91
109
|
/** Per-run {results:[...]} stub cursors; in-memory by design (see eval-run-options.ts). */
|
|
@@ -103,19 +121,21 @@ export class AssemblyLineRuntime {
|
|
|
103
121
|
connections;
|
|
104
122
|
env;
|
|
105
123
|
fetch;
|
|
124
|
+
attachmentHostResolver;
|
|
106
125
|
logger;
|
|
107
126
|
connectionGrantStore;
|
|
108
127
|
connectionAuthorizationSessionStore;
|
|
128
|
+
connectionEventStore;
|
|
109
129
|
connectionCallbackBaseUrl;
|
|
110
130
|
skillStore;
|
|
131
|
+
learningStore;
|
|
111
132
|
memoryStore;
|
|
112
133
|
scheduleStore;
|
|
113
134
|
connectionDefinitionStore;
|
|
114
135
|
skillsConfig;
|
|
115
136
|
schedulesConfig;
|
|
116
137
|
connectionsConfig;
|
|
117
|
-
|
|
118
|
-
skillScopeMigrated = false;
|
|
138
|
+
runtimeLearning;
|
|
119
139
|
connectionScopeMigrated = false;
|
|
120
140
|
dynamicConnectionsCache;
|
|
121
141
|
schedulerEnabled;
|
|
@@ -150,31 +170,39 @@ export class AssemblyLineRuntime {
|
|
|
150
170
|
hostInstrumentationProvided;
|
|
151
171
|
instrumentationConfig;
|
|
152
172
|
sourceLoader;
|
|
173
|
+
skillBundleIndex;
|
|
174
|
+
skillResourceReader;
|
|
153
175
|
contextPolicyPromise;
|
|
154
176
|
/** Fast local view of durable control intents, refreshed by run heartbeats. */
|
|
155
177
|
runControlIntents = new Map();
|
|
178
|
+
/** Runs currently owned by this process, used to route immediate control signals without leaking orphan ids. */
|
|
179
|
+
activeRunExecutions = new Set();
|
|
156
180
|
/** Deadline-fired runs (read by shouldStopRun) + their in-flight abort controllers. */
|
|
157
181
|
runDeadlines = new Set();
|
|
158
182
|
runAbortControllers = new Map();
|
|
159
183
|
maxRunDurationMs;
|
|
160
184
|
constructor(options) {
|
|
185
|
+
super();
|
|
161
186
|
this.manifest = options.manifest;
|
|
162
187
|
const normalizedState = normalizeRuntimeState(options.state ?? new InMemoryStateAdapter());
|
|
163
188
|
// Events fan out to live streams; terminal outcomes become log lines at
|
|
164
189
|
// this one choke point (logger read lazily — assigned below).
|
|
165
|
-
this.state = withRunEventPublishing(normalizedState.state, this.runEventBus, (runId, event) => logTerminalRunEvent(this.logger, runId, event), (runId, event) => this.
|
|
190
|
+
this.state = withRunEventPublishing(normalizedState.state, this.runEventBus, (runId, event) => logTerminalRunEvent(this.logger, runId, event), (runId, event) => this.handleRuntimeEvent(runId, event));
|
|
166
191
|
this.blob = options.blob ?? new LocalBlobAdapter();
|
|
167
192
|
this.sandbox = options.sandbox ?? new LocalSandboxAdapter();
|
|
168
193
|
this.scheduler = options.scheduler ?? schedulerAdapterForKind(this.manifest.gateway.scheduler?.kind);
|
|
194
|
+
this.mediaProcessors = options.mediaProcessors ?? [];
|
|
169
195
|
this.deliveryMode = options.deliveryMode ?? "send";
|
|
170
196
|
this.toolStubs = options.toolStubs ?? {};
|
|
171
197
|
this.devMode = options.devMode ?? false;
|
|
172
198
|
this.sourceBundle = options.sourceBundle ?? {};
|
|
173
199
|
this.connections = options.connections ?? {};
|
|
174
|
-
this.env =
|
|
200
|
+
this.env = { ...(options.env ?? process.env) };
|
|
175
201
|
this.fetch = options.fetch ?? globalThis.fetch.bind(globalThis);
|
|
202
|
+
this.attachmentHostResolver = options.attachmentHostResolver;
|
|
176
203
|
this.logger = options.logger ??
|
|
177
|
-
createJsonConsoleLogger({ level: normalizeLogLevel(this.env.
|
|
204
|
+
createJsonConsoleLogger({ level: normalizeLogLevel(this.env.ASSEMBLY_LINE_LOG_LEVEL) ?? "info" });
|
|
205
|
+
this.eventHandlers = new AgentEventHandlerRegistry(this.agentName(), (runId, type, data) => this.state.appendEvent(runId, type, data), this.logger);
|
|
178
206
|
if (normalizedState.degradedFacets.length > 0) {
|
|
179
207
|
this.logger.warn("state.degraded", {
|
|
180
208
|
missingFacets: normalizedState.degradedFacets,
|
|
@@ -185,7 +213,7 @@ export class AssemblyLineRuntime {
|
|
|
185
213
|
this.models = options.models;
|
|
186
214
|
this.agentHarnessOverride = options.agentHarness;
|
|
187
215
|
this.modelHarnesses = options.modelHarnesses ?? {};
|
|
188
|
-
this.checkpointEveryIteration = resolveBooleanEnv(this.env.
|
|
216
|
+
this.checkpointEveryIteration = resolveBooleanEnv(this.env.ASSEMBLY_LINE_CHECKPOINT_EVERY_ITERATION, true);
|
|
189
217
|
this.checkpointRetention = resolveCheckpointRetentionPolicy(options.checkpointRetention, this.env);
|
|
190
218
|
this.checkpointBlobStorageEnabled = options.blob !== undefined && this.checkpointRetention.blobThresholdBytes > 0;
|
|
191
219
|
this.telemetry = options.telemetry;
|
|
@@ -201,11 +229,13 @@ export class AssemblyLineRuntime {
|
|
|
201
229
|
};
|
|
202
230
|
this.connectionGrantStore = options.connectionGrantStore ?? new InMemoryConnectionGrantStore();
|
|
203
231
|
this.connectionAuthorizationSessionStore = options.connectionAuthorizationSessionStore ?? new InMemoryConnectionAuthorizationSessionStore();
|
|
232
|
+
this.connectionEventStore = options.connectionEventStore ?? new InMemoryConnectionEventStore();
|
|
204
233
|
this.connectionCallbackBaseUrl = options.connectionCallbackBaseUrl;
|
|
205
234
|
this.skillStore = options.skillStore ?? new InMemorySkillStore();
|
|
235
|
+
this.learningStore = options.learningStore ?? new InMemoryLearningStore();
|
|
206
236
|
this.memoryEmbeddingProvider = options.memoryEmbeddingProvider;
|
|
207
237
|
const memoryEmbeddingsRequested = options.memoryEmbeddingsEnabled ??
|
|
208
|
-
resolveBooleanEnv(this.env.
|
|
238
|
+
resolveBooleanEnv(this.env.ASSEMBLY_LINE_MEMORY_EMBEDDINGS_ENABLED, Boolean(options.memoryEmbeddingProvider));
|
|
209
239
|
const memoryEmbeddingStoreAvailable = this.state.supportsMemoryEmbeddings?.() ?? true;
|
|
210
240
|
this.memoryEmbeddingsEnabled = memoryEmbeddingsRequested && memoryEmbeddingStoreAvailable;
|
|
211
241
|
if (memoryEmbeddingsRequested && !memoryEmbeddingStoreAvailable) {
|
|
@@ -221,27 +251,48 @@ export class AssemblyLineRuntime {
|
|
|
221
251
|
this.connectionsConfig = resolveConnectionsConfig(this.manifest.agent.dynamicConnections, this.env);
|
|
222
252
|
this.schedulerEnabled = options.schedulerEnabled;
|
|
223
253
|
this.schedulerTickMs = options.schedulerTickMs ?? 60_000;
|
|
224
|
-
this.scheduleMaxConsecutiveFailures = resolvePositiveIntegerEnv(this.env.
|
|
254
|
+
this.scheduleMaxConsecutiveFailures = resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_SCHEDULE_MAX_FAILURES, 5);
|
|
225
255
|
this.now = options.now ?? (() => new Date());
|
|
256
|
+
this.workspaceRuntime = new RuntimeWorkspaceManager({
|
|
257
|
+
state: this.state,
|
|
258
|
+
blob: this.blob,
|
|
259
|
+
agentScope: this.durableAgentScope(),
|
|
260
|
+
now: this.now,
|
|
261
|
+
env: this.env,
|
|
262
|
+
...(this.memoryEmbeddingProvider ? { embeddingProvider: this.memoryEmbeddingProvider } : {}),
|
|
263
|
+
sandboxSessionKey: (run) => this.sandboxSessionKey(run)
|
|
264
|
+
});
|
|
265
|
+
this.runtimeLearning = new RuntimeLearningManager({
|
|
266
|
+
state: this.state, manifest: this.manifest,
|
|
267
|
+
env: this.env, logger: this.logger,
|
|
268
|
+
learningStore: this.learningStore,
|
|
269
|
+
skillStore: this.skillStore, memoryStore: this.memoryStore,
|
|
270
|
+
skillsConfigForSurface: (surfacePath) => this.skillsConfigForSurface(surfacePath),
|
|
271
|
+
skillScopeForSurface: (surfacePath) => this.skillScopeForSurface(surfacePath),
|
|
272
|
+
anySkillsEnabled: () => this.anySkillsEnabled(),
|
|
273
|
+
memoryScopeForRun: (run) => this.memoryScopeForRun(run),
|
|
274
|
+
resolveAgentHarness: (modelSpec) => this.resolveAgentHarness(modelSpec),
|
|
275
|
+
now: () => this.now()
|
|
276
|
+
});
|
|
226
277
|
this.sandboxSnapshotPolicy = resolveSandboxSnapshotPolicy(this.manifest, this.env, options.sandboxSnapshotPolicy);
|
|
227
|
-
this.sandboxSyncInline = options.sandboxSyncInline ?? resolveBooleanEnv(this.env.
|
|
228
|
-
this.sandboxSyncLeaseMs = options.sandboxSyncLeaseMs ?? resolvePositiveIntegerEnv(this.env.
|
|
229
|
-
this.sandboxSyncBatchSize = options.sandboxSyncBatchSize ?? resolvePositiveIntegerEnv(this.env.
|
|
230
|
-
this.sandboxSyncMaxAttempts = options.sandboxSyncMaxAttempts ?? resolvePositiveIntegerEnv(this.env.
|
|
231
|
-
this.deliveryQueueLeaseMs = options.deliveryQueueLeaseMs ?? resolvePositiveIntegerEnv(this.env.
|
|
232
|
-
this.toolOutputMaxChars = resolvePositiveIntegerEnv(this.env.
|
|
233
|
-
this.toolTimeoutMs = resolveNonNegativeIntegerEnv(this.env.
|
|
234
|
-
this.deliveryQueueBatchSize = options.deliveryQueueBatchSize ?? resolvePositiveIntegerEnv(this.env.
|
|
235
|
-
this.deliveryQueueMaxAttempts = options.deliveryQueueMaxAttempts ?? resolvePositiveIntegerEnv(this.env.
|
|
236
|
-
this.deliveryQueueIntervalMs = options.deliveryQueueIntervalMs ?? resolvePositiveIntegerEnv(this.env.
|
|
237
|
-
this.runHeartbeatMs = options.runHeartbeatMs ?? resolvePositiveIntegerEnv(this.env.
|
|
238
|
-
this.maxRunDurationMs = options.maxRunDurationMs ?? resolveNonNegativeIntegerEnv(this.env.
|
|
239
|
-
this.runRecoveryIntervalMs = options.runRecoveryIntervalMs ?? resolvePositiveIntegerEnv(this.env.
|
|
240
|
-
this.maxModelIterations = resolvePositiveIntegerEnv(this.env.
|
|
241
|
-
this.outputValidationMaxRetries = resolveNonNegativeIntegerEnv(this.env.
|
|
278
|
+
this.sandboxSyncInline = options.sandboxSyncInline ?? resolveBooleanEnv(this.env.ASSEMBLY_LINE_SANDBOX_SYNC_INLINE, false);
|
|
279
|
+
this.sandboxSyncLeaseMs = options.sandboxSyncLeaseMs ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_SANDBOX_SYNC_LEASE_MS, 5 * 60_000);
|
|
280
|
+
this.sandboxSyncBatchSize = options.sandboxSyncBatchSize ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_SANDBOX_SYNC_BATCH_SIZE, 10);
|
|
281
|
+
this.sandboxSyncMaxAttempts = options.sandboxSyncMaxAttempts ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_SANDBOX_SYNC_MAX_ATTEMPTS, 5);
|
|
282
|
+
this.deliveryQueueLeaseMs = options.deliveryQueueLeaseMs ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_DELIVERY_QUEUE_LEASE_MS, 60_000);
|
|
283
|
+
this.toolOutputMaxChars = resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_TOOL_OUTPUT_MAX_CHARS, DEFAULT_MODEL_OUTPUT_MAX_CHARS);
|
|
284
|
+
this.toolTimeoutMs = resolveNonNegativeIntegerEnv(this.env.ASSEMBLY_LINE_TOOL_TIMEOUT_MS, 600_000);
|
|
285
|
+
this.deliveryQueueBatchSize = options.deliveryQueueBatchSize ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_DELIVERY_QUEUE_BATCH_SIZE, 10);
|
|
286
|
+
this.deliveryQueueMaxAttempts = options.deliveryQueueMaxAttempts ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_DELIVERY_QUEUE_MAX_ATTEMPTS, 5);
|
|
287
|
+
this.deliveryQueueIntervalMs = options.deliveryQueueIntervalMs ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_DELIVERY_QUEUE_INTERVAL_MS, 15_000);
|
|
288
|
+
this.runHeartbeatMs = options.runHeartbeatMs ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_RUN_HEARTBEAT_MS, 30_000);
|
|
289
|
+
this.maxRunDurationMs = options.maxRunDurationMs ?? resolveNonNegativeIntegerEnv(this.env.ASSEMBLY_LINE_MAX_RUN_DURATION_MS, 3_600_000);
|
|
290
|
+
this.runRecoveryIntervalMs = options.runRecoveryIntervalMs ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_RUN_RECOVERY_INTERVAL_MS, 60_000);
|
|
291
|
+
this.maxModelIterations = resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_MAX_MODEL_ITERATIONS, DEFAULT_MAX_MODEL_ITERATIONS);
|
|
292
|
+
this.outputValidationMaxRetries = resolveNonNegativeIntegerEnv(this.env.ASSEMBLY_LINE_OUTPUT_VALIDATION_MAX_RETRIES, DEFAULT_OUTPUT_VALIDATION_MAX_RETRIES);
|
|
242
293
|
this.runSemaphore = new BoundedSemaphore({
|
|
243
|
-
maxConcurrent: options.maxConcurrentRuns ?? resolvePositiveIntegerEnv(this.env.
|
|
244
|
-
maxQueued: options.maxQueuedRuns ?? resolvePositiveIntegerEnv(this.env.
|
|
294
|
+
maxConcurrent: options.maxConcurrentRuns ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_MAX_CONCURRENT_RUNS, Infinity),
|
|
295
|
+
maxQueued: options.maxQueuedRuns ?? resolvePositiveIntegerEnv(this.env.ASSEMBLY_LINE_MAX_QUEUED_RUNS, 0)
|
|
245
296
|
});
|
|
246
297
|
this.conversationTurnDispatcher = new ConversationTurnDispatcher({
|
|
247
298
|
state: this.state, logger: this.logger,
|
|
@@ -258,13 +309,21 @@ export class AssemblyLineRuntime {
|
|
|
258
309
|
this.sourceLoader = new AgentSourceModuleLoader({
|
|
259
310
|
manifest: this.manifest,
|
|
260
311
|
sourceBundle: this.sourceBundle,
|
|
261
|
-
...(options.artifactRoot ? { cacheRoot: join(resolve(options.artifactRoot),
|
|
312
|
+
...(options.artifactRoot ? { cacheRoot: join(resolve(options.artifactRoot), ARTIFACT_DIR_NAME, "module-cache") } : {})
|
|
313
|
+
});
|
|
314
|
+
this.skillBundleIndex = createSkillBundleIndex(this.manifest);
|
|
315
|
+
this.skillResourceReader = createSkillResourceReader({
|
|
316
|
+
manifest: this.manifest,
|
|
317
|
+
...(options.resourcesRoot ? { resourcesRoot: options.resourcesRoot } : {}),
|
|
318
|
+
manifestRoot: this.manifest.root,
|
|
319
|
+
sourceBundle: this.sourceBundle
|
|
262
320
|
});
|
|
263
321
|
}
|
|
264
322
|
boot() {
|
|
265
|
-
if (this.manifest.schemaVersion !==
|
|
266
|
-
throw new Error(`Unsupported
|
|
323
|
+
if (this.manifest.schemaVersion !== ASSEMBLY_LINE_MANIFEST_SCHEMA_VERSION) {
|
|
324
|
+
throw new Error(`Unsupported Assembly Line manifest schema ${this.manifest.schemaVersion}.`);
|
|
267
325
|
}
|
|
326
|
+
this.sourceLoader.ensureCacheReady();
|
|
268
327
|
if (!this.devMode) {
|
|
269
328
|
const missing = this.manifest.preflight.filter((requirement) => requirement.kind === "env" &&
|
|
270
329
|
requirement.required &&
|
|
@@ -348,46 +407,41 @@ export class AssemblyLineRuntime {
|
|
|
348
407
|
this.logger.warn("provider ingress security warning", { warning });
|
|
349
408
|
}
|
|
350
409
|
}
|
|
351
|
-
skillScope() {
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
410
|
+
skillScope() { return this.skillScopeForSurface("root"); }
|
|
411
|
+
skillScopeForSurface(surfacePath) {
|
|
412
|
+
surfaceForPath(this.manifest, surfacePath);
|
|
413
|
+
return durableAgentSurfaceScope(this.durableAgentScope(), surfacePath);
|
|
414
|
+
}
|
|
415
|
+
skillScopeForRun(run) {
|
|
416
|
+
return this.skillScopeForSurface(surfaceForRun(this.manifest, run).path);
|
|
417
|
+
}
|
|
418
|
+
skillsConfigForSurface(surfacePath) {
|
|
419
|
+
if (surfacePath === "root")
|
|
420
|
+
return this.skillsConfig;
|
|
421
|
+
const surface = surfaceForPath(this.manifest, surfacePath);
|
|
422
|
+
return resolveSkillsConfig({
|
|
423
|
+
...(this.manifest.agent.selfImprovement ?? {}),
|
|
424
|
+
...(surface.selfImprovement ?? {})
|
|
425
|
+
}, this.env);
|
|
426
|
+
}
|
|
427
|
+
skillsConfigForRun(run) {
|
|
428
|
+
return this.skillsConfigForSurface(surfaceForRun(this.manifest, run).path);
|
|
429
|
+
}
|
|
430
|
+
anySkillsEnabled() {
|
|
431
|
+
return ["root", ...flattenSubagents(this.manifest.subagents).map((subagent) => subagent.path)]
|
|
432
|
+
.some((surfacePath) => this.skillsConfigForSurface(surfacePath).enabled);
|
|
433
|
+
}
|
|
434
|
+
connectionScope() { return this.durableAgentScope(); }
|
|
435
|
+
durableAgentScope() { return durableAgentScopeForManifest(this.manifest); }
|
|
436
|
+
usesRevisionScopedDurableState() { return this.durableAgentScope() === this.manifest.agentRevision; }
|
|
363
437
|
scheduleScopeForRun(run) {
|
|
364
|
-
const
|
|
365
|
-
|
|
366
|
-
|
|
438
|
+
const audience = audienceFromRun(run);
|
|
439
|
+
return audienceUserKey(audience)
|
|
440
|
+
?? (!audience.private ? audience.conversationId : undefined)
|
|
441
|
+
?? this.durableAgentScope();
|
|
367
442
|
}
|
|
368
443
|
/** Seed the durable skill store from compiled manifest skills (idempotent). */
|
|
369
|
-
async ensureSkillsSeeded() {
|
|
370
|
-
if (this.skillsSeeded)
|
|
371
|
-
return;
|
|
372
|
-
await this.migrateLegacySkillScope();
|
|
373
|
-
await seedSkills(this.skillStore, this.skillScope(), this.manifest.skills);
|
|
374
|
-
this.skillsSeeded = true;
|
|
375
|
-
}
|
|
376
|
-
async migrateLegacySkillScope() {
|
|
377
|
-
if (this.skillScopeMigrated)
|
|
378
|
-
return;
|
|
379
|
-
this.skillScopeMigrated = true;
|
|
380
|
-
const scope = this.skillScope();
|
|
381
|
-
const legacyScope = this.manifest.agentRevision;
|
|
382
|
-
if (scope === legacyScope)
|
|
383
|
-
return;
|
|
384
|
-
const current = await this.skillStore.list(scope);
|
|
385
|
-
if (current.length > 0)
|
|
386
|
-
return;
|
|
387
|
-
for (const skill of await this.skillStore.list(legacyScope)) {
|
|
388
|
-
await this.skillStore.put(scope, skill);
|
|
389
|
-
}
|
|
390
|
-
}
|
|
444
|
+
async ensureSkillsSeeded(surfacePath = "root") { return this.runtimeLearning.ensureSkillsSeeded(surfacePath); }
|
|
391
445
|
async migrateLegacyConnectionScope() {
|
|
392
446
|
if (this.connectionScopeMigrated)
|
|
393
447
|
return;
|
|
@@ -404,30 +458,24 @@ export class AssemblyLineRuntime {
|
|
|
404
458
|
}
|
|
405
459
|
}
|
|
406
460
|
/** Live skill catalog (durable store, post-seed) for context assembly and inspection. */
|
|
407
|
-
async listSkills() {
|
|
408
|
-
await this.ensureSkillsSeeded();
|
|
409
|
-
return liveSkills(this.skillStore, this.skillScope());
|
|
410
|
-
}
|
|
461
|
+
async listSkills(surfacePath = "root") { return this.runtimeLearning.listSkills(surfacePath); }
|
|
411
462
|
/** Persist an agent/user authored skill, honoring the write-approval gate. */
|
|
412
|
-
async saveSkill(input) {
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
}
|
|
429
|
-
await this.ensureSkillsSeeded();
|
|
430
|
-
await this.skillStore.delete(this.skillScope(), name);
|
|
463
|
+
async saveSkill(input, surfacePath = "root") { return this.runtimeLearning.saveSkill(input, surfacePath); }
|
|
464
|
+
async deleteSkill(name, surfacePath = "root") { return this.runtimeLearning.deleteSkill(name, surfacePath); }
|
|
465
|
+
async listSkillRevisions(name, surfacePath = "root") { return this.runtimeLearning.listSkillRevisions(name, surfacePath); }
|
|
466
|
+
async restoreSkillRevision(name, revision, surfacePath = "root") { return this.runtimeLearning.restoreSkillRevision(name, revision, surfacePath); }
|
|
467
|
+
async listPendingSkillChanges(surfacePath = "root") { return this.runtimeLearning.listPendingSkillChanges(surfacePath); }
|
|
468
|
+
async approveSkillChange(id, surfacePath = "root") { return this.runtimeLearning.approveSkillChange(id, surfacePath); }
|
|
469
|
+
async rejectSkillChange(id, surfacePath = "root") { return this.runtimeLearning.rejectSkillChange(id, surfacePath); }
|
|
470
|
+
async recordRunFeedback(runId, feedback) {
|
|
471
|
+
return this.runtimeLearning.recordRunFeedback(runId, feedback);
|
|
472
|
+
}
|
|
473
|
+
async listBackgroundReviews(surfacePath = "root") { return this.runtimeLearning.listBackgroundReviews(surfacePath); }
|
|
474
|
+
async runDueBackgroundReviews(options = {}) {
|
|
475
|
+
return this.runtimeLearning.runDueBackgroundReviews(options);
|
|
476
|
+
}
|
|
477
|
+
startBackgroundReviewWorker(options = {}) {
|
|
478
|
+
return this.runtimeLearning.startBackgroundReviewWorker(options);
|
|
431
479
|
}
|
|
432
480
|
async createDynamicSchedule(input) {
|
|
433
481
|
if (!this.schedulesConfig.dynamic) {
|
|
@@ -538,301 +586,53 @@ export class AssemblyLineRuntime {
|
|
|
538
586
|
this.dynamicConnectionsCache = undefined;
|
|
539
587
|
}
|
|
540
588
|
async syncMemoryFromSandbox(run, sandboxSession, tombstones) {
|
|
541
|
-
|
|
542
|
-
const deleted = [];
|
|
543
|
-
const tombstonedPaths = new Set(tombstones
|
|
544
|
-
.map((tombstone) => tombstone.path)
|
|
545
|
-
.filter((path) => path.startsWith("/memory/")));
|
|
546
|
-
for (const path of tombstonedPaths) {
|
|
547
|
-
await this.state.deleteMemoryDocument(scope, path);
|
|
548
|
-
deleted.push(path);
|
|
549
|
-
}
|
|
550
|
-
let files;
|
|
551
|
-
try {
|
|
552
|
-
files = await scanSandboxFiles(sandboxSession, "/memory");
|
|
553
|
-
}
|
|
554
|
-
catch {
|
|
555
|
-
return { written: [], deleted };
|
|
556
|
-
}
|
|
557
|
-
const written = [];
|
|
558
|
-
for (const file of files) {
|
|
559
|
-
const path = memoryPathFromSandboxRelativePath(file.relativePath);
|
|
560
|
-
if (!path || tombstonedPaths.has(path))
|
|
561
|
-
continue;
|
|
562
|
-
const content = sandboxFileContentsToUtf8(file.contents);
|
|
563
|
-
const current = await this.memoryStore.read(scope, { path });
|
|
564
|
-
if (current && memoryBodyText(current) === content)
|
|
565
|
-
continue;
|
|
566
|
-
await this.memoryStore.write(scope, {
|
|
567
|
-
path,
|
|
568
|
-
content,
|
|
569
|
-
mode: "replace",
|
|
570
|
-
metadata: {
|
|
571
|
-
tags: ["sandbox"],
|
|
572
|
-
sourceRefs: [`sandbox:${run.id}`]
|
|
573
|
-
}
|
|
574
|
-
});
|
|
575
|
-
written.push(path);
|
|
576
|
-
}
|
|
577
|
-
if (written.length > 0 || deleted.length > 0) {
|
|
578
|
-
await this.state.appendEvent(run.id, "memory.documents_synced", {
|
|
579
|
-
written,
|
|
580
|
-
deleted
|
|
581
|
-
});
|
|
582
|
-
}
|
|
583
|
-
return { written, deleted };
|
|
589
|
+
return syncMemoryFromSandbox(this.sandboxStateSyncHost(), run, sandboxSession, tombstones);
|
|
584
590
|
}
|
|
585
591
|
/** Reconcile skill files the agent explicitly edited/deleted under `/skills`. */
|
|
586
592
|
async syncSkillsFromSandbox(run, sandboxSession, tombstones) {
|
|
587
|
-
|
|
588
|
-
try {
|
|
589
|
-
files = await scanSandboxFiles(sandboxSession, "/skills");
|
|
590
|
-
}
|
|
591
|
-
catch {
|
|
592
|
-
files = [];
|
|
593
|
-
}
|
|
594
|
-
const skillScope = this.skillScope();
|
|
595
|
-
const before = await this.skillStore.list(skillScope);
|
|
596
|
-
const beforeByName = new Map(before.map((skill) => [skill.name, skill]));
|
|
597
|
-
const deletedSkillNames = new Set(tombstones
|
|
598
|
-
.map((tombstone) => skillNameFromSkillPath(tombstone.path))
|
|
599
|
-
.filter((name) => Boolean(name)));
|
|
600
|
-
const sandboxSkills = [];
|
|
601
|
-
const invalid = [];
|
|
602
|
-
for (const file of files) {
|
|
603
|
-
const name = skillNameFromSandboxRelativePath(file.relativePath);
|
|
604
|
-
if (!name) {
|
|
605
|
-
if (file.relativePath.endsWith("SKILL.md"))
|
|
606
|
-
invalid.push(file.relativePath);
|
|
607
|
-
continue;
|
|
608
|
-
}
|
|
609
|
-
const body = sandboxFileContentsToUtf8(file.contents);
|
|
610
|
-
if (!isValidSandboxSkillBody(body)) {
|
|
611
|
-
invalid.push(`/skills/${file.relativePath}`);
|
|
612
|
-
continue;
|
|
613
|
-
}
|
|
614
|
-
sandboxSkills.push({ name, body });
|
|
615
|
-
}
|
|
616
|
-
const changed = sandboxSkills.filter((skill) => {
|
|
617
|
-
if (deletedSkillNames.has(skill.name))
|
|
618
|
-
return false;
|
|
619
|
-
return beforeByName.get(skill.name)?.bodySha256 !== sha256Text(skill.body);
|
|
620
|
-
});
|
|
621
|
-
if (!this.skillsConfig.writable) {
|
|
622
|
-
if (changed.length > 0 || deletedSkillNames.size > 0 || invalid.length > 0) {
|
|
623
|
-
throw new Error("Sandbox skill writes are blocked because self-improvement is disabled.");
|
|
624
|
-
}
|
|
625
|
-
return;
|
|
626
|
-
}
|
|
627
|
-
if (invalid.length > 0) {
|
|
628
|
-
throw new Error(`Invalid sandbox skill file(s): ${invalid.join(", ")}`);
|
|
629
|
-
}
|
|
630
|
-
const created = [];
|
|
631
|
-
const updated = [];
|
|
632
|
-
const deleted = [];
|
|
633
|
-
for (const name of deletedSkillNames) {
|
|
634
|
-
if (!beforeByName.has(name))
|
|
635
|
-
continue;
|
|
636
|
-
await this.skillStore.delete(skillScope, name);
|
|
637
|
-
deleted.push(name);
|
|
638
|
-
}
|
|
639
|
-
for (const skill of changed) {
|
|
640
|
-
const existing = beforeByName.get(skill.name);
|
|
641
|
-
await writeSkill(this.skillStore, skillScope, {
|
|
642
|
-
name: skill.name,
|
|
643
|
-
body: skill.body,
|
|
644
|
-
origin: "agent"
|
|
645
|
-
}, {
|
|
646
|
-
requireApproval: this.skillsConfig.writeApproval
|
|
647
|
-
});
|
|
648
|
-
if (existing)
|
|
649
|
-
updated.push(skill.name);
|
|
650
|
-
else
|
|
651
|
-
created.push(skill.name);
|
|
652
|
-
}
|
|
653
|
-
if (created.length || updated.length || deleted.length) {
|
|
654
|
-
await this.state.appendEvent(run.id, "skill.synced", {
|
|
655
|
-
created,
|
|
656
|
-
updated,
|
|
657
|
-
deleted,
|
|
658
|
-
pending: this.skillsConfig.writeApproval
|
|
659
|
-
});
|
|
660
|
-
}
|
|
593
|
+
return syncSkillsFromSandbox(this.sandboxStateSyncHost(), run, sandboxSession, tombstones);
|
|
661
594
|
}
|
|
662
|
-
|
|
663
|
-
const runtime = this;
|
|
664
|
-
let sandboxSession;
|
|
665
|
-
let acquiring;
|
|
666
|
-
const acquire = async () => {
|
|
667
|
-
const run = getRun();
|
|
668
|
-
sandboxSession = await runtime.acquireSandboxForRun(run);
|
|
669
|
-
const updatedRun = await runtime.state.updateRun(run.id, { sandboxId: sandboxSession.id });
|
|
670
|
-
setRun(updatedRun);
|
|
671
|
-
await runtime.state.appendEvent(run.id, "sandbox.acquired", { sandboxId: sandboxSession.id, root: sandboxSession.root });
|
|
672
|
-
await runtime.createCheckpoint({ runId: run.id, name: "sandbox.acquired", data: { sandboxId: sandboxSession.id } });
|
|
673
|
-
await hydrateSandboxFilesystem(sandboxSession, getBundle(), {
|
|
674
|
-
fullHydration: runtime.legacyFullSandboxHydration(),
|
|
675
|
-
blob: runtime.blob
|
|
676
|
-
});
|
|
677
|
-
await runtime.state.appendEvent(run.id, "filesystem.hydrated", {
|
|
678
|
-
memory: "/memory",
|
|
679
|
-
history: "/history",
|
|
680
|
-
files: "/files",
|
|
681
|
-
workspace: "/workspace",
|
|
682
|
-
mode: runtime.legacyFullSandboxHydration() ? "full" : "minimal"
|
|
683
|
-
});
|
|
684
|
-
await runtime.createCheckpoint({
|
|
685
|
-
runId: run.id,
|
|
686
|
-
name: "filesystem.hydrated",
|
|
687
|
-
data: {
|
|
688
|
-
memory: "/memory",
|
|
689
|
-
history: "/history",
|
|
690
|
-
files: "/files",
|
|
691
|
-
workspace: "/workspace",
|
|
692
|
-
mode: runtime.legacyFullSandboxHydration() ? "full" : "minimal"
|
|
693
|
-
}
|
|
694
|
-
});
|
|
695
|
-
await materializeConnectionCredentialsIntoSandbox(run, runtime.createConnectionRegistryForRun(run, "local"), sandboxSession, (eventType, payload) => runtime.state.appendEvent(run.id, eventType, payload));
|
|
696
|
-
return sandboxSession;
|
|
697
|
-
};
|
|
595
|
+
sandboxStateSyncHost() {
|
|
698
596
|
return {
|
|
699
|
-
|
|
700
|
-
|
|
701
|
-
|
|
702
|
-
|
|
703
|
-
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
acquiring ??= acquire().catch((error) => {
|
|
708
|
-
acquiring = undefined;
|
|
709
|
-
throw error;
|
|
710
|
-
});
|
|
711
|
-
return acquiring;
|
|
712
|
-
},
|
|
713
|
-
async getWrapped() {
|
|
714
|
-
const run = getRun();
|
|
715
|
-
return runtime.wrapSandbox(run.id, await this.get());
|
|
716
|
-
},
|
|
717
|
-
async dispose() {
|
|
718
|
-
if (!sandboxSession)
|
|
719
|
-
return;
|
|
720
|
-
await runtime.disposeSandboxSession(getRun().id, sandboxSession);
|
|
721
|
-
}
|
|
597
|
+
state: this.state,
|
|
598
|
+
memoryStore: this.memoryStore,
|
|
599
|
+
skillStore: this.skillStore,
|
|
600
|
+
skillBundleIndex: this.skillBundleIndex,
|
|
601
|
+
learningStore: this.learningStore,
|
|
602
|
+
skillsConfigForRun: (run) => this.skillsConfigForRun(run),
|
|
603
|
+
memoryScopeForRun: (candidate) => this.memoryScopeForRun(candidate),
|
|
604
|
+
skillScopeForRun: (run) => this.skillScopeForRun(run)
|
|
722
605
|
};
|
|
723
606
|
}
|
|
607
|
+
createSandboxHandle(getRun, setRun, getBundle) {
|
|
608
|
+
return createSandboxHandleImpl({
|
|
609
|
+
state: this.state,
|
|
610
|
+
blob: this.blob,
|
|
611
|
+
acquireSandboxForRun: (run) => this.acquireSandboxForRun(run),
|
|
612
|
+
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
613
|
+
legacyFullSandboxHydration: () => this.legacyFullSandboxHydration(),
|
|
614
|
+
hydrateWorkspace: (run, session) => this.workspaceRuntime.service.hydrate(run, session, this.sandboxSessionKey(run)),
|
|
615
|
+
projectLoadedSkills: (run, session) => this.projectLoadedSkillsIntoSandbox(run, session),
|
|
616
|
+
createConnectionRegistryForRun: (run, channel, selectedConnections) => this.createConnectionRegistryForRun(run, channel, undefined, selectedConnections),
|
|
617
|
+
wrapSandbox: (runId, session) => this.wrapSandbox(runId, session),
|
|
618
|
+
disposeSandboxSession: (runId, session) => this.disposeSandboxSession(runId, session)
|
|
619
|
+
}, getRun, setRun, getBundle);
|
|
620
|
+
}
|
|
724
621
|
sandboxSessionKey(run) {
|
|
725
622
|
return sandboxSessionKeyForRun(this.durableAgentScope(), run);
|
|
726
623
|
}
|
|
727
624
|
async acquireSandboxForRun(run) {
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
731
|
-
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
sandboxId: existing?.sandboxId ?? "",
|
|
736
|
-
sessionKey,
|
|
737
|
-
manifest: reconnectManifest
|
|
738
|
-
};
|
|
739
|
-
const root = stringValue(reconnectManifest.sandboxRoot);
|
|
740
|
-
if (root)
|
|
741
|
-
reconnectInput.root = root;
|
|
742
|
-
if (existing?.sandboxId && reconnectCompatible) {
|
|
743
|
-
const connected = await this.sandbox.connect?.(reconnectInput)
|
|
744
|
-
.catch(this.debugSwallow("sandbox connect probe failed", { runId: run.id, sessionKey }));
|
|
745
|
-
if (connected) {
|
|
746
|
-
await this.upsertSandboxSessionForRun(run, sessionKey, provider, connected, existing.dirty, existing.syncJobId, {
|
|
747
|
-
...existing.manifest,
|
|
748
|
-
sandboxRoot: connected.root,
|
|
749
|
-
...sandboxFilesystemContractMetadata(connected.provider === "local" ? "emulated" : "physical")
|
|
750
|
-
}, "live");
|
|
751
|
-
await this.state.appendEvent(run.id, "sandbox.reused", { sandboxId: connected.id, sessionKey, mode: "connect" });
|
|
752
|
-
return connected;
|
|
753
|
-
}
|
|
754
|
-
const woken = await this.sandbox.wake?.(reconnectInput)
|
|
755
|
-
.catch(this.debugSwallow("sandbox wake probe failed", { runId: run.id, sessionKey }));
|
|
756
|
-
if (woken) {
|
|
757
|
-
await this.upsertSandboxSessionForRun(run, sessionKey, provider, woken, existing.dirty, existing.syncJobId, {
|
|
758
|
-
...existing.manifest,
|
|
759
|
-
sandboxRoot: woken.root,
|
|
760
|
-
...sandboxFilesystemContractMetadata(woken.provider === "local" ? "emulated" : "physical")
|
|
761
|
-
}, "live");
|
|
762
|
-
await this.state.appendEvent(run.id, "sandbox.reused", { sandboxId: woken.id, sessionKey, mode: "wake" });
|
|
763
|
-
return woken;
|
|
764
|
-
}
|
|
765
|
-
}
|
|
766
|
-
const lookup = (!existing || reconnectCompatible) ? await this.sandbox.lookup?.({
|
|
767
|
-
sessionKey,
|
|
768
|
-
runId: run.id,
|
|
769
|
-
agentRevision: run.agentRevision,
|
|
770
|
-
manifest: {
|
|
771
|
-
...reconnectManifest,
|
|
772
|
-
...sandboxFilesystemContractMetadata(this.sandbox.provider === "local" ? "emulated" : "physical")
|
|
773
|
-
}
|
|
774
|
-
}).catch(this.debugSwallow("sandbox lookup probe failed", { runId: run.id, sessionKey })) : undefined;
|
|
775
|
-
if (lookup) {
|
|
776
|
-
const lookupInput = {
|
|
777
|
-
runId: run.id,
|
|
778
|
-
sandboxId: lookup.sandboxId,
|
|
779
|
-
sessionKey,
|
|
780
|
-
manifest: lookup.manifest ?? reconnectManifest
|
|
781
|
-
};
|
|
782
|
-
if (lookup.root)
|
|
783
|
-
lookupInput.root = lookup.root;
|
|
784
|
-
const connected = await this.sandbox.connect?.(lookupInput)
|
|
785
|
-
.catch(this.debugSwallow("sandbox connect probe failed", { runId: run.id, sessionKey })) ??
|
|
786
|
-
await this.sandbox.wake?.(lookupInput)
|
|
787
|
-
.catch(this.debugSwallow("sandbox wake probe failed", { runId: run.id, sessionKey }));
|
|
788
|
-
if (connected) {
|
|
789
|
-
await this.upsertSandboxSessionForRun(run, sessionKey, provider, connected, existing?.dirty ?? false, existing?.syncJobId, {
|
|
790
|
-
...(lookup.manifest ?? existing?.manifest ?? {}),
|
|
791
|
-
sandboxRoot: connected.root,
|
|
792
|
-
...sandboxFilesystemContractMetadata(connected.provider === "local" ? "emulated" : "physical")
|
|
793
|
-
}, "live");
|
|
794
|
-
await this.state.appendEvent(run.id, "sandbox.reused", { sandboxId: connected.id, sessionKey, mode: lookup.state ?? "lookup" });
|
|
795
|
-
return connected;
|
|
796
|
-
}
|
|
797
|
-
}
|
|
798
|
-
const createInput = {
|
|
799
|
-
sessionKey,
|
|
800
|
-
metadata: {
|
|
801
|
-
sessionKey,
|
|
802
|
-
runId: run.id,
|
|
803
|
-
agentRevision: run.agentRevision,
|
|
804
|
-
...sandboxFilesystemContractMetadata(this.sandbox.provider === "local" ? "emulated" : "physical")
|
|
805
|
-
}
|
|
806
|
-
};
|
|
807
|
-
if (existing?.snapshotId && reconnectCompatible)
|
|
808
|
-
createInput.snapshotId = existing.snapshotId;
|
|
809
|
-
const created = this.sandbox.create
|
|
810
|
-
? await this.sandbox.create(run, createInput)
|
|
811
|
-
: await this.sandbox.acquire(run);
|
|
812
|
-
await this.upsertSandboxSessionForRun(run, sessionKey, provider, created, existing?.dirty ?? false, existing?.syncJobId, {
|
|
813
|
-
...(existing?.manifest ?? {}),
|
|
814
|
-
sandboxRoot: created.root,
|
|
815
|
-
...sandboxFilesystemContractMetadata(created.provider === "local" ? "emulated" : "physical")
|
|
816
|
-
}, existing?.dirty ? "dirty" : "live");
|
|
817
|
-
await this.state.appendEvent(run.id, "sandbox.created", { sandboxId: created.id, sessionKey });
|
|
818
|
-
return created;
|
|
819
|
-
}
|
|
820
|
-
async upsertSandboxSessionForRun(run, sessionKey, provider, session, dirty, syncJobId, manifest, state) {
|
|
821
|
-
return this.state.upsertSandboxSession({
|
|
822
|
-
sessionKey,
|
|
823
|
-
provider: session.provider ?? provider,
|
|
824
|
-
sandboxId: session.id,
|
|
825
|
-
runId: run.id,
|
|
826
|
-
state: dirty ? "dirty" : state,
|
|
827
|
-
dirty,
|
|
828
|
-
lastSeenAt: timestamp(),
|
|
829
|
-
...(syncJobId ? { syncJobId } : {}),
|
|
830
|
-
manifest
|
|
831
|
-
});
|
|
625
|
+
return acquireSandboxSessionForRun({
|
|
626
|
+
manifest: this.manifest,
|
|
627
|
+
state: this.state,
|
|
628
|
+
sandbox: this.sandbox,
|
|
629
|
+
sessionKey: (candidate) => this.sandboxSessionKey(candidate),
|
|
630
|
+
swallow: (message, fields) => this.debugSwallow(message, fields)
|
|
631
|
+
}, run);
|
|
832
632
|
}
|
|
833
633
|
legacyFullSandboxHydration() {
|
|
834
|
-
return this.env.
|
|
835
|
-
this.env.
|
|
634
|
+
return this.env.ASSEMBLY_LINE_LEGACY_FULL_SANDBOX_HYDRATION === "1" ||
|
|
635
|
+
this.env.ASSEMBLY_LINE_LEGACY_FULL_SANDBOX_HYDRATION === "true";
|
|
836
636
|
}
|
|
837
637
|
async ensureDynamicConnections() {
|
|
838
638
|
if (!this.connectionsConfig.dynamic) {
|
|
@@ -924,22 +724,59 @@ export class AssemblyLineRuntime {
|
|
|
924
724
|
await this.ensureSkillsSeeded();
|
|
925
725
|
await this.ensureDynamicConnections();
|
|
926
726
|
const spanStartedAt = timestamp();
|
|
927
|
-
const channel = options.
|
|
727
|
+
const channel = (options.existingRun && typeof options.existingRun.input.channel === "string"
|
|
728
|
+
? options.existingRun.input.channel
|
|
729
|
+
: undefined) ?? options.turn?.channel ?? options.channel ?? "local";
|
|
928
730
|
const channelDefinition = this.manifest.channels.find((candidate) => candidate.name === channel);
|
|
929
|
-
const
|
|
930
|
-
|
|
731
|
+
const suppliedConversationId = (options.existingRun && typeof options.existingRun.input.conversationId === "string"
|
|
732
|
+
? options.existingRun.input.conversationId
|
|
733
|
+
: undefined) ?? options.turn?.conversationId ?? options.conversationId;
|
|
734
|
+
const legacyUserId = options.turn?.userId ?? options.userId;
|
|
735
|
+
const principal = (options.existingRun ? principalFromRun(options.existingRun) : undefined)
|
|
736
|
+
?? normalizeAgentPrincipal(options.turn?.principal ?? options.principal)
|
|
737
|
+
?? defaultUserPrincipal(legacyUserId, channel);
|
|
738
|
+
const initiator = (options.existingRun ? initiatorFromRun(options.existingRun) : undefined)
|
|
739
|
+
?? normalizeAgentPrincipal(options.turn?.initiator ?? options.initiator)
|
|
740
|
+
?? principal;
|
|
741
|
+
// Channel turns derive their audience from the authenticated turn, so it
|
|
742
|
+
// cannot disagree with the principal or conversation; other callers are
|
|
743
|
+
// trusted embedders and default to a private direct run.
|
|
744
|
+
const audience = (options.existingRun ? normalizeAgentAudience(options.existingRun.input.audience) : undefined)
|
|
745
|
+
?? normalizeAgentAudience(options.turn?.audience ?? options.audience)
|
|
746
|
+
?? { private: true };
|
|
747
|
+
const replyTarget = options.existingRun && isJsonObject(options.existingRun.input.replyTarget)
|
|
748
|
+
? options.existingRun.input.replyTarget
|
|
749
|
+
: safeJson({
|
|
750
|
+
channel,
|
|
751
|
+
conversationId: suppliedConversationId ?? null,
|
|
752
|
+
delivery: options.turn?.delivery ?? options.delivery ?? null
|
|
753
|
+
});
|
|
931
754
|
const runInput = {
|
|
932
755
|
message: options.message,
|
|
933
|
-
|
|
756
|
+
agentSurface: "root",
|
|
934
757
|
channel,
|
|
935
758
|
eventId: options.turn?.eventId ?? options.eventId ?? null,
|
|
936
|
-
conversationId:
|
|
937
|
-
|
|
759
|
+
conversationId: suppliedConversationId ?? options.existingRun?.input.conversationId ?? null,
|
|
760
|
+
autoConversation: suppliedConversationId
|
|
761
|
+
? false
|
|
762
|
+
: options.existingRun
|
|
763
|
+
? options.existingRun.input.autoConversation === true
|
|
764
|
+
: true,
|
|
765
|
+
userId: principalUserId(principal) ?? legacyUserId ?? null,
|
|
766
|
+
principal: principal ? safeJson(principal) : null,
|
|
767
|
+
initiator: initiator ? safeJson(initiator) : null,
|
|
768
|
+
audience: safeJson(audience),
|
|
938
769
|
projectId: options.projectId ?? options.existingRun?.input.projectId ?? null,
|
|
939
|
-
|
|
770
|
+
workspaceId: options.workspaceId ?? options.existingRun?.input.workspaceId ?? null,
|
|
771
|
+
tenantId: options.tenantId ?? options.existingRun?.input.tenantId ?? null,
|
|
772
|
+
delivery: isJsonObject(replyTarget.delivery) ? replyTarget.delivery : null,
|
|
773
|
+
replyTarget,
|
|
940
774
|
metadata: options.metadata ?? options.turn?.metadata ?? {},
|
|
775
|
+
sandboxCredentials: options.sandboxCredentials ?? (options.existingRun && isJsonObject(options.existingRun.input.sandboxCredentials) ? options.existingRun.input.sandboxCredentials : {}),
|
|
776
|
+
...(options.replay !== undefined ? { replay: safeJson(options.replay) } : {}),
|
|
941
777
|
...(options.eval !== undefined ? { eval: validateEvalRunOptions(options.eval) } : {})
|
|
942
778
|
};
|
|
779
|
+
await rememberDefaultOutboundRoute({ manifest: this.manifest, state: this.state, agentScope: this.durableAgentScope(), now: this.now() }, options, runInput);
|
|
943
780
|
let run = options.existingRun
|
|
944
781
|
? await this.state.updateRun(options.existingRun.id, {
|
|
945
782
|
input: {
|
|
@@ -958,14 +795,20 @@ export class AssemblyLineRuntime {
|
|
|
958
795
|
catch (error) {
|
|
959
796
|
this.logger.warn("onRunCreated hook failed", { runId: run.id, error: error instanceof Error ? error.message : String(error) });
|
|
960
797
|
}
|
|
961
|
-
await this.state.appendEvent(run.id, "run.accepted", { agentRevision: this.manifest.agentRevision
|
|
962
|
-
if (
|
|
798
|
+
await this.state.appendEvent(run.id, "run.accepted", { agentRevision: this.manifest.agentRevision });
|
|
799
|
+
if (options.replay)
|
|
800
|
+
await recordRunReplayStarted(this.state, run.id, options.replay);
|
|
801
|
+
if (this.usesRevisionScopedDurableState() && (this.skillsConfig.enabled || this.connectionsConfig.dynamic)) {
|
|
963
802
|
await this.state.appendEvent(run.id, "agent.scope_fallback", {
|
|
964
803
|
reason: "missing_agent_id",
|
|
965
804
|
scope: this.manifest.agentRevision,
|
|
966
805
|
message: "Durable learned state is scoped to agentRevision because agent.id is not configured."
|
|
967
806
|
});
|
|
968
807
|
}
|
|
808
|
+
const preExecution = await this.state.getRun(run.id);
|
|
809
|
+
if (preExecution?.status === "cancelled") {
|
|
810
|
+
return this.result(preExecution, "Run was cancelled before execution started.");
|
|
811
|
+
}
|
|
969
812
|
run = await this.state.updateRun(run.id, { status: "running" });
|
|
970
813
|
const heartbeat = this.startRunHeartbeat(run.id);
|
|
971
814
|
const channelTurnStart = earlyChannelTurn
|
|
@@ -983,43 +826,101 @@ export class AssemblyLineRuntime {
|
|
|
983
826
|
await this.stopChannelTurn(channelLifecycle, run, channel);
|
|
984
827
|
};
|
|
985
828
|
try {
|
|
986
|
-
const
|
|
987
|
-
|
|
988
|
-
|
|
829
|
+
const channelModule = channelDefinition
|
|
830
|
+
? await this.loadChannelModule(channelDefinition)
|
|
831
|
+
: undefined;
|
|
832
|
+
const humanInputMode = humanInputModeForChannel(channelModule);
|
|
833
|
+
run = await this.state.updateRun(run.id, {
|
|
834
|
+
input: withHumanInputMode(run.input, humanInputMode)
|
|
835
|
+
});
|
|
836
|
+
await this.state.appendEvent(run.id, "human_input.route_selected", {
|
|
989
837
|
channel,
|
|
990
|
-
|
|
991
|
-
...(trustedProvider ? { trustedProvider } : {}),
|
|
992
|
-
...(resolveAttachment ? { resolveAttachment } : {}),
|
|
993
|
-
env: this.env,
|
|
994
|
-
fetch: this.fetch,
|
|
995
|
-
blob: this.blob,
|
|
996
|
-
state: this.state
|
|
838
|
+
mode: humanInputMode
|
|
997
839
|
});
|
|
840
|
+
const turnAttachments = options.attachments ?? options.turn?.attachments ?? [];
|
|
841
|
+
let attachments = [];
|
|
842
|
+
if (turnAttachments.length > 0) {
|
|
843
|
+
if (typeof run.input.conversationId !== "string" || !run.input.conversationId) {
|
|
844
|
+
run = await this.state.updateRun(run.id, {
|
|
845
|
+
input: { ...run.input, conversationId: run.id }
|
|
846
|
+
});
|
|
847
|
+
}
|
|
848
|
+
const fileWorkspace = await this.workspaceRuntime.service.resolveForRun(run);
|
|
849
|
+
const resolveAttachment = await this.channelAttachmentResolver(channelDefinition, trustedProvider);
|
|
850
|
+
attachments = await materializeTurnAttachments({
|
|
851
|
+
run,
|
|
852
|
+
workspaceId: fileWorkspace.id,
|
|
853
|
+
channel,
|
|
854
|
+
attachments: turnAttachments,
|
|
855
|
+
...(trustedProvider ? { trustedProvider } : {}),
|
|
856
|
+
...(resolveAttachment ? { resolveAttachment } : {}),
|
|
857
|
+
allowRemoteDownload: options.allowRemoteAttachments === true,
|
|
858
|
+
env: this.env,
|
|
859
|
+
fetch: this.fetch,
|
|
860
|
+
...(this.attachmentHostResolver ? { hostResolver: this.attachmentHostResolver } : {}),
|
|
861
|
+
blob: this.blob,
|
|
862
|
+
state: this.state
|
|
863
|
+
});
|
|
864
|
+
}
|
|
998
865
|
const hydratedOptions = { ...options, attachments };
|
|
999
866
|
if (options.turn)
|
|
1000
867
|
hydratedOptions.turn = { ...options.turn, attachments };
|
|
1001
868
|
const conversation = await this.prepareConversation(run, hydratedOptions, channel);
|
|
869
|
+
if (!conversation)
|
|
870
|
+
throw new Error("Every run must resolve a conversation before agent hook evaluation.");
|
|
871
|
+
hydratedOptions.conversationId = conversation.id;
|
|
872
|
+
const persistedInitiator = conversationInitiator(conversation.metadata) ?? initiatorFromRun(run);
|
|
873
|
+
if (persistedInitiator) {
|
|
874
|
+
hydratedOptions.initiator = persistedInitiator;
|
|
875
|
+
if (hydratedOptions.turn)
|
|
876
|
+
hydratedOptions.turn = { ...hydratedOptions.turn, initiator: persistedInitiator };
|
|
877
|
+
}
|
|
878
|
+
if (run.input.conversationId !== conversation.id || persistedInitiator) {
|
|
879
|
+
run = await this.state.updateRun(run.id, {
|
|
880
|
+
input: {
|
|
881
|
+
...run.input,
|
|
882
|
+
conversationId: conversation.id,
|
|
883
|
+
...(persistedInitiator ? { initiator: safeJson(persistedInitiator) } : {})
|
|
884
|
+
}
|
|
885
|
+
});
|
|
886
|
+
}
|
|
887
|
+
const hookController = await this.createAgentHookController(run, hydratedOptions, channel, conversation.id, attachments);
|
|
888
|
+
const capabilitySnapshot = await hookController.evaluate(options.existingRun ? "recovery" : "run_start");
|
|
889
|
+
const capabilities = capabilitySnapshot.declaration;
|
|
890
|
+
run = await this.state.updateRun(run.id, {
|
|
891
|
+
input: {
|
|
892
|
+
...run.input,
|
|
893
|
+
model: capabilities.model,
|
|
894
|
+
agentSandbox: capabilities.sandbox ?? null,
|
|
895
|
+
agentConnections: capabilities.connections,
|
|
896
|
+
agentSubagents: capabilities.subagents,
|
|
897
|
+
attachmentMetadata: attachments
|
|
898
|
+
}
|
|
899
|
+
});
|
|
900
|
+
const media = await processRuntimeTurnMedia(this, run, attachments, hydratedOptions, channel, principalUserId(principal) ?? legacyUserId, conversation.id);
|
|
1002
901
|
const augmentation = hydratedOptions.turn
|
|
1003
902
|
? await this.augmentChannelContext(channel, hydratedOptions.turn, run)
|
|
1004
903
|
: undefined;
|
|
1005
904
|
const recentHistory = hydratedOptions.recentHistory ??
|
|
1006
905
|
hydratedOptions.turn?.recentHistory ??
|
|
1007
906
|
augmentation?.recentHistory ??
|
|
1008
|
-
(conversation ? await this.recentHistory(conversation.id) : []);
|
|
907
|
+
(conversation ? await this.recentHistory(conversation.id, run.id) : []);
|
|
1009
908
|
const contextInput = {
|
|
1010
909
|
message: hydratedOptions.message,
|
|
1011
910
|
channel,
|
|
1012
911
|
recentHistory,
|
|
1013
912
|
attachments,
|
|
913
|
+
capabilities,
|
|
1014
914
|
run
|
|
1015
915
|
};
|
|
1016
|
-
|
|
1017
|
-
|
|
916
|
+
const channelContext = mergeJsonObjects(media.channelContext, augmentation?.channelContext);
|
|
917
|
+
if (channelContext)
|
|
918
|
+
contextInput.channelContext = channelContext;
|
|
1018
919
|
if (hydratedOptions.promptContext)
|
|
1019
920
|
contextInput.promptContext = hydratedOptions.promptContext;
|
|
1020
921
|
if (hydratedOptions.target)
|
|
1021
922
|
contextInput.target = hydratedOptions.target;
|
|
1022
|
-
|
|
923
|
+
let bundle = options.contextSnapshot ? structuredClone(options.contextSnapshot) : await this.buildContextBundle(contextInput);
|
|
1023
924
|
const contextBlob = await this.blob.put(`context/${run.id}.json`, JSON.stringify(bundle, null, 2), "application/json");
|
|
1024
925
|
run = await this.state.updateRun(run.id, { contextBundleId: contextBlob.id });
|
|
1025
926
|
await this.state.appendEvent(run.id, "context.bundle_built", { contextBundleId: contextBlob.id });
|
|
@@ -1028,44 +929,31 @@ export class AssemblyLineRuntime {
|
|
|
1028
929
|
name: "context.bundle_built",
|
|
1029
930
|
data: { contextBundleId: contextBlob.id }
|
|
1030
931
|
});
|
|
1031
|
-
const missingConnections = this.missingRequiredConnections();
|
|
1032
|
-
if (missingConnections.length > 0) {
|
|
1033
|
-
const waitingRun = await this.state.updateRun(run.id, { status: "waiting_for_connection" });
|
|
1034
|
-
await this.state.appendEvent(run.id, "connection.required", {
|
|
1035
|
-
missingConnections,
|
|
1036
|
-
recoverable: true
|
|
1037
|
-
});
|
|
1038
|
-
await this.emitSpan("ai.assembly-line.turn", spanStartedAt, this.runSpanAttributes(waitingRun, {
|
|
1039
|
-
status: "waiting_for_connection"
|
|
1040
|
-
}), {
|
|
1041
|
-
spanId: this.turnSpanId(waitingRun.id),
|
|
1042
|
-
status: "ok"
|
|
1043
|
-
});
|
|
1044
|
-
await this.emitSpan("assembly-line.run", spanStartedAt, {
|
|
1045
|
-
runId: run.id,
|
|
1046
|
-
status: "waiting_for_connection",
|
|
1047
|
-
agentRevision: this.manifest.agentRevision
|
|
1048
|
-
});
|
|
1049
|
-
return this.result(waitingRun, `Connection required: ${missingConnections.join(", ")}`, false, false, true);
|
|
1050
|
-
}
|
|
1051
|
-
const resolution = await this.resolveRunCapabilities(run, hydratedOptions, conversation?.id);
|
|
1052
932
|
const sandboxHandle = this.createSandboxHandle(() => run, (nextRun) => {
|
|
1053
933
|
run = nextRun;
|
|
1054
934
|
}, () => bundle);
|
|
1055
935
|
await this.state.appendEvent(run.id, "harness.started", { harness: this.manifest.gateway.runtime?.kind ?? "node" });
|
|
1056
|
-
const
|
|
1057
|
-
const targetInstructions = resolution?.instructions
|
|
1058
|
-
? `${baseInstructions}\n\n${resolution.instructions}`
|
|
1059
|
-
: baseInstructions;
|
|
936
|
+
const targetInstructions = await this.instructionsForRunTarget(run, hydratedOptions.target, bundle.instructions);
|
|
1060
937
|
let response = options.message;
|
|
1061
938
|
let structuredOutput;
|
|
1062
939
|
const tool = this.selectTool(hydratedOptions);
|
|
1063
940
|
if (tool) {
|
|
941
|
+
if (!capabilities.tools.includes(tool.name) && tool.visibility !== "deferred") {
|
|
942
|
+
const message = `Forced tool ${tool.name} is not enabled by the current agent capability snapshot.`;
|
|
943
|
+
const error = new Error(message);
|
|
944
|
+
error.name = "AgentCapabilityViolationError";
|
|
945
|
+
run = await failRunImpl({ state: this.state }, run.id, {
|
|
946
|
+
reason: "run.capability_violation",
|
|
947
|
+
error: message,
|
|
948
|
+
data: { toolName: tool.name }
|
|
949
|
+
});
|
|
950
|
+
throw error;
|
|
951
|
+
}
|
|
1064
952
|
const modelSpanStartedAt = timestamp();
|
|
1065
|
-
await this.state.appendEvent(run.id, "model.request_started", { model:
|
|
1066
|
-
await this.state.appendEvent(run.id, "model.response_completed", { model:
|
|
953
|
+
await this.state.appendEvent(run.id, "model.request_started", { model: capabilities.model, forcedTool: tool.name });
|
|
954
|
+
await this.state.appendEvent(run.id, "model.response_completed", { model: capabilities.model, simulated: true });
|
|
1067
955
|
await this.emitSpan("ai.streamText", modelSpanStartedAt, this.runSpanAttributes(run, {
|
|
1068
|
-
model:
|
|
956
|
+
model: capabilities.model,
|
|
1069
957
|
stepIndex: 0,
|
|
1070
958
|
forcedTool: tool.name,
|
|
1071
959
|
simulated: true,
|
|
@@ -1096,21 +984,23 @@ export class AssemblyLineRuntime {
|
|
|
1096
984
|
sandboxHandle,
|
|
1097
985
|
message: hydratedOptions.message,
|
|
1098
986
|
channel,
|
|
987
|
+
controller: hookController,
|
|
988
|
+
refreshBundle: async (nextCapabilities) => {
|
|
989
|
+
contextInput.capabilities = nextCapabilities;
|
|
990
|
+
run = await this.state.getRun(run.id) ?? run;
|
|
991
|
+
contextInput.run = run;
|
|
992
|
+
bundle = await this.buildContextBundle(contextInput);
|
|
993
|
+
return bundle;
|
|
994
|
+
},
|
|
1099
995
|
instructions: targetInstructions
|
|
1100
996
|
};
|
|
1101
997
|
if (hydratedOptions.turn)
|
|
1102
998
|
loopInput.turn = hydratedOptions.turn;
|
|
1103
999
|
if (conversation?.id) {
|
|
1104
1000
|
loopInput.conversationId = conversation.id;
|
|
1105
|
-
|
|
1001
|
+
if (!options.contextSnapshot)
|
|
1002
|
+
loopInput.transcript = await this.loadConversationTranscript(conversation.id, run.id);
|
|
1106
1003
|
}
|
|
1107
|
-
// A host-forced model wins over the resolver; the resolver wins over the manifest default.
|
|
1108
|
-
if (model)
|
|
1109
|
-
loopInput.model = model;
|
|
1110
|
-
else if (resolution?.model)
|
|
1111
|
-
loopInput.model = resolution.model;
|
|
1112
|
-
if (resolution?.defaultTools)
|
|
1113
|
-
loopInput.defaultToolNames = resolution.defaultTools;
|
|
1114
1004
|
const outcome = await this.runHarnessLoop(loopInput);
|
|
1115
1005
|
run = outcome.run;
|
|
1116
1006
|
if (outcome.waitingForApproval || outcome.waitingForInput || outcome.waitingForConnection) {
|
|
@@ -1156,10 +1046,12 @@ export class AssemblyLineRuntime {
|
|
|
1156
1046
|
return result;
|
|
1157
1047
|
}
|
|
1158
1048
|
catch (error) {
|
|
1159
|
-
|
|
1160
|
-
|
|
1161
|
-
|
|
1162
|
-
|
|
1049
|
+
await handleRunExecutionError({
|
|
1050
|
+
state: this.state,
|
|
1051
|
+
logger: this.logger,
|
|
1052
|
+
deliveryQueueMaxAttempts: this.deliveryQueueMaxAttempts,
|
|
1053
|
+
now: () => this.now()
|
|
1054
|
+
}, run.id, error);
|
|
1163
1055
|
throw error;
|
|
1164
1056
|
}
|
|
1165
1057
|
finally {
|
|
@@ -1173,7 +1065,7 @@ export class AssemblyLineRuntime {
|
|
|
1173
1065
|
}
|
|
1174
1066
|
/** Bump `updatedAt` while a run executes; enforces the wall-clock deadline (run-heartbeat.ts). */
|
|
1175
1067
|
startRunHeartbeat(runId) {
|
|
1176
|
-
return startRunHeartbeatImpl({
|
|
1068
|
+
return trackActiveRunHeartbeat(this.activeRunExecutions, runId, startRunHeartbeatImpl({
|
|
1177
1069
|
state: this.state,
|
|
1178
1070
|
logger: this.logger,
|
|
1179
1071
|
runHeartbeatMs: this.runHeartbeatMs,
|
|
@@ -1185,10 +1077,10 @@ export class AssemblyLineRuntime {
|
|
|
1185
1077
|
controller.abort();
|
|
1186
1078
|
},
|
|
1187
1079
|
debugSwallow: (message, fields) => this.debugSwallow(message, fields)
|
|
1188
|
-
}, runId);
|
|
1080
|
+
}, runId));
|
|
1189
1081
|
}
|
|
1190
1082
|
registerRunAbort(runId, controller) {
|
|
1191
|
-
return registerRunAbortController(this.runAbortControllers, this.runDeadlines, runId, controller);
|
|
1083
|
+
return registerRunAbortController(this.runAbortControllers, this.runDeadlines, runId, controller, this.runControlIntents);
|
|
1192
1084
|
}
|
|
1193
1085
|
conversationContextHost() {
|
|
1194
1086
|
const runtime = this;
|
|
@@ -1199,6 +1091,7 @@ export class AssemblyLineRuntime {
|
|
|
1199
1091
|
coreToolPolicy: this.coreToolPolicy,
|
|
1200
1092
|
memoryStore: this.memoryStore,
|
|
1201
1093
|
skillStore: this.skillStore,
|
|
1094
|
+
skillBundleIndex: this.skillBundleIndex,
|
|
1202
1095
|
sourceLoader: this.sourceLoader,
|
|
1203
1096
|
get contextPolicyPromise() {
|
|
1204
1097
|
return runtime.contextPolicyPromise;
|
|
@@ -1211,15 +1104,16 @@ export class AssemblyLineRuntime {
|
|
|
1211
1104
|
warnSwallow: (message, fields) => this.warnSwallow(message, fields),
|
|
1212
1105
|
memoryScopeForRun: (run) => this.memoryScopeForRun(run),
|
|
1213
1106
|
durableAgentScope: () => this.durableAgentScope(),
|
|
1214
|
-
ensureSkillsSeeded: () => this.ensureSkillsSeeded(),
|
|
1215
|
-
|
|
1107
|
+
ensureSkillsSeeded: (surfacePath) => this.ensureSkillsSeeded(surfacePath),
|
|
1108
|
+
skillScopeForSurface: (surfacePath) => this.skillScopeForSurface(surfacePath),
|
|
1109
|
+
surfaceForRun: (run) => surfaceForRun(this.manifest, run)
|
|
1216
1110
|
};
|
|
1217
1111
|
}
|
|
1218
1112
|
async prepareConversation(run, options, channel) {
|
|
1219
1113
|
return prepareConversationImpl(this.conversationContextHost(), run, options, channel);
|
|
1220
1114
|
}
|
|
1221
|
-
async recentHistory(conversationId) {
|
|
1222
|
-
return recentHistoryImpl(this.conversationContextHost(), conversationId);
|
|
1115
|
+
async recentHistory(conversationId, excludeRunId) {
|
|
1116
|
+
return recentHistoryImpl(this.conversationContextHost(), conversationId, excludeRunId);
|
|
1223
1117
|
}
|
|
1224
1118
|
async augmentChannelContext(channelName, turn, run) {
|
|
1225
1119
|
return augmentChannelContextImpl(this.conversationContextHost(), channelName, turn, run);
|
|
@@ -1258,28 +1152,34 @@ export class AssemblyLineRuntime {
|
|
|
1258
1152
|
return runtime.instrumentationConfig;
|
|
1259
1153
|
},
|
|
1260
1154
|
createConnectionRegistry: (channel, turn) => this.createConnectionRegistry(channel, turn),
|
|
1261
|
-
createConnectionRegistryForRun: (run, fallbackChannel, sandboxHandle) => this.createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle),
|
|
1155
|
+
createConnectionRegistryForRun: (run, fallbackChannel, sandboxHandle, selectedConnections) => this.createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle, selectedConnections),
|
|
1156
|
+
missingRequiredConnections: (selected) => this.missingRequiredConnections(selected),
|
|
1262
1157
|
visibleToolSet: (defaultToolNames, activeSkills) => this.visibleToolSet(defaultToolNames, activeSkills),
|
|
1263
|
-
modelTools: (activeToolNames, connectionRegistry, discoveredConnectionTools) => this.modelTools(activeToolNames, connectionRegistry, discoveredConnectionTools),
|
|
1158
|
+
modelTools: (run, activeToolNames, connectionRegistry, discoveredConnectionTools, options) => this.modelTools(run, activeToolNames, connectionRegistry, discoveredConnectionTools, options),
|
|
1264
1159
|
harnessExecuteTool: (call, state) => this.harnessExecuteTool(call, state),
|
|
1265
1160
|
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
1161
|
+
hydrateCheckpointData: (data) => this.hydrateCheckpointData(data),
|
|
1266
1162
|
emitSpan: (name, startedAt, attributes, options) => this.emitSpan(name, startedAt, attributes, options),
|
|
1267
1163
|
runSpanAttributes: (run, extra) => this.runSpanAttributes(run, extra),
|
|
1268
1164
|
turnSpanId: (runId) => this.turnSpanId(runId)
|
|
1269
1165
|
};
|
|
1270
1166
|
}
|
|
1271
1167
|
async resolveAgentHarness(modelSpec) {
|
|
1272
|
-
|
|
1273
|
-
|
|
1274
|
-
|
|
1275
|
-
return
|
|
1168
|
+
const resolvedModel = modelSpec ?? this.manifest.possibleModels[0];
|
|
1169
|
+
if (!resolvedModel)
|
|
1170
|
+
throw new Error("No compiled model is available for harness resolution.");
|
|
1171
|
+
return resolveAgentHarnessImpl(this.harnessLoopHost(), resolvedModel);
|
|
1276
1172
|
}
|
|
1277
1173
|
async runHarnessLoop(input) {
|
|
1278
1174
|
return runHarnessLoopImpl(this.harnessLoopHost(), input);
|
|
1279
1175
|
}
|
|
1280
1176
|
/** Load the conversation's stored transcript for resume, or undefined when disabled/absent. */
|
|
1281
1177
|
async loadConversationTranscript(conversationId, runId) {
|
|
1282
|
-
return loadResumableConversationTranscriptImpl(this.conversationContextHost(), {
|
|
1178
|
+
return loadResumableConversationTranscriptImpl(this.conversationContextHost(), {
|
|
1179
|
+
state: this.state,
|
|
1180
|
+
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
1181
|
+
hydrateCheckpointData: (data) => this.hydrateCheckpointData(data)
|
|
1182
|
+
}, conversationId, runId);
|
|
1283
1183
|
}
|
|
1284
1184
|
createHarnessContext(session, loopState, resumed) {
|
|
1285
1185
|
return createHarnessContextImpl(this.harnessLoopHost(), session, loopState, resumed);
|
|
@@ -1328,29 +1228,37 @@ export class AssemblyLineRuntime {
|
|
|
1328
1228
|
ensureDynamicConnections: () => this.ensureDynamicConnections(),
|
|
1329
1229
|
withRunAdmission: (work) => this.withRunAdmission(work),
|
|
1330
1230
|
listHydratedCheckpoints: (runId) => this.listHydratedCheckpoints(runId),
|
|
1231
|
+
hydrateCheckpointData: (data) => this.hydrateCheckpointData(data),
|
|
1331
1232
|
resolveAgentHarness: (modelSpec) => this.resolveAgentHarness(modelSpec),
|
|
1233
|
+
ensureAgentHookController: (run) => this.ensureAgentHookController(run),
|
|
1234
|
+
resolvedInstructionsForRun: (run, bundle, capabilities) => resolvedHookInstructionsForRun(this.manifest, run, bundle.instructions, capabilities),
|
|
1332
1235
|
buildContextBundle: (input) => this.buildContextBundle(input),
|
|
1333
1236
|
createSandboxHandle: (getRun, setRun, getBundle) => this.createSandboxHandle(getRun, setRun, getBundle),
|
|
1334
1237
|
executeToolWithRecord: (run, tool, toolCall, input, sandboxHandle, approvedToolCall) => this.executeToolWithRecord(run, tool, toolCall, input, sandboxHandle, approvedToolCall),
|
|
1335
1238
|
executeConnectionToolWithRecord: (run, registry, toolName, toolCall, input) => this.executeConnectionToolWithRecord(run, registry, toolName, toolCall, input),
|
|
1336
1239
|
createConnectionRegistry: (channel, turn) => this.createConnectionRegistry(channel, turn),
|
|
1337
|
-
createConnectionRegistryForRun: (run, fallbackChannel, sandboxHandle) => this.createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle),
|
|
1240
|
+
createConnectionRegistryForRun: (run, fallbackChannel, sandboxHandle, selectedConnections) => this.createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle, selectedConnections),
|
|
1338
1241
|
createConnectionRegistryForSession: (session) => this.createConnectionRegistryForSession(session),
|
|
1339
1242
|
mergedConnections: () => this.mergedConnections(),
|
|
1340
1243
|
loadConnectionDefinition: (connection) => this.loadConnectionDefinition(connection),
|
|
1341
1244
|
startRunHeartbeat: (runId) => this.startRunHeartbeat(runId),
|
|
1342
1245
|
createHarnessContext: (session, loopState, resumed) => this.createHarnessContext(session, loopState, resumed),
|
|
1343
|
-
executeHarnessTurn: (harness, input, session, loopState, resumed) => executeHarnessTurnImpl(this.harnessLoopHost(), harness, input, session, loopState, resumed),
|
|
1246
|
+
executeHarnessTurn: (harness, input, session, loopState, resumed, refreshCapabilities) => executeHarnessTurnImpl(this.harnessLoopHost(), harness, input, session, loopState, resumed, refreshCapabilities),
|
|
1344
1247
|
persistHarnessContinuation: (runId, session, continuation, pause) => this.persistHarnessContinuation(runId, session, continuation, pause),
|
|
1345
1248
|
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
1346
1249
|
result: (run, response, waitingForApproval, waitingForInput, waitingForConnection) => this.result(run, response, waitingForApproval, waitingForInput, waitingForConnection),
|
|
1347
1250
|
completeRun: (run, sandboxHandle, response, channel, turn, conversationId) => this.completeRun(run, sandboxHandle, response, channel, turn, conversationId),
|
|
1348
|
-
runDeliveryChannel: (run) => this.runDeliveryChannel(run)
|
|
1251
|
+
runDeliveryChannel: (run) => this.runDeliveryChannel(run),
|
|
1252
|
+
enqueueConversationTurn: (input) => this.conversationTurnDispatcher.enqueue(input)
|
|
1349
1253
|
};
|
|
1350
1254
|
}
|
|
1351
1255
|
async replay(runId) {
|
|
1352
1256
|
return replayImpl(this.replayResumeHost(), runId);
|
|
1353
1257
|
}
|
|
1258
|
+
/** Start a new, isolated run from a terminal run's verified durable input snapshot. */
|
|
1259
|
+
async rerun(runId, lifecycle) {
|
|
1260
|
+
return rerunFromSnapshot({ runId, state: this.state, blob: this.blob, manifest: this.manifest, run: (options) => this.run(options) }, lifecycle);
|
|
1261
|
+
}
|
|
1354
1262
|
/** Resumes never consume run capacity (deadlock risk); they only count toward `onIdle()`. */
|
|
1355
1263
|
async resumeApproval(runId) {
|
|
1356
1264
|
const result = await this.withRunAdmission(() => this.resumeApprovalNow(runId));
|
|
@@ -1361,9 +1269,22 @@ export class AssemblyLineRuntime {
|
|
|
1361
1269
|
return resumeApprovalNowImpl(this.replayResumeHost(), runId);
|
|
1362
1270
|
}
|
|
1363
1271
|
async completeConnectionAuthorizationCallback(callback) {
|
|
1272
|
+
const authorizationSession = callback.params.state
|
|
1273
|
+
? await this.connectionAuthorizationSessionStore.getSessionByState(callback.params.state)
|
|
1274
|
+
: undefined;
|
|
1364
1275
|
const result = await completeConnectionAuthorizationCallbackImpl(this.replayResumeHost(), callback);
|
|
1365
1276
|
if (result.runResult)
|
|
1366
1277
|
await this.conversationTurnDispatcher.settleRunResult(result.runResult);
|
|
1278
|
+
if (authorizationSession) {
|
|
1279
|
+
await this.reconcileConnectionEvents({
|
|
1280
|
+
connection: authorizationSession.connectionName,
|
|
1281
|
+
principal: authorizationSession.principal,
|
|
1282
|
+
force: true
|
|
1283
|
+
}).catch((error) => this.logger.warn("connection event reconcile after authorization failed", {
|
|
1284
|
+
connection: authorizationSession.connectionName,
|
|
1285
|
+
error: error instanceof Error ? error.message : String(error)
|
|
1286
|
+
}));
|
|
1287
|
+
}
|
|
1367
1288
|
return result;
|
|
1368
1289
|
}
|
|
1369
1290
|
/**
|
|
@@ -1379,6 +1300,65 @@ export class AssemblyLineRuntime {
|
|
|
1379
1300
|
async beginConnectionAuthorization(connectionName, session = {}) {
|
|
1380
1301
|
return beginConnectionAuthorizationImpl(this.toolExecutionHost(), connectionName, session);
|
|
1381
1302
|
}
|
|
1303
|
+
connectionEventsHost(publicUrl) {
|
|
1304
|
+
const resolvedPublicUrl = publicUrl ?? this.connectionCallbackBaseUrl;
|
|
1305
|
+
return {
|
|
1306
|
+
manifest: this.manifest,
|
|
1307
|
+
env: this.env,
|
|
1308
|
+
fetch: this.fetch,
|
|
1309
|
+
logger: this.logger,
|
|
1310
|
+
agentScope: this.durableAgentScope(),
|
|
1311
|
+
store: this.connectionEventStore,
|
|
1312
|
+
grantStore: this.connectionGrantStore,
|
|
1313
|
+
...(resolvedPublicUrl ? { publicUrl: resolvedPublicUrl } : {}),
|
|
1314
|
+
createRegistry: (principal) => new RuntimeConnectionRegistry({
|
|
1315
|
+
connections: this.mergedConnections(),
|
|
1316
|
+
env: this.env,
|
|
1317
|
+
fetch: this.fetch,
|
|
1318
|
+
session: {
|
|
1319
|
+
channel: "connection-event",
|
|
1320
|
+
principal,
|
|
1321
|
+
...(principal.type === "user" ? { userId: principal.id } : {})
|
|
1322
|
+
},
|
|
1323
|
+
agentId: this.manifest.agent.id ?? this.manifest.agentRevision,
|
|
1324
|
+
grantStore: this.connectionGrantStore,
|
|
1325
|
+
authorizationSessionStore: this.connectionAuthorizationSessionStore,
|
|
1326
|
+
...(this.connectionCallbackBaseUrl ? { callbackBaseUrl: this.connectionCallbackBaseUrl } : {}),
|
|
1327
|
+
loadDefinition: async (connection) => this.loadConnectionDefinition(connection)
|
|
1328
|
+
}),
|
|
1329
|
+
dispatchAutomationEvent: (event) => this.dispatchAutomationEvent(event),
|
|
1330
|
+
appendAudit: (type, data) => this.state.appendRuntimeControlEvent(this.durableAgentScope(), type, data)
|
|
1331
|
+
};
|
|
1332
|
+
}
|
|
1333
|
+
async reconcileConnectionEvents(options = {}) {
|
|
1334
|
+
return reconcileConnectionEvents(this.connectionEventsHost(options.publicUrl), options);
|
|
1335
|
+
}
|
|
1336
|
+
async checkConnectionEvents(connection) {
|
|
1337
|
+
return checkConnectionEvents(this.connectionEventsHost(), connection);
|
|
1338
|
+
}
|
|
1339
|
+
async acceptConnectionEvent(connectionName, bindingId, request) {
|
|
1340
|
+
return acceptConnectionEvent(this.connectionEventsHost(), connectionName, bindingId, request);
|
|
1341
|
+
}
|
|
1342
|
+
async runDueConnectionEvents(options = {}) {
|
|
1343
|
+
return drainConnectionEventInbox(this.connectionEventsHost(), options);
|
|
1344
|
+
}
|
|
1345
|
+
startConnectionEventWorker(options = {}) {
|
|
1346
|
+
const intervalMs = positiveLimit(options.intervalMs, 1_000);
|
|
1347
|
+
const tick = () => this.runDueConnectionEvents({
|
|
1348
|
+
...(options.batchSize !== undefined ? { limit: options.batchSize } : {}),
|
|
1349
|
+
...(options.leaseForMs !== undefined ? { leaseForMs: options.leaseForMs } : {})
|
|
1350
|
+
}).catch((error) => this.logger.warn("connection event worker tick failed", { error: error instanceof Error ? error.message : String(error) }));
|
|
1351
|
+
void tick();
|
|
1352
|
+
const timer = setInterval(() => void tick(), intervalMs);
|
|
1353
|
+
timer.unref?.();
|
|
1354
|
+
const reconcile = () => this.reconcileConnectionEvents().catch((error) => this.logger.warn("connection event reconcile tick failed", {
|
|
1355
|
+
error: error instanceof Error ? error.message : String(error)
|
|
1356
|
+
}));
|
|
1357
|
+
void reconcile();
|
|
1358
|
+
const reconcileTimer = setInterval(() => void reconcile(), 60_000);
|
|
1359
|
+
reconcileTimer.unref?.();
|
|
1360
|
+
return { stop: () => { clearInterval(timer); clearInterval(reconcileTimer); } };
|
|
1361
|
+
}
|
|
1382
1362
|
/** Resumes never consume run capacity (deadlock risk); they only count toward `onIdle()`. */
|
|
1383
1363
|
async resumeInput(runId, answer) {
|
|
1384
1364
|
const result = await this.withRunAdmission(() => this.resumeInputNow(runId, answer));
|
|
@@ -1431,12 +1411,7 @@ export class AssemblyLineRuntime {
|
|
|
1431
1411
|
state: this.state,
|
|
1432
1412
|
boot: () => this.boot(),
|
|
1433
1413
|
durableAgentScope: () => this.durableAgentScope(),
|
|
1434
|
-
cacheRunControl: (runId, intent) =>
|
|
1435
|
-
if (intent)
|
|
1436
|
-
this.runControlIntents.set(runId, intent);
|
|
1437
|
-
else
|
|
1438
|
-
this.runControlIntents.delete(runId);
|
|
1439
|
-
}
|
|
1414
|
+
cacheRunControl: (runId, intent) => cacheRunControlSignal(this.runControlIntents, this.activeRunExecutions, this.runAbortControllers, runId, intent)
|
|
1440
1415
|
};
|
|
1441
1416
|
}
|
|
1442
1417
|
async resumeHarnessLoop(run, harness, restored, resume) {
|
|
@@ -1451,6 +1426,7 @@ export class AssemblyLineRuntime {
|
|
|
1451
1426
|
replay: (runId) => this.replay(runId),
|
|
1452
1427
|
listHydratedCheckpoints: (runId) => this.listHydratedCheckpoints(runId),
|
|
1453
1428
|
buildContextBundle: (input) => this.buildContextBundle(input),
|
|
1429
|
+
createSubagentHookController: (run, subagent, message, conversationId) => this.createSubagentHookController(run, subagent, message, conversationId),
|
|
1454
1430
|
createSandboxHandle: (getRun, setRun, getBundle) => this.createSandboxHandle(getRun, setRun, getBundle),
|
|
1455
1431
|
startRunHeartbeat: (runId) => this.startRunHeartbeat(runId),
|
|
1456
1432
|
runHarnessLoop: (input) => this.runHarnessLoop(input),
|
|
@@ -1471,7 +1447,15 @@ export class AssemblyLineRuntime {
|
|
|
1471
1447
|
return sendSubagentFollowupImpl(this.subagentExecutionHost(), childRunId, message);
|
|
1472
1448
|
}
|
|
1473
1449
|
async loadSkill(runId, skillName) {
|
|
1474
|
-
const
|
|
1450
|
+
const run = await this.state.getRun(runId);
|
|
1451
|
+
if (!run)
|
|
1452
|
+
throw new Error(`Run not found: ${runId}`);
|
|
1453
|
+
const controller = await this.ensureAgentHookController(run);
|
|
1454
|
+
const snapshot = await controller.refreshIfDirty();
|
|
1455
|
+
if (!snapshot.declaration.skills.includes(skillName)) {
|
|
1456
|
+
throw new Error(`Skill ${skillName} is not enabled by the current agent capability snapshot.`);
|
|
1457
|
+
}
|
|
1458
|
+
const loaded = await this.skillLoadDetails(run, skillName);
|
|
1475
1459
|
const output = {
|
|
1476
1460
|
name: loaded.name,
|
|
1477
1461
|
skillName: loaded.name,
|
|
@@ -1556,7 +1540,7 @@ export class AssemblyLineRuntime {
|
|
|
1556
1540
|
shouldStartScheduler() {
|
|
1557
1541
|
if (this.schedulerEnabled === false)
|
|
1558
1542
|
return false;
|
|
1559
|
-
if (this.env.
|
|
1543
|
+
if (this.env.ASSEMBLY_LINE_SCHEDULER_ENABLED === "false" || this.env.ASSEMBLY_LINE_SCHEDULER_ENABLED === "0")
|
|
1560
1544
|
return false;
|
|
1561
1545
|
return true;
|
|
1562
1546
|
}
|
|
@@ -1580,6 +1564,8 @@ export class AssemblyLineRuntime {
|
|
|
1580
1564
|
runHeartbeatMs: this.runHeartbeatMs,
|
|
1581
1565
|
sandboxSyncMaxAttempts: this.sandboxSyncMaxAttempts,
|
|
1582
1566
|
deliveryQueueMaxAttempts: this.deliveryQueueMaxAttempts,
|
|
1567
|
+
connectionAuthorizationSessionStore: this.connectionAuthorizationSessionStore,
|
|
1568
|
+
missingRequiredConnections: (selected) => this.missingRequiredConnections(selected),
|
|
1583
1569
|
resumeRunFromContinuation: (run, context) => this.withRunAdmission(() => this.resumeRunFromContinuation(run, context)),
|
|
1584
1570
|
listHydratedCheckpoints: (runId) => this.listHydratedCheckpoints(runId)
|
|
1585
1571
|
};
|
|
@@ -1594,7 +1580,7 @@ export class AssemblyLineRuntime {
|
|
|
1594
1580
|
async resumeRunFromContinuation(run, context) {
|
|
1595
1581
|
return resumeRunFromContinuationImpl(this.replayResumeHost(), run, context);
|
|
1596
1582
|
}
|
|
1597
|
-
/** Start delivery, sandbox-sync, conversation-turn, and orphan-recovery workers. */
|
|
1583
|
+
/** Start delivery, sandbox-sync, conversation-turn, background-review, and orphan-recovery workers. */
|
|
1598
1584
|
startBackgroundWorkers(options = {}) {
|
|
1599
1585
|
return startBackgroundWorkersImpl({
|
|
1600
1586
|
env: this.env,
|
|
@@ -1603,6 +1589,8 @@ export class AssemblyLineRuntime {
|
|
|
1603
1589
|
startDeliveryWorker: (workerOptions) => this.startDeliveryWorker(workerOptions),
|
|
1604
1590
|
startSandboxSyncWorker: (workerOptions) => this.startSandboxSyncWorker(workerOptions),
|
|
1605
1591
|
startConversationTurnWorker: (workerOptions) => this.conversationTurnDispatcher.startWorker(workerOptions?.intervalMs),
|
|
1592
|
+
startBackgroundReviewWorker: (workerOptions) => this.startBackgroundReviewWorker(workerOptions),
|
|
1593
|
+
startConnectionEventWorker: (workerOptions) => this.startConnectionEventWorker(workerOptions),
|
|
1606
1594
|
recoverIncompleteRuns: (recoveryOptions) => this.recoverIncompleteRuns(recoveryOptions),
|
|
1607
1595
|
agentEnabled: () => this.agentEnabled()
|
|
1608
1596
|
}, options);
|
|
@@ -1647,6 +1635,10 @@ export class AssemblyLineRuntime {
|
|
|
1647
1635
|
deliveryQueueLeaseMs: this.deliveryQueueLeaseMs,
|
|
1648
1636
|
deliveryQueueMaxAttempts: this.deliveryQueueMaxAttempts,
|
|
1649
1637
|
sandboxSyncMaxAttempts: this.sandboxSyncMaxAttempts,
|
|
1638
|
+
workspaceFilesForDelivery: async (run) => {
|
|
1639
|
+
const workspace = await this.workspaceRuntime.service.resolveForRun(run);
|
|
1640
|
+
return (await this.workspaceRuntime.service.loadManifest(workspace)).manifest.entries;
|
|
1641
|
+
},
|
|
1650
1642
|
result: (run, response, waitingForApproval, waitingForInput, waitingForConnection) => this.result(run, response, waitingForApproval, waitingForInput, waitingForConnection),
|
|
1651
1643
|
sandboxSessionKey: (run) => this.sandboxSessionKey(run),
|
|
1652
1644
|
debugSwallow: (message, fields) => this.debugSwallow(message, fields),
|
|
@@ -1664,9 +1656,6 @@ export class AssemblyLineRuntime {
|
|
|
1664
1656
|
async latestRunFailureMessage(runId) {
|
|
1665
1657
|
return latestRunFailureMessageImpl(this.deliverySendHost(), runId);
|
|
1666
1658
|
}
|
|
1667
|
-
async enqueueSandboxSyncAfterDelivery(run, sandboxSession) {
|
|
1668
|
-
return enqueueSandboxSyncAfterDeliveryImpl(this.deliverySendHost(), run, sandboxSession);
|
|
1669
|
-
}
|
|
1670
1659
|
sandboxSyncWorkerHost() {
|
|
1671
1660
|
return {
|
|
1672
1661
|
state: this.state,
|
|
@@ -1681,6 +1670,7 @@ export class AssemblyLineRuntime {
|
|
|
1681
1670
|
readSandboxTombstonesWithMissingProjectedFiles: (sandbox) => this.readSandboxTombstonesWithMissingProjectedFiles(sandbox),
|
|
1682
1671
|
syncMemoryFromSandbox: (run, sandboxSession, tombstones) => this.syncMemoryFromSandbox(run, sandboxSession, tombstones),
|
|
1683
1672
|
syncSkillsFromSandbox: (run, sandboxSession, tombstones) => this.syncSkillsFromSandbox(run, sandboxSession, tombstones),
|
|
1673
|
+
syncWorkspace: (run, sandboxSession, syncJob) => this.workspaceRuntime.sync(run, sandboxSession, syncJob),
|
|
1684
1674
|
emitSpan: (name, startedAt, attributes, options) => this.emitSpan(name, startedAt, attributes, options),
|
|
1685
1675
|
runSpanAttributes: (run, extra) => this.runSpanAttributes(run, extra),
|
|
1686
1676
|
turnSpanId: (runId) => this.turnSpanId(runId),
|
|
@@ -1729,14 +1719,14 @@ export class AssemblyLineRuntime {
|
|
|
1729
1719
|
visibleToolSet(defaultToolNames, activeSkills) {
|
|
1730
1720
|
return visibleToolSetImpl(this.toolExecutionHost(), defaultToolNames, activeSkills);
|
|
1731
1721
|
}
|
|
1732
|
-
async skillLoadDetails(skillName) {
|
|
1733
|
-
return skillLoadDetailsImpl(this.toolExecutionHost(), skillName);
|
|
1722
|
+
async skillLoadDetails(run, skillName) {
|
|
1723
|
+
return skillLoadDetailsImpl(this.toolExecutionHost(), run, skillName);
|
|
1734
1724
|
}
|
|
1735
1725
|
async instructionsForRunTarget(run, target, baseInstructions) {
|
|
1736
|
-
return instructionsForRunTargetImpl({ appendEvent: (runId, type, data) => this.state.appendEvent(runId, type, data), skillLoadDetails: (skillName) => this.skillLoadDetails(skillName) }, run, target, baseInstructions);
|
|
1726
|
+
return instructionsForRunTargetImpl({ appendEvent: (runId, type, data) => this.state.appendEvent(runId, type, data), skillLoadDetails: (skillName) => this.skillLoadDetails(run, skillName) }, run, target, baseInstructions);
|
|
1737
1727
|
}
|
|
1738
|
-
async modelTools(activeToolNames, connectionRegistry, discoveredConnectionTools = new Map()) {
|
|
1739
|
-
return modelToolsImpl(this.toolExecutionHost(), activeToolNames, connectionRegistry, discoveredConnectionTools);
|
|
1728
|
+
async modelTools(run, activeToolNames, connectionRegistry, discoveredConnectionTools = new Map(), options) {
|
|
1729
|
+
return modelToolsImpl(this.toolExecutionHost(), run, activeToolNames, connectionRegistry, discoveredConnectionTools, options);
|
|
1740
1730
|
}
|
|
1741
1731
|
async harnessExecuteTool(call, state) {
|
|
1742
1732
|
return harnessExecuteToolImpl(this.toolExecutionHost(), call, state);
|
|
@@ -1744,8 +1734,8 @@ export class AssemblyLineRuntime {
|
|
|
1744
1734
|
createConnectionRegistry(channel, turn) {
|
|
1745
1735
|
return createConnectionRegistryImpl(this.toolExecutionHost(), channel, turn);
|
|
1746
1736
|
}
|
|
1747
|
-
createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle) {
|
|
1748
|
-
return createConnectionRegistryForRunImpl(this.toolExecutionHost(), run, fallbackChannel, sandboxHandle);
|
|
1737
|
+
createConnectionRegistryForRun(run, fallbackChannel, sandboxHandle, selectedConnections) {
|
|
1738
|
+
return createConnectionRegistryForRunImpl(this.toolExecutionHost(), run, fallbackChannel, sandboxHandle, selectedConnections);
|
|
1749
1739
|
}
|
|
1750
1740
|
createConnectionRegistryForSession(session) {
|
|
1751
1741
|
return createConnectionRegistryForSessionImpl(this.toolExecutionHost(), session);
|
|
@@ -1779,12 +1769,18 @@ export class AssemblyLineRuntime {
|
|
|
1779
1769
|
env: this.env,
|
|
1780
1770
|
fetch: this.fetch,
|
|
1781
1771
|
state: this.state,
|
|
1782
|
-
blob: this.blob
|
|
1772
|
+
blob: this.blob,
|
|
1773
|
+
agent: {
|
|
1774
|
+
start: (turn) => startChannelAgentTurnImpl(this.channelIngressHost(), channel.name, turn),
|
|
1775
|
+
observe: (observation) => observeChannelMessageImpl(this.channelIngressHost(), channel, observation),
|
|
1776
|
+
cancel: (runId) => this.cancelRun(runId)
|
|
1777
|
+
}
|
|
1783
1778
|
};
|
|
1784
1779
|
}
|
|
1785
|
-
missingRequiredConnections() {
|
|
1780
|
+
missingRequiredConnections(selected) {
|
|
1781
|
+
const selectedNames = new Set(selected);
|
|
1786
1782
|
return this.manifest.connections
|
|
1787
|
-
.filter((connection) => connection.required && connection.protocol === "declaration")
|
|
1783
|
+
.filter((connection) => selectedNames.has(connection.name) && connection.required && connection.protocol === "declaration")
|
|
1788
1784
|
.map((connection) => connection.name)
|
|
1789
1785
|
.filter((name) => this.connections[name] === undefined);
|
|
1790
1786
|
}
|
|
@@ -1796,11 +1792,11 @@ export class AssemblyLineRuntime {
|
|
|
1796
1792
|
this.instrumentationLoaded = true;
|
|
1797
1793
|
return;
|
|
1798
1794
|
}
|
|
1799
|
-
const instrumentation =
|
|
1795
|
+
const instrumentation = this.manifest.instrumentation
|
|
1796
|
+
? await this.sourceLoader.load(this.manifest.instrumentation)
|
|
1797
|
+
: {};
|
|
1800
1798
|
const defaultExport = instrumentation.default;
|
|
1801
1799
|
const definition = isInstrumentationDefinition(defaultExport) ? defaultExport : undefined;
|
|
1802
|
-
// Host/gateway-supplied instrumentation wins over instrumentation.ts, mirroring
|
|
1803
|
-
// the telemetry-sink precedence below.
|
|
1804
1800
|
if (definition && !this.hostInstrumentationProvided) {
|
|
1805
1801
|
this.instrumentationConfig = {
|
|
1806
1802
|
recordInputs: definition.recordInputs ?? false,
|
|
@@ -1826,7 +1822,7 @@ export class AssemblyLineRuntime {
|
|
|
1826
1822
|
this.instrumentationLoaded = true;
|
|
1827
1823
|
}
|
|
1828
1824
|
agentName() {
|
|
1829
|
-
return this.manifest.agent.name ?? this.manifest.agent.description ?? `
|
|
1825
|
+
return this.manifest.agent.name ?? this.manifest.agent.description ?? `assembly-line-${this.manifest.agentRevision.slice(0, 12)}`;
|
|
1830
1826
|
}
|
|
1831
1827
|
traceIdForRun(runId) {
|
|
1832
1828
|
return createHash("sha256").update(runId).digest("hex").slice(0, 32);
|
|
@@ -1853,11 +1849,13 @@ export class AssemblyLineRuntime {
|
|
|
1853
1849
|
toolExecutionHost() {
|
|
1854
1850
|
return {
|
|
1855
1851
|
state: this.state,
|
|
1852
|
+
blob: this.blob,
|
|
1856
1853
|
env: this.env,
|
|
1857
1854
|
fetch: this.fetch,
|
|
1858
1855
|
manifest: this.manifest,
|
|
1859
1856
|
coreToolPolicy: this.coreToolPolicy,
|
|
1860
1857
|
skillStore: this.skillStore,
|
|
1858
|
+
skillBundleIndex: this.skillBundleIndex,
|
|
1861
1859
|
memoryStore: this.memoryStore,
|
|
1862
1860
|
sandbox: this.sandbox,
|
|
1863
1861
|
connections: this.connections,
|
|
@@ -1867,11 +1865,13 @@ export class AssemblyLineRuntime {
|
|
|
1867
1865
|
toolOutputMaxChars: this.toolOutputMaxChars,
|
|
1868
1866
|
toolTimeoutMs: this.toolTimeoutMs,
|
|
1869
1867
|
sandboxSyncMaxAttempts: this.sandboxSyncMaxAttempts,
|
|
1870
|
-
|
|
1868
|
+
skillsConfigForRun: (run) => this.skillsConfigForRun(run),
|
|
1871
1869
|
schedulesConfig: this.schedulesConfig,
|
|
1872
1870
|
connectionsConfig: this.connectionsConfig,
|
|
1873
|
-
|
|
1874
|
-
|
|
1871
|
+
surfaceForRun: (run) => surfaceForRun(this.manifest, run),
|
|
1872
|
+
agentStateForRun: (runId) => this.agentStateForRun(runId),
|
|
1873
|
+
ensureSkillsSeeded: (run) => this.ensureSkillsSeeded(surfaceForRun(this.manifest, run).path),
|
|
1874
|
+
skillScopeForRun: (run) => this.skillScopeForRun(run),
|
|
1875
1875
|
scheduleScopeForRun: (run) => this.scheduleScopeForRun(run),
|
|
1876
1876
|
memoryScopeForRun: (run) => this.memoryScopeForRun(run),
|
|
1877
1877
|
sandboxSessionKey: (run) => this.sandboxSessionKey(run),
|
|
@@ -1884,13 +1884,14 @@ export class AssemblyLineRuntime {
|
|
|
1884
1884
|
recordSandboxTombstone: (run, sandbox, path) => this.recordSandboxTombstone(run, sandbox, path),
|
|
1885
1885
|
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
1886
1886
|
listHydratedCheckpoints: (runId) => this.listHydratedCheckpoints(runId),
|
|
1887
|
+
executeWorkspaceTool: (run, toolName, input, sandboxHandle) => this.workspaceRuntime.executeTool(run, toolName, input, sandboxHandle),
|
|
1887
1888
|
emitSpan: (name, startedAt, attributes, options) => this.emitSpan(name, startedAt, attributes, options),
|
|
1888
1889
|
runSpanAttributes: (run, extra) => this.runSpanAttributes(run, extra),
|
|
1889
1890
|
turnSpanId: (runId) => this.turnSpanId(runId),
|
|
1890
1891
|
toolContentAttributes: (input, output) => this.toolContentAttributes(input, output),
|
|
1891
|
-
saveSkill: (input) => this.saveSkill(input),
|
|
1892
|
-
listSkills: () => this.listSkills(),
|
|
1893
|
-
deleteSkill: (name) => this.deleteSkill(name),
|
|
1892
|
+
saveSkill: (input, run) => this.saveSkill(input, surfaceForRun(this.manifest, run).path),
|
|
1893
|
+
listSkills: (run) => this.listSkills(surfaceForRun(this.manifest, run).path),
|
|
1894
|
+
deleteSkill: (name, run) => this.deleteSkill(name, surfaceForRun(this.manifest, run).path),
|
|
1894
1895
|
createDynamicSchedule: (input) => this.createDynamicSchedule(input),
|
|
1895
1896
|
listDynamicSchedules: (scope) => this.listDynamicSchedules(scope),
|
|
1896
1897
|
updateDynamicSchedule: (scope, id, patch) => this.updateDynamicSchedule(scope, id, patch),
|
|
@@ -1930,11 +1931,14 @@ export class AssemblyLineRuntime {
|
|
|
1930
1931
|
blob: this.blob,
|
|
1931
1932
|
memoryStore: this.memoryStore,
|
|
1932
1933
|
skillStore: this.skillStore,
|
|
1934
|
+
skillBundleIndex: this.skillBundleIndex,
|
|
1935
|
+
skillResourceReader: this.skillResourceReader,
|
|
1933
1936
|
resourceProjectionPolicy: this.resourceProjectionPolicy,
|
|
1934
1937
|
memoryEmbeddingProvider: this.memoryEmbeddingProvider,
|
|
1935
1938
|
memoryEmbeddingsEnabled: this.memoryEmbeddingsEnabled,
|
|
1936
|
-
|
|
1937
|
-
durableAgentScope: () => this.durableAgentScope()
|
|
1939
|
+
skillScopeForRun: (run) => this.skillScopeForRun(run),
|
|
1940
|
+
durableAgentScope: () => this.durableAgentScope(),
|
|
1941
|
+
surfaceForRun: (run) => surfaceForRun(this.manifest, run)
|
|
1938
1942
|
};
|
|
1939
1943
|
}
|
|
1940
1944
|
async listResourcesForRun(run, scope, input = {}) {
|
|
@@ -1949,6 +1953,9 @@ export class AssemblyLineRuntime {
|
|
|
1949
1953
|
async projectSkillIntoSandbox(run, sandbox, skillName) {
|
|
1950
1954
|
return projectSkillIntoSandboxImpl(this.resourceProjectionHost(), run, sandbox, skillName);
|
|
1951
1955
|
}
|
|
1956
|
+
async projectLoadedSkillsIntoSandbox(run, sandbox) {
|
|
1957
|
+
return projectLoadedSkillsIntoSandboxImpl(this.resourceProjectionHost(), run, sandbox);
|
|
1958
|
+
}
|
|
1952
1959
|
async hydrateLogicalPathForTool(run, sandbox, path, options = {}) {
|
|
1953
1960
|
return hydrateLogicalPathForToolImpl(this.resourceProjectionHost(), run, sandbox, path, options);
|
|
1954
1961
|
}
|
|
@@ -1967,33 +1974,117 @@ export class AssemblyLineRuntime {
|
|
|
1967
1974
|
async runMemoryEmbeddingBackfill(options = {}) {
|
|
1968
1975
|
return runMemoryEmbeddingBackfillImpl(this.resourceProjectionHost(), options);
|
|
1969
1976
|
}
|
|
1970
|
-
|
|
1971
|
-
|
|
1972
|
-
if (
|
|
1973
|
-
|
|
1974
|
-
|
|
1975
|
-
|
|
1976
|
-
|
|
1977
|
-
|
|
1978
|
-
|
|
1977
|
+
async dispatchHookEvent(runId, event) {
|
|
1978
|
+
await this.eventHandlers?.dispatch(runId, event);
|
|
1979
|
+
if (this.eventHandlers)
|
|
1980
|
+
removeTerminalAgentHookState(runId, event, this.eventHandlers, this.agentHookControllers, this.agentStateHandles);
|
|
1981
|
+
}
|
|
1982
|
+
async handleRuntimeEvent(runId, event) {
|
|
1983
|
+
await this.dispatchHookEvent(runId, event);
|
|
1984
|
+
await this.runtimeLearning.handleRuntimeEvent(runId, event.type);
|
|
1985
|
+
}
|
|
1986
|
+
async createAgentHookController(run, options, channel, conversationId, attachments) {
|
|
1987
|
+
const disabledTools = this.disabledToolsForRun(run);
|
|
1988
|
+
const surface = rootAgentSurface(this.manifest);
|
|
1989
|
+
const liveSkills = (await this.listSkills(surface.path)).map((skill) => skill.name).sort();
|
|
1990
|
+
const baseCatalog = hookCapabilityCatalog(this.manifest, surface);
|
|
1991
|
+
const created = await createRuntimeAgentHookController({
|
|
1992
|
+
manifest: this.manifest,
|
|
1993
|
+
state: this.state,
|
|
1994
|
+
blob: this.blob,
|
|
1995
|
+
sourceLoader: this.sourceLoader,
|
|
1996
|
+
eventHandlers: this.eventHandlers,
|
|
1997
|
+
logger: this.logger,
|
|
1998
|
+
agentScope: this.durableAgentScope(),
|
|
1999
|
+
conversationId,
|
|
2000
|
+
run: immutableAgentRunContext({
|
|
2001
|
+
id: run.id,
|
|
2002
|
+
message: options.message,
|
|
2003
|
+
channel,
|
|
2004
|
+
conversationId,
|
|
2005
|
+
...(typeof run.input.userId === "string" ? { userId: run.input.userId } : {}),
|
|
2006
|
+
...(principalFromRun(run) ? { principal: principalFromRun(run) } : {}),
|
|
2007
|
+
...(initiatorFromRun(run) ? { initiator: initiatorFromRun(run) } : {}),
|
|
2008
|
+
audience: audienceFromRun(run),
|
|
2009
|
+
...((options.metadata ?? options.turn?.metadata) ? {
|
|
2010
|
+
metadata: (options.metadata ?? options.turn?.metadata)
|
|
2011
|
+
} : {}),
|
|
2012
|
+
attachments
|
|
2013
|
+
}),
|
|
2014
|
+
surface,
|
|
2015
|
+
catalog: { ...baseCatalog, skills: new Set(liveSkills) },
|
|
2016
|
+
defaultSkills: liveSkills,
|
|
2017
|
+
disabledTools,
|
|
2018
|
+
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
2019
|
+
listCheckpoints: (runId) => this.listHydratedCheckpoints(runId)
|
|
1979
2020
|
});
|
|
1980
|
-
|
|
1981
|
-
|
|
1982
|
-
|
|
1983
|
-
|
|
1984
|
-
|
|
1985
|
-
|
|
1986
|
-
|
|
1987
|
-
|
|
1988
|
-
|
|
1989
|
-
if (options.metadata !== undefined)
|
|
1990
|
-
input.metadata = options.metadata;
|
|
1991
|
-
return resolveRunCapabilitiesImpl({
|
|
2021
|
+
this.agentStateHandles.set(run.id, created.agentState);
|
|
2022
|
+
this.agentHookControllers.set(run.id, created.controller);
|
|
2023
|
+
return created.controller;
|
|
2024
|
+
}
|
|
2025
|
+
async createSubagentHookController(run, subagent, message, conversationId) {
|
|
2026
|
+
const surface = subagentSurface(subagent);
|
|
2027
|
+
const liveSkills = (await this.listSkills(surface.path)).map((skill) => skill.name).sort();
|
|
2028
|
+
const baseCatalog = hookCapabilityCatalog(this.manifest, surface);
|
|
2029
|
+
const created = await createRuntimeAgentHookController({
|
|
1992
2030
|
manifest: this.manifest,
|
|
1993
|
-
|
|
1994
|
-
|
|
1995
|
-
|
|
1996
|
-
|
|
2031
|
+
state: this.state,
|
|
2032
|
+
blob: this.blob,
|
|
2033
|
+
sourceLoader: this.sourceLoader,
|
|
2034
|
+
eventHandlers: this.eventHandlers,
|
|
2035
|
+
logger: this.logger,
|
|
2036
|
+
agentScope: `${this.durableAgentScope()}:subagent:${subagent.path}`,
|
|
2037
|
+
conversationId,
|
|
2038
|
+
agentSource: subagent.agentSource,
|
|
2039
|
+
surface,
|
|
2040
|
+
catalog: {
|
|
2041
|
+
...baseCatalog,
|
|
2042
|
+
skills: new Set(liveSkills),
|
|
2043
|
+
models: new Set(subagent.possibleModels),
|
|
2044
|
+
connections: new Set(subagent.connections),
|
|
2045
|
+
...(subagent.maxReasoning !== undefined ? { maxReasoning: subagent.maxReasoning } : {})
|
|
2046
|
+
},
|
|
2047
|
+
defaultSkills: liveSkills,
|
|
2048
|
+
run: immutableAgentRunContext({
|
|
2049
|
+
id: run.id,
|
|
2050
|
+
message,
|
|
2051
|
+
channel: "subagent",
|
|
2052
|
+
conversationId,
|
|
2053
|
+
...(typeof run.input.userId === "string" ? { userId: run.input.userId } : {}),
|
|
2054
|
+
...(principalFromRun(run) ? { principal: principalFromRun(run) } : {}),
|
|
2055
|
+
...(initiatorFromRun(run) ? { initiator: initiatorFromRun(run) } : {}),
|
|
2056
|
+
audience: audienceFromRun(run),
|
|
2057
|
+
...(isJsonObject(run.input.metadata) ? { metadata: run.input.metadata } : {}),
|
|
2058
|
+
attachments: []
|
|
2059
|
+
}),
|
|
2060
|
+
disabledTools: this.disabledToolsForRun(run),
|
|
2061
|
+
createCheckpoint: (input) => this.createCheckpoint(input),
|
|
2062
|
+
listCheckpoints: (runId) => this.listHydratedCheckpoints(runId)
|
|
2063
|
+
});
|
|
2064
|
+
this.agentStateHandles.set(run.id, created.agentState);
|
|
2065
|
+
this.agentHookControllers.set(run.id, created.controller);
|
|
2066
|
+
return created.controller;
|
|
2067
|
+
}
|
|
2068
|
+
disabledToolsForRun(run) {
|
|
2069
|
+
const disabledTools = new Set(Object.entries(this.coreToolPolicy).filter(([, mode]) => mode === "disabled").map(([name]) => name));
|
|
2070
|
+
return disabledTools;
|
|
2071
|
+
}
|
|
2072
|
+
agentStateForRun(runId) {
|
|
2073
|
+
const handle = this.agentStateHandles.get(runId);
|
|
2074
|
+
if (!handle)
|
|
2075
|
+
throw new Error(`Agent state is unavailable before hook evaluation for run ${runId}.`);
|
|
2076
|
+
return handle;
|
|
2077
|
+
}
|
|
2078
|
+
async ensureAgentHookController(run) {
|
|
2079
|
+
const existing = this.agentHookControllers.get(run.id);
|
|
2080
|
+
if (existing)
|
|
2081
|
+
return existing;
|
|
2082
|
+
return recoverAgentHookController({
|
|
2083
|
+
run,
|
|
2084
|
+
manifest: this.manifest,
|
|
2085
|
+
createMain: (message, metadata, channel, conversationId, attachments) => this.createAgentHookController(run, { message, ...(metadata ? { metadata } : {}) }, channel, conversationId, attachments),
|
|
2086
|
+
createSubagent: (subagent, message, conversationId) => this.createSubagentHookController(run, subagent, message, conversationId)
|
|
2087
|
+
});
|
|
1997
2088
|
}
|
|
1998
2089
|
async loadTool(tool, run) {
|
|
1999
2090
|
const stub = resolveEvalToolStub(this.evalStubCursors, run, tool.name) ?? this.toolStubs[tool.name];
|
|
@@ -2004,8 +2095,6 @@ export class AssemblyLineRuntime {
|
|
|
2004
2095
|
execute: async (input) => stub(input)
|
|
2005
2096
|
};
|
|
2006
2097
|
}
|
|
2007
|
-
// Only builtin-sourced entries resolve to the built-in implementation; an
|
|
2008
|
-
// authored tool that shares a built-in's name is an override and loads its module.
|
|
2009
2098
|
if (tool.source.path.startsWith("__builtin__")) {
|
|
2010
2099
|
const builtIn = builtInToolDefinition(tool.name);
|
|
2011
2100
|
if (builtIn)
|
|
@@ -2014,26 +2103,8 @@ export class AssemblyLineRuntime {
|
|
|
2014
2103
|
const module = await this.sourceLoader.load(tool.source);
|
|
2015
2104
|
return module.default;
|
|
2016
2105
|
}
|
|
2017
|
-
async loadInstrumentationModule() {
|
|
2018
|
-
if (!this.manifest.instrumentation)
|
|
2019
|
-
return {};
|
|
2020
|
-
return this.sourceLoader.load(this.manifest.instrumentation);
|
|
2021
|
-
}
|
|
2022
2106
|
async result(run, response, waitingForApproval, waitingForInput, waitingForConnection) {
|
|
2023
|
-
|
|
2024
|
-
run,
|
|
2025
|
-
events: await this.state.listEvents(run.id),
|
|
2026
|
-
toolCalls: await this.state.listToolCalls(run.id),
|
|
2027
|
-
deliveries: await this.state.listDeliveries(run.id),
|
|
2028
|
-
response
|
|
2029
|
-
};
|
|
2030
|
-
if (waitingForApproval !== undefined)
|
|
2031
|
-
result.waitingForApproval = waitingForApproval;
|
|
2032
|
-
if (waitingForInput !== undefined)
|
|
2033
|
-
result.waitingForInput = waitingForInput;
|
|
2034
|
-
if (waitingForConnection !== undefined)
|
|
2035
|
-
result.waitingForConnection = waitingForConnection;
|
|
2036
|
-
return result;
|
|
2107
|
+
return buildRunAgentResult(this.state, run, response, waitingForApproval, waitingForInput, waitingForConnection);
|
|
2037
2108
|
}
|
|
2038
2109
|
}
|
|
2039
2110
|
export async function runLocalAgent(options) {
|