@animalabs/agent-framework 0.22.2 → 0.22.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +3 -1
- package/dist/src/agent.d.ts +77 -12
- package/dist/src/agent.d.ts.map +1 -1
- package/dist/src/agent.js +143 -41
- package/dist/src/agent.js.map +1 -1
- package/dist/src/api/mcp-server-core.js +1 -1
- package/dist/src/api/mcp-server-core.js.map +1 -1
- package/dist/src/api/server.d.ts.map +1 -1
- package/dist/src/api/server.js +5 -1
- package/dist/src/api/server.js.map +1 -1
- package/dist/src/api/types.d.ts +1 -1
- package/dist/src/api/types.d.ts.map +1 -1
- package/dist/src/branch-names.d.ts +14 -0
- package/dist/src/branch-names.d.ts.map +1 -0
- package/dist/src/branch-names.js +22 -0
- package/dist/src/branch-names.js.map +1 -0
- package/dist/src/closest-names.d.ts +28 -0
- package/dist/src/closest-names.d.ts.map +1 -0
- package/dist/src/closest-names.js +98 -0
- package/dist/src/closest-names.js.map +1 -0
- package/dist/src/code-execution/py-runner.d.ts +16 -5
- package/dist/src/code-execution/py-runner.d.ts.map +1 -1
- package/dist/src/code-execution/py-runner.js +186 -74
- package/dist/src/code-execution/py-runner.js.map +1 -1
- package/dist/src/code-execution/runtime-py.d.ts.map +1 -1
- package/dist/src/code-execution/runtime-py.js +49 -3
- package/dist/src/code-execution/runtime-py.js.map +1 -1
- package/dist/src/code-execution/tool-definition.d.ts +12 -1
- package/dist/src/code-execution/tool-definition.d.ts.map +1 -1
- package/dist/src/code-execution/tool-definition.js +21 -3
- package/dist/src/code-execution/tool-definition.js.map +1 -1
- package/dist/src/config-checks.d.ts +28 -0
- package/dist/src/config-checks.d.ts.map +1 -0
- package/dist/src/config-checks.js +52 -0
- package/dist/src/config-checks.js.map +1 -0
- package/dist/src/deadline-timer.d.ts +21 -0
- package/dist/src/deadline-timer.d.ts.map +1 -0
- package/dist/src/deadline-timer.js +43 -0
- package/dist/src/deadline-timer.js.map +1 -0
- package/dist/src/error-message.d.ts +30 -0
- package/dist/src/error-message.d.ts.map +1 -0
- package/dist/src/error-message.js +50 -0
- package/dist/src/error-message.js.map +1 -0
- package/dist/src/framework.d.ts +828 -88
- package/dist/src/framework.d.ts.map +1 -1
- package/dist/src/framework.js +5011 -1326
- package/dist/src/framework.js.map +1 -1
- package/dist/src/gate/event-gate.d.ts +8 -0
- package/dist/src/gate/event-gate.d.ts.map +1 -1
- package/dist/src/gate/event-gate.js +27 -3
- package/dist/src/gate/event-gate.js.map +1 -1
- package/dist/src/index.d.ts +4 -2
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +4 -2
- package/dist/src/index.js.map +1 -1
- package/dist/src/mcpl/channel-registry.d.ts +144 -6
- package/dist/src/mcpl/channel-registry.d.ts.map +1 -1
- package/dist/src/mcpl/channel-registry.js +424 -263
- package/dist/src/mcpl/channel-registry.js.map +1 -1
- package/dist/src/mcpl/checkpoint-manager.d.ts +21 -1
- package/dist/src/mcpl/checkpoint-manager.d.ts.map +1 -1
- package/dist/src/mcpl/checkpoint-manager.js +91 -30
- package/dist/src/mcpl/checkpoint-manager.js.map +1 -1
- package/dist/src/mcpl/conversation-router.d.ts +19 -3
- package/dist/src/mcpl/conversation-router.d.ts.map +1 -1
- package/dist/src/mcpl/conversation-router.js +23 -8
- package/dist/src/mcpl/conversation-router.js.map +1 -1
- package/dist/src/mcpl/convert-block.d.ts +20 -0
- package/dist/src/mcpl/convert-block.d.ts.map +1 -0
- package/dist/src/mcpl/convert-block.js +89 -0
- package/dist/src/mcpl/convert-block.js.map +1 -0
- package/dist/src/mcpl/errors.d.ts +13 -0
- package/dist/src/mcpl/errors.d.ts.map +1 -1
- package/dist/src/mcpl/errors.js +28 -0
- package/dist/src/mcpl/errors.js.map +1 -1
- package/dist/src/mcpl/hook-orchestrator.d.ts +23 -0
- package/dist/src/mcpl/hook-orchestrator.d.ts.map +1 -1
- package/dist/src/mcpl/hook-orchestrator.js +83 -72
- package/dist/src/mcpl/hook-orchestrator.js.map +1 -1
- package/dist/src/mcpl/inbound-source.d.ts +114 -0
- package/dist/src/mcpl/inbound-source.d.ts.map +1 -0
- package/dist/src/mcpl/inbound-source.js +83 -0
- package/dist/src/mcpl/inbound-source.js.map +1 -0
- package/dist/src/mcpl/index.d.ts +3 -1
- package/dist/src/mcpl/index.d.ts.map +1 -1
- package/dist/src/mcpl/index.js +3 -1
- package/dist/src/mcpl/index.js.map +1 -1
- package/dist/src/mcpl/inference-router.d.ts +15 -11
- package/dist/src/mcpl/inference-router.d.ts.map +1 -1
- package/dist/src/mcpl/inference-router.js +153 -84
- package/dist/src/mcpl/inference-router.js.map +1 -1
- package/dist/src/mcpl/push-coalescer.d.ts +33 -11
- package/dist/src/mcpl/push-coalescer.d.ts.map +1 -1
- package/dist/src/mcpl/push-coalescer.js +52 -20
- package/dist/src/mcpl/push-coalescer.js.map +1 -1
- package/dist/src/mcpl/push-handler.d.ts +16 -9
- package/dist/src/mcpl/push-handler.d.ts.map +1 -1
- package/dist/src/mcpl/push-handler.js +18 -83
- package/dist/src/mcpl/push-handler.js.map +1 -1
- package/dist/src/mcpl/reference-fetcher.d.ts +14 -2
- package/dist/src/mcpl/reference-fetcher.d.ts.map +1 -1
- package/dist/src/mcpl/reference-fetcher.js +72 -30
- package/dist/src/mcpl/reference-fetcher.js.map +1 -1
- package/dist/src/mcpl/references.d.ts +47 -12
- package/dist/src/mcpl/references.d.ts.map +1 -1
- package/dist/src/mcpl/references.js +74 -21
- package/dist/src/mcpl/references.js.map +1 -1
- package/dist/src/mcpl/server-connection.d.ts +89 -10
- package/dist/src/mcpl/server-connection.d.ts.map +1 -1
- package/dist/src/mcpl/server-connection.js +405 -129
- package/dist/src/mcpl/server-connection.js.map +1 -1
- package/dist/src/mcpl/server-registry.d.ts +10 -1
- package/dist/src/mcpl/server-registry.d.ts.map +1 -1
- package/dist/src/mcpl/server-registry.js +14 -3
- package/dist/src/mcpl/server-registry.js.map +1 -1
- package/dist/src/mcpl/skip-reply-wake.d.ts +36 -0
- package/dist/src/mcpl/skip-reply-wake.d.ts.map +1 -0
- package/dist/src/mcpl/skip-reply-wake.js +55 -0
- package/dist/src/mcpl/skip-reply-wake.js.map +1 -0
- package/dist/src/mcpl/transport.d.ts +51 -2
- package/dist/src/mcpl/transport.d.ts.map +1 -1
- package/dist/src/mcpl/transport.js +114 -20
- package/dist/src/mcpl/transport.js.map +1 -1
- package/dist/src/mcpl/types.d.ts +14 -3
- package/dist/src/mcpl/types.d.ts.map +1 -1
- package/dist/src/mcpl/types.js.map +1 -1
- package/dist/src/mcpl/visible-content.d.ts +15 -0
- package/dist/src/mcpl/visible-content.d.ts.map +1 -1
- package/dist/src/mcpl/visible-content.js +25 -0
- package/dist/src/mcpl/visible-content.js.map +1 -1
- package/dist/src/module-registry.d.ts +19 -1
- package/dist/src/module-registry.d.ts.map +1 -1
- package/dist/src/module-registry.js +54 -25
- package/dist/src/module-registry.js.map +1 -1
- package/dist/src/modules/api/index.js +1 -1
- package/dist/src/modules/api/index.js.map +1 -1
- package/dist/src/modules/discord/discord-js-client.d.ts +1 -0
- package/dist/src/modules/discord/discord-js-client.d.ts.map +1 -1
- package/dist/src/modules/discord/discord-js-client.js +25 -9
- package/dist/src/modules/discord/discord-js-client.js.map +1 -1
- package/dist/src/modules/discord/index.d.ts +29 -3
- package/dist/src/modules/discord/index.d.ts.map +1 -1
- package/dist/src/modules/discord/index.js +379 -143
- package/dist/src/modules/discord/index.js.map +1 -1
- package/dist/src/modules/discord/types.d.ts +14 -1
- package/dist/src/modules/discord/types.d.ts.map +1 -1
- package/dist/src/modules/health/index.d.ts.map +1 -1
- package/dist/src/modules/health/index.js +2 -1
- package/dist/src/modules/health/index.js.map +1 -1
- package/dist/src/modules/history/index.d.ts +3 -1
- package/dist/src/modules/history/index.d.ts.map +1 -1
- package/dist/src/modules/history/index.js +359 -127
- package/dist/src/modules/history/index.js.map +1 -1
- package/dist/src/modules/history/semantic.d.ts +28 -1
- package/dist/src/modules/history/semantic.d.ts.map +1 -1
- package/dist/src/modules/history/semantic.js +177 -32
- package/dist/src/modules/history/semantic.js.map +1 -1
- package/dist/src/modules/unknown-tool.d.ts +10 -0
- package/dist/src/modules/unknown-tool.d.ts.map +1 -0
- package/dist/src/modules/unknown-tool.js +17 -0
- package/dist/src/modules/unknown-tool.js.map +1 -0
- package/dist/src/modules/workspace/disk-agreement.d.ts +32 -2
- package/dist/src/modules/workspace/disk-agreement.d.ts.map +1 -1
- package/dist/src/modules/workspace/disk-agreement.js +30 -2
- package/dist/src/modules/workspace/disk-agreement.js.map +1 -1
- package/dist/src/modules/workspace/effects.d.ts +64 -6
- package/dist/src/modules/workspace/effects.d.ts.map +1 -1
- package/dist/src/modules/workspace/effects.js +291 -44
- package/dist/src/modules/workspace/effects.js.map +1 -1
- package/dist/src/modules/workspace/index.d.ts +119 -23
- package/dist/src/modules/workspace/index.d.ts.map +1 -1
- package/dist/src/modules/workspace/index.js +793 -247
- package/dist/src/modules/workspace/index.js.map +1 -1
- package/dist/src/modules/workspace/observe.d.ts +75 -8
- package/dist/src/modules/workspace/observe.d.ts.map +1 -1
- package/dist/src/modules/workspace/observe.js +174 -14
- package/dist/src/modules/workspace/observe.js.map +1 -1
- package/dist/src/modules/workspace/reconcile.d.ts +58 -7
- package/dist/src/modules/workspace/reconcile.d.ts.map +1 -1
- package/dist/src/modules/workspace/reconcile.js +521 -56
- package/dist/src/modules/workspace/reconcile.js.map +1 -1
- package/dist/src/modules/workspace/types.d.ts +18 -4
- package/dist/src/modules/workspace/types.d.ts.map +1 -1
- package/dist/src/modules/workspace/types.js.map +1 -1
- package/dist/src/modules/workspace/watcher.d.ts +7 -2
- package/dist/src/modules/workspace/watcher.d.ts.map +1 -1
- package/dist/src/modules/workspace/watcher.js +28 -4
- package/dist/src/modules/workspace/watcher.js.map +1 -1
- package/dist/src/prose-drafts.d.ts +240 -0
- package/dist/src/prose-drafts.d.ts.map +1 -0
- package/dist/src/prose-drafts.js +362 -0
- package/dist/src/prose-drafts.js.map +1 -0
- package/dist/src/prose-segments.d.ts +21 -2
- package/dist/src/prose-segments.d.ts.map +1 -1
- package/dist/src/prose-segments.js +46 -9
- package/dist/src/prose-segments.js.map +1 -1
- package/dist/src/recovery/offline-branch.d.ts +1 -0
- package/dist/src/recovery/offline-branch.d.ts.map +1 -1
- package/dist/src/recovery/offline-branch.js +3 -1
- package/dist/src/recovery/offline-branch.js.map +1 -1
- package/dist/src/safe-slice.d.ts +5 -1
- package/dist/src/safe-slice.d.ts.map +1 -1
- package/dist/src/safe-slice.js +9 -1
- package/dist/src/safe-slice.js.map +1 -1
- package/dist/src/thinking-token-stamp.d.ts +12 -0
- package/dist/src/thinking-token-stamp.d.ts.map +1 -1
- package/dist/src/thinking-token-stamp.js +34 -3
- package/dist/src/thinking-token-stamp.js.map +1 -1
- package/dist/src/tool-image-ledger.d.ts +87 -19
- package/dist/src/tool-image-ledger.d.ts.map +1 -1
- package/dist/src/tool-image-ledger.js +135 -32
- package/dist/src/tool-image-ledger.js.map +1 -1
- package/dist/src/tool-presentation.d.ts +9 -0
- package/dist/src/tool-presentation.d.ts.map +1 -1
- package/dist/src/tool-presentation.js +257 -60
- package/dist/src/tool-presentation.js.map +1 -1
- package/dist/src/tool-result-guard.d.ts.map +1 -1
- package/dist/src/tool-result-guard.js +7 -10
- package/dist/src/tool-result-guard.js.map +1 -1
- package/dist/src/tool-result-history.d.ts +32 -3
- package/dist/src/tool-result-history.d.ts.map +1 -1
- package/dist/src/tool-result-history.js +106 -19
- package/dist/src/tool-result-history.js.map +1 -1
- package/dist/src/tune-out/coordinator.d.ts +25 -1
- package/dist/src/tune-out/coordinator.d.ts.map +1 -1
- package/dist/src/tune-out/coordinator.js +260 -65
- package/dist/src/tune-out/coordinator.js.map +1 -1
- package/dist/src/types/agent.d.ts +17 -5
- package/dist/src/types/agent.d.ts.map +1 -1
- package/dist/src/types/events.d.ts +17 -0
- package/dist/src/types/events.d.ts.map +1 -1
- package/dist/src/types/framework.d.ts +21 -5
- package/dist/src/types/framework.d.ts.map +1 -1
- package/dist/src/types/inference-log.d.ts +1 -1
- package/dist/src/types/inference-log.d.ts.map +1 -1
- package/dist/src/types/module.d.ts +23 -4
- package/dist/src/types/module.d.ts.map +1 -1
- package/dist/src/types/trace.d.ts +95 -6
- package/dist/src/types/trace.d.ts.map +1 -1
- package/dist/src/usage/usage-tracker.d.ts +5 -0
- package/dist/src/usage/usage-tracker.d.ts.map +1 -1
- package/dist/src/usage/usage-tracker.js +35 -8
- package/dist/src/usage/usage-tracker.js.map +1 -1
- package/package.json +6 -4
- package/src/agent.ts +169 -41
- package/src/api/mcp-server-core.ts +1 -1
- package/src/api/server.ts +4 -1
- package/src/api/types.ts +1 -1
- package/src/branch-names.ts +19 -0
- package/src/closest-names.ts +94 -0
- package/src/code-execution/py-runner.ts +200 -76
- package/src/code-execution/runtime-py.ts +49 -3
- package/src/code-execution/tool-definition.ts +28 -4
- package/src/config-checks.ts +48 -0
- package/src/deadline-timer.ts +44 -0
- package/src/error-message.ts +48 -0
- package/src/framework.ts +5352 -1388
- package/src/gate/event-gate.ts +28 -3
- package/src/index.ts +11 -2
- package/src/mcpl/channel-registry.ts +517 -286
- package/src/mcpl/checkpoint-manager.ts +104 -29
- package/src/mcpl/conversation-router.ts +28 -8
- package/src/mcpl/convert-block.ts +97 -0
- package/src/mcpl/errors.ts +28 -0
- package/src/mcpl/hook-orchestrator.ts +84 -77
- package/src/mcpl/inbound-source.ts +156 -0
- package/src/mcpl/index.ts +10 -1
- package/src/mcpl/inference-router.ts +174 -99
- package/src/mcpl/push-coalescer.ts +60 -24
- package/src/mcpl/push-handler.ts +20 -90
- package/src/mcpl/reference-fetcher.ts +71 -26
- package/src/mcpl/references.ts +81 -22
- package/src/mcpl/server-connection.ts +427 -132
- package/src/mcpl/server-registry.ts +15 -4
- package/src/mcpl/skip-reply-wake.ts +73 -0
- package/src/mcpl/transport.ts +120 -18
- package/src/mcpl/types.ts +14 -3
- package/src/mcpl/visible-content.ts +27 -0
- package/src/module-registry.ts +58 -23
- package/src/modules/api/index.ts +1 -1
- package/src/modules/discord/discord-js-client.ts +26 -10
- package/src/modules/discord/index.ts +391 -158
- package/src/modules/discord/types.ts +15 -2
- package/src/modules/health/index.ts +2 -1
- package/src/modules/history/index.ts +410 -120
- package/src/modules/history/semantic.ts +189 -32
- package/src/modules/unknown-tool.ts +16 -0
- package/src/modules/workspace/disk-agreement.ts +51 -3
- package/src/modules/workspace/effects.ts +279 -35
- package/src/modules/workspace/index.ts +810 -260
- package/src/modules/workspace/observe.ts +194 -20
- package/src/modules/workspace/reconcile.ts +619 -64
- package/src/modules/workspace/types.ts +18 -4
- package/src/modules/workspace/watcher.ts +27 -4
- package/src/prose-drafts.ts +481 -0
- package/src/prose-segments.ts +51 -8
- package/src/recovery/offline-branch.ts +4 -1
- package/src/safe-slice.ts +9 -1
- package/src/thinking-token-stamp.ts +34 -3
- package/src/tool-image-ledger.ts +153 -34
- package/src/tool-presentation.ts +224 -40
- package/src/tool-result-guard.ts +7 -8
- package/src/tool-result-history.ts +124 -20
- package/src/tune-out/coordinator.ts +259 -65
- package/src/types/agent.ts +17 -7
- package/src/types/events.ts +17 -0
- package/src/types/framework.ts +21 -5
- package/src/types/inference-log.ts +1 -1
- package/src/types/module.ts +24 -4
- package/src/types/trace.ts +101 -6
- package/src/usage/usage-tracker.ts +32 -8
- package/dist/test/activation-request-sanitize.test.d.ts +0 -2
- package/dist/test/activation-request-sanitize.test.d.ts.map +0 -1
- package/dist/test/activation-request-sanitize.test.js +0 -89
- package/dist/test/activation-request-sanitize.test.js.map +0 -1
- package/dist/test/agent-cache-ttl.test.d.ts +0 -2
- package/dist/test/agent-cache-ttl.test.d.ts.map +0 -1
- package/dist/test/agent-cache-ttl.test.js +0 -41
- package/dist/test/agent-cache-ttl.test.js.map +0 -1
- package/dist/test/agent-runtime-settings.test.d.ts +0 -2
- package/dist/test/agent-runtime-settings.test.d.ts.map +0 -1
- package/dist/test/agent-runtime-settings.test.js +0 -1598
- package/dist/test/agent-runtime-settings.test.js.map +0 -1
- package/dist/test/api-admin-gate.test.d.ts +0 -2
- package/dist/test/api-admin-gate.test.d.ts.map +0 -1
- package/dist/test/api-admin-gate.test.js +0 -116
- package/dist/test/api-admin-gate.test.js.map +0 -1
- package/dist/test/assistant-persist-refusal.test.d.ts +0 -2
- package/dist/test/assistant-persist-refusal.test.d.ts.map +0 -1
- package/dist/test/assistant-persist-refusal.test.js +0 -63
- package/dist/test/assistant-persist-refusal.test.js.map +0 -1
- package/dist/test/batched-wake-locus.test.d.ts +0 -2
- package/dist/test/batched-wake-locus.test.d.ts.map +0 -1
- package/dist/test/batched-wake-locus.test.js +0 -166
- package/dist/test/batched-wake-locus.test.js.map +0 -1
- package/dist/test/busy-agent-scheduler.test.d.ts +0 -2
- package/dist/test/busy-agent-scheduler.test.d.ts.map +0 -1
- package/dist/test/busy-agent-scheduler.test.js +0 -92
- package/dist/test/busy-agent-scheduler.test.js.map +0 -1
- package/dist/test/channel-incoming-targeting.test.d.ts +0 -2
- package/dist/test/channel-incoming-targeting.test.d.ts.map +0 -1
- package/dist/test/channel-incoming-targeting.test.js +0 -81
- package/dist/test/channel-incoming-targeting.test.js.map +0 -1
- package/dist/test/channel-label-history.test.d.ts +0 -2
- package/dist/test/channel-label-history.test.d.ts.map +0 -1
- package/dist/test/channel-label-history.test.js +0 -424
- package/dist/test/channel-label-history.test.js.map +0 -1
- package/dist/test/channel-lifecycle-provenance.test.d.ts +0 -2
- package/dist/test/channel-lifecycle-provenance.test.d.ts.map +0 -1
- package/dist/test/channel-lifecycle-provenance.test.js +0 -47
- package/dist/test/channel-lifecycle-provenance.test.js.map +0 -1
- package/dist/test/channel-registry-routing.test.d.ts +0 -2
- package/dist/test/channel-registry-routing.test.d.ts.map +0 -1
- package/dist/test/channel-registry-routing.test.js +0 -446
- package/dist/test/channel-registry-routing.test.js.map +0 -1
- package/dist/test/channel-registry-typing.test.d.ts +0 -2
- package/dist/test/channel-registry-typing.test.d.ts.map +0 -1
- package/dist/test/channel-registry-typing.test.js +0 -91
- package/dist/test/channel-registry-typing.test.js.map +0 -1
- package/dist/test/channels-changed-respond-first.test.d.ts +0 -2
- package/dist/test/channels-changed-respond-first.test.d.ts.map +0 -1
- package/dist/test/channels-changed-respond-first.test.js +0 -74
- package/dist/test/channels-changed-respond-first.test.js.map +0 -1
- package/dist/test/checkpoint-attribution.test.d.ts +0 -2
- package/dist/test/checkpoint-attribution.test.d.ts.map +0 -1
- package/dist/test/checkpoint-attribution.test.js +0 -200
- package/dist/test/checkpoint-attribution.test.js.map +0 -1
- package/dist/test/code-execution.test.d.ts +0 -11
- package/dist/test/code-execution.test.d.ts.map +0 -1
- package/dist/test/code-execution.test.js +0 -1272
- package/dist/test/code-execution.test.js.map +0 -1
- package/dist/test/component-defaults.test.d.ts +0 -2
- package/dist/test/component-defaults.test.d.ts.map +0 -1
- package/dist/test/component-defaults.test.js +0 -54
- package/dist/test/component-defaults.test.js.map +0 -1
- package/dist/test/conversation-fork-injection-scoping.test.d.ts +0 -2
- package/dist/test/conversation-fork-injection-scoping.test.d.ts.map +0 -1
- package/dist/test/conversation-fork-injection-scoping.test.js +0 -200
- package/dist/test/conversation-fork-injection-scoping.test.js.map +0 -1
- package/dist/test/conversation-router.test.d.ts +0 -2
- package/dist/test/conversation-router.test.d.ts.map +0 -1
- package/dist/test/conversation-router.test.js +0 -174
- package/dist/test/conversation-router.test.js.map +0 -1
- package/dist/test/conversation-routing.test.d.ts +0 -7
- package/dist/test/conversation-routing.test.d.ts.map +0 -1
- package/dist/test/conversation-routing.test.js +0 -621
- package/dist/test/conversation-routing.test.js.map +0 -1
- package/dist/test/deferred-wake-integrity.test.d.ts +0 -29
- package/dist/test/deferred-wake-integrity.test.d.ts.map +0 -1
- package/dist/test/deferred-wake-integrity.test.js +0 -320
- package/dist/test/deferred-wake-integrity.test.js.map +0 -1
- package/dist/test/discord-awareness-outbox.test.d.ts +0 -2
- package/dist/test/discord-awareness-outbox.test.d.ts.map +0 -1
- package/dist/test/discord-awareness-outbox.test.js +0 -371
- package/dist/test/discord-awareness-outbox.test.js.map +0 -1
- package/dist/test/discord-history-delete-window.test.d.ts +0 -2
- package/dist/test/discord-history-delete-window.test.d.ts.map +0 -1
- package/dist/test/discord-history-delete-window.test.js +0 -81
- package/dist/test/discord-history-delete-window.test.js.map +0 -1
- package/dist/test/discord-history-sync.test.d.ts +0 -2
- package/dist/test/discord-history-sync.test.d.ts.map +0 -1
- package/dist/test/discord-history-sync.test.js +0 -56
- package/dist/test/discord-history-sync.test.js.map +0 -1
- package/dist/test/discord-typing-keepalive.test.d.ts +0 -2
- package/dist/test/discord-typing-keepalive.test.d.ts.map +0 -1
- package/dist/test/discord-typing-keepalive.test.js +0 -77
- package/dist/test/discord-typing-keepalive.test.js.map +0 -1
- package/dist/test/ephemeral-settle.test.d.ts +0 -2
- package/dist/test/ephemeral-settle.test.d.ts.map +0 -1
- package/dist/test/ephemeral-settle.test.js +0 -354
- package/dist/test/ephemeral-settle.test.js.map +0 -1
- package/dist/test/event-gate-passthrough.test.d.ts +0 -15
- package/dist/test/event-gate-passthrough.test.d.ts.map +0 -1
- package/dist/test/event-gate-passthrough.test.js +0 -289
- package/dist/test/event-gate-passthrough.test.js.map +0 -1
- package/dist/test/event-gate-policy-mutation.test.d.ts +0 -2
- package/dist/test/event-gate-policy-mutation.test.d.ts.map +0 -1
- package/dist/test/event-gate-policy-mutation.test.js +0 -137
- package/dist/test/event-gate-policy-mutation.test.js.map +0 -1
- package/dist/test/event-gate-rate-limit.test.d.ts +0 -2
- package/dist/test/event-gate-rate-limit.test.d.ts.map +0 -1
- package/dist/test/event-gate-rate-limit.test.js +0 -627
- package/dist/test/event-gate-rate-limit.test.js.map +0 -1
- package/dist/test/event-gate-script.test.d.ts +0 -2
- package/dist/test/event-gate-script.test.d.ts.map +0 -1
- package/dist/test/event-gate-script.test.js +0 -95
- package/dist/test/event-gate-script.test.js.map +0 -1
- package/dist/test/event-gate-selfwake.test.d.ts +0 -15
- package/dist/test/event-gate-selfwake.test.d.ts.map +0 -1
- package/dist/test/event-gate-selfwake.test.js +0 -125
- package/dist/test/event-gate-selfwake.test.js.map +0 -1
- package/dist/test/event-gate-tags.test.d.ts +0 -2
- package/dist/test/event-gate-tags.test.d.ts.map +0 -1
- package/dist/test/event-gate-tags.test.js +0 -76
- package/dist/test/event-gate-tags.test.js.map +0 -1
- package/dist/test/event-gate.test.d.ts +0 -2
- package/dist/test/event-gate.test.d.ts.map +0 -1
- package/dist/test/event-gate.test.js +0 -919
- package/dist/test/event-gate.test.js.map +0 -1
- package/dist/test/explicit-prose-routing.test.d.ts +0 -11
- package/dist/test/explicit-prose-routing.test.d.ts.map +0 -1
- package/dist/test/explicit-prose-routing.test.js +0 -1715
- package/dist/test/explicit-prose-routing.test.js.map +0 -1
- package/dist/test/framework.test.d.ts +0 -5
- package/dist/test/framework.test.d.ts.map +0 -1
- package/dist/test/framework.test.js +0 -1048
- package/dist/test/framework.test.js.map +0 -1
- package/dist/test/gather-context-timeout.test.d.ts +0 -2
- package/dist/test/gather-context-timeout.test.d.ts.map +0 -1
- package/dist/test/gather-context-timeout.test.js +0 -120
- package/dist/test/gather-context-timeout.test.js.map +0 -1
- package/dist/test/health-snapshot.test.d.ts +0 -2
- package/dist/test/health-snapshot.test.d.ts.map +0 -1
- package/dist/test/health-snapshot.test.js +0 -74
- package/dist/test/health-snapshot.test.js.map +0 -1
- package/dist/test/helpers/coalescing-fixture.d.ts +0 -74
- package/dist/test/helpers/coalescing-fixture.d.ts.map +0 -1
- package/dist/test/helpers/coalescing-fixture.js +0 -152
- package/dist/test/helpers/coalescing-fixture.js.map +0 -1
- package/dist/test/helpers/coalescing-kill-child.d.ts +0 -2
- package/dist/test/helpers/coalescing-kill-child.d.ts.map +0 -1
- package/dist/test/helpers/coalescing-kill-child.js +0 -24
- package/dist/test/helpers/coalescing-kill-child.js.map +0 -1
- package/dist/test/helpers/mock-membrane.d.ts +0 -53
- package/dist/test/helpers/mock-membrane.d.ts.map +0 -1
- package/dist/test/helpers/mock-membrane.js +0 -168
- package/dist/test/helpers/mock-membrane.js.map +0 -1
- package/dist/test/helpers/pytc-stop-rows.d.ts +0 -11
- package/dist/test/helpers/pytc-stop-rows.d.ts.map +0 -1
- package/dist/test/helpers/pytc-stop-rows.js +0 -143
- package/dist/test/helpers/pytc-stop-rows.js.map +0 -1
- package/dist/test/helpers/quiesce-crash-child.d.ts +0 -2
- package/dist/test/helpers/quiesce-crash-child.d.ts.map +0 -1
- package/dist/test/helpers/quiesce-crash-child.js +0 -156
- package/dist/test/helpers/quiesce-crash-child.js.map +0 -1
- package/dist/test/hide-then-turn.test.d.ts +0 -2
- package/dist/test/hide-then-turn.test.d.ts.map +0 -1
- package/dist/test/hide-then-turn.test.js +0 -101
- package/dist/test/hide-then-turn.test.js.map +0 -1
- package/dist/test/history-module-overview.test.d.ts +0 -2
- package/dist/test/history-module-overview.test.d.ts.map +0 -1
- package/dist/test/history-module-overview.test.js +0 -711
- package/dist/test/history-module-overview.test.js.map +0 -1
- package/dist/test/history-module-realstore.test.d.ts +0 -2
- package/dist/test/history-module-realstore.test.d.ts.map +0 -1
- package/dist/test/history-module-realstore.test.js +0 -363
- package/dist/test/history-module-realstore.test.js.map +0 -1
- package/dist/test/history-module-semantic.test.d.ts +0 -2
- package/dist/test/history-module-semantic.test.d.ts.map +0 -1
- package/dist/test/history-module-semantic.test.js +0 -213
- package/dist/test/history-module-semantic.test.js.map +0 -1
- package/dist/test/history-module-ux.test.d.ts +0 -2
- package/dist/test/history-module-ux.test.d.ts.map +0 -1
- package/dist/test/history-module-ux.test.js +0 -304
- package/dist/test/history-module-ux.test.js.map +0 -1
- package/dist/test/history-module.test.d.ts +0 -2
- package/dist/test/history-module.test.d.ts.map +0 -1
- package/dist/test/history-module.test.js +0 -619
- package/dist/test/history-module.test.js.map +0 -1
- package/dist/test/history-semantic-review-findings.test.d.ts +0 -2
- package/dist/test/history-semantic-review-findings.test.d.ts.map +0 -1
- package/dist/test/history-semantic-review-findings.test.js +0 -338
- package/dist/test/history-semantic-review-findings.test.js.map +0 -1
- package/dist/test/history-semantic-sync-converges.test.d.ts +0 -2
- package/dist/test/history-semantic-sync-converges.test.d.ts.map +0 -1
- package/dist/test/history-semantic-sync-converges.test.js +0 -109
- package/dist/test/history-semantic-sync-converges.test.js.map +0 -1
- package/dist/test/host-quiesce.test.d.ts +0 -2
- package/dist/test/host-quiesce.test.d.ts.map +0 -1
- package/dist/test/host-quiesce.test.js +0 -988
- package/dist/test/host-quiesce.test.js.map +0 -1
- package/dist/test/inference-exhaustion-rewind.test.d.ts +0 -2
- package/dist/test/inference-exhaustion-rewind.test.d.ts.map +0 -1
- package/dist/test/inference-exhaustion-rewind.test.js +0 -387
- package/dist/test/inference-exhaustion-rewind.test.js.map +0 -1
- package/dist/test/inference-failure-bounds.test.d.ts +0 -2
- package/dist/test/inference-failure-bounds.test.d.ts.map +0 -1
- package/dist/test/inference-failure-bounds.test.js +0 -1202
- package/dist/test/inference-failure-bounds.test.js.map +0 -1
- package/dist/test/inference-failure-observability.test.d.ts +0 -2
- package/dist/test/inference-failure-observability.test.d.ts.map +0 -1
- package/dist/test/inference-failure-observability.test.js +0 -84
- package/dist/test/inference-failure-observability.test.js.map +0 -1
- package/dist/test/journal-tool.test.d.ts +0 -2
- package/dist/test/journal-tool.test.d.ts.map +0 -1
- package/dist/test/journal-tool.test.js +0 -33
- package/dist/test/journal-tool.test.js.map +0 -1
- package/dist/test/kv-unified-open-flight-retry.test.d.ts +0 -2
- package/dist/test/kv-unified-open-flight-retry.test.d.ts.map +0 -1
- package/dist/test/kv-unified-open-flight-retry.test.js +0 -189
- package/dist/test/kv-unified-open-flight-retry.test.js.map +0 -1
- package/dist/test/kv-unified-wiring.test.d.ts +0 -2
- package/dist/test/kv-unified-wiring.test.d.ts.map +0 -1
- package/dist/test/kv-unified-wiring.test.js +0 -95
- package/dist/test/kv-unified-wiring.test.js.map +0 -1
- package/dist/test/late-events-after-stop.test.d.ts +0 -2
- package/dist/test/late-events-after-stop.test.d.ts.map +0 -1
- package/dist/test/late-events-after-stop.test.js +0 -122
- package/dist/test/late-events-after-stop.test.js.map +0 -1
- package/dist/test/liveness-watchdog.test.d.ts +0 -2
- package/dist/test/liveness-watchdog.test.d.ts.map +0 -1
- package/dist/test/liveness-watchdog.test.js +0 -94
- package/dist/test/liveness-watchdog.test.js.map +0 -1
- package/dist/test/machine-close-provenance.test.d.ts +0 -2
- package/dist/test/machine-close-provenance.test.d.ts.map +0 -1
- package/dist/test/machine-close-provenance.test.js +0 -116
- package/dist/test/machine-close-provenance.test.js.map +0 -1
- package/dist/test/maintenance-timer.test.d.ts +0 -2
- package/dist/test/maintenance-timer.test.d.ts.map +0 -1
- package/dist/test/maintenance-timer.test.js +0 -1827
- package/dist/test/maintenance-timer.test.js.map +0 -1
- package/dist/test/mcp-server-bin.test.d.ts +0 -2
- package/dist/test/mcp-server-bin.test.d.ts.map +0 -1
- package/dist/test/mcp-server-bin.test.js +0 -142
- package/dist/test/mcp-server-bin.test.js.map +0 -1
- package/dist/test/mcpl-access-provider.test.d.ts +0 -2
- package/dist/test/mcpl-access-provider.test.d.ts.map +0 -1
- package/dist/test/mcpl-access-provider.test.js +0 -20
- package/dist/test/mcpl-access-provider.test.js.map +0 -1
- package/dist/test/mcpl-awareness-barrier.test.d.ts +0 -2
- package/dist/test/mcpl-awareness-barrier.test.d.ts.map +0 -1
- package/dist/test/mcpl-awareness-barrier.test.js +0 -769
- package/dist/test/mcpl-awareness-barrier.test.js.map +0 -1
- package/dist/test/mcpl-capability-grant.test.d.ts +0 -10
- package/dist/test/mcpl-capability-grant.test.d.ts.map +0 -1
- package/dist/test/mcpl-capability-grant.test.js +0 -111
- package/dist/test/mcpl-capability-grant.test.js.map +0 -1
- package/dist/test/mcpl-capability-scoping.test.d.ts +0 -2
- package/dist/test/mcpl-capability-scoping.test.d.ts.map +0 -1
- package/dist/test/mcpl-capability-scoping.test.js +0 -266
- package/dist/test/mcpl-capability-scoping.test.js.map +0 -1
- package/dist/test/mcpl-child-env.test.d.ts +0 -2
- package/dist/test/mcpl-child-env.test.d.ts.map +0 -1
- package/dist/test/mcpl-child-env.test.js +0 -158
- package/dist/test/mcpl-child-env.test.js.map +0 -1
- package/dist/test/mcpl-coalesced-content-parity.test.d.ts +0 -2
- package/dist/test/mcpl-coalesced-content-parity.test.d.ts.map +0 -1
- package/dist/test/mcpl-coalesced-content-parity.test.js +0 -532
- package/dist/test/mcpl-coalesced-content-parity.test.js.map +0 -1
- package/dist/test/mcpl-coalescing.test.d.ts +0 -2
- package/dist/test/mcpl-coalescing.test.d.ts.map +0 -1
- package/dist/test/mcpl-coalescing.test.js +0 -1125
- package/dist/test/mcpl-coalescing.test.js.map +0 -1
- package/dist/test/mcpl-config-diagnostics.test.d.ts +0 -2
- package/dist/test/mcpl-config-diagnostics.test.d.ts.map +0 -1
- package/dist/test/mcpl-config-diagnostics.test.js +0 -452
- package/dist/test/mcpl-config-diagnostics.test.js.map +0 -1
- package/dist/test/mcpl-empty-content.test.d.ts +0 -2
- package/dist/test/mcpl-empty-content.test.d.ts.map +0 -1
- package/dist/test/mcpl-empty-content.test.js +0 -368
- package/dist/test/mcpl-empty-content.test.js.map +0 -1
- package/dist/test/mcpl-gate-roundtrip.test.d.ts +0 -2
- package/dist/test/mcpl-gate-roundtrip.test.d.ts.map +0 -1
- package/dist/test/mcpl-gate-roundtrip.test.js +0 -285
- package/dist/test/mcpl-gate-roundtrip.test.js.map +0 -1
- package/dist/test/mcpl-list-status.test.d.ts +0 -2
- package/dist/test/mcpl-list-status.test.d.ts.map +0 -1
- package/dist/test/mcpl-list-status.test.js +0 -82
- package/dist/test/mcpl-list-status.test.js.map +0 -1
- package/dist/test/mcpl-manifest-changed.test.d.ts +0 -2
- package/dist/test/mcpl-manifest-changed.test.d.ts.map +0 -1
- package/dist/test/mcpl-manifest-changed.test.js +0 -178
- package/dist/test/mcpl-manifest-changed.test.js.map +0 -1
- package/dist/test/mcpl-push-convert.test.d.ts +0 -2
- package/dist/test/mcpl-push-convert.test.d.ts.map +0 -1
- package/dist/test/mcpl-push-convert.test.js +0 -42
- package/dist/test/mcpl-push-convert.test.js.map +0 -1
- package/dist/test/mcpl-reconnect-events.test.d.ts +0 -2
- package/dist/test/mcpl-reconnect-events.test.d.ts.map +0 -1
- package/dist/test/mcpl-reconnect-events.test.js +0 -144
- package/dist/test/mcpl-reconnect-events.test.js.map +0 -1
- package/dist/test/mcpl-reconnect-reregistration.test.d.ts +0 -2
- package/dist/test/mcpl-reconnect-reregistration.test.d.ts.map +0 -1
- package/dist/test/mcpl-reconnect-reregistration.test.js +0 -238
- package/dist/test/mcpl-reconnect-reregistration.test.js.map +0 -1
- package/dist/test/mcpl-reference-fetcher.test.d.ts +0 -2
- package/dist/test/mcpl-reference-fetcher.test.d.ts.map +0 -1
- package/dist/test/mcpl-reference-fetcher.test.js +0 -427
- package/dist/test/mcpl-reference-fetcher.test.js.map +0 -1
- package/dist/test/mcpl-reference-fields.test.d.ts +0 -2
- package/dist/test/mcpl-reference-fields.test.d.ts.map +0 -1
- package/dist/test/mcpl-reference-fields.test.js +0 -149
- package/dist/test/mcpl-reference-fields.test.js.map +0 -1
- package/dist/test/mcpl-rejection-log-lines.test.d.ts +0 -2
- package/dist/test/mcpl-rejection-log-lines.test.d.ts.map +0 -1
- package/dist/test/mcpl-rejection-log-lines.test.js +0 -349
- package/dist/test/mcpl-rejection-log-lines.test.js.map +0 -1
- package/dist/test/mcpl-request-timeout.test.d.ts +0 -2
- package/dist/test/mcpl-request-timeout.test.d.ts.map +0 -1
- package/dist/test/mcpl-request-timeout.test.js +0 -138
- package/dist/test/mcpl-request-timeout.test.js.map +0 -1
- package/dist/test/mcpl-runtime-lifecycle.test.d.ts +0 -7
- package/dist/test/mcpl-runtime-lifecycle.test.d.ts.map +0 -1
- package/dist/test/mcpl-runtime-lifecycle.test.js +0 -142
- package/dist/test/mcpl-runtime-lifecycle.test.js.map +0 -1
- package/dist/test/mcpl-stderr-tail.test.d.ts +0 -2
- package/dist/test/mcpl-stderr-tail.test.d.ts.map +0 -1
- package/dist/test/mcpl-stderr-tail.test.js +0 -210
- package/dist/test/mcpl-stderr-tail.test.js.map +0 -1
- package/dist/test/mcpl-tool-class-listing.test.d.ts +0 -2
- package/dist/test/mcpl-tool-class-listing.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-class-listing.test.js +0 -147
- package/dist/test/mcpl-tool-class-listing.test.js.map +0 -1
- package/dist/test/mcpl-tool-classes.test.d.ts +0 -7
- package/dist/test/mcpl-tool-classes.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-classes.test.js +0 -80
- package/dist/test/mcpl-tool-classes.test.js.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-e2e.test.d.ts +0 -2
- package/dist/test/mcpl-tool-lifecycle-e2e.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-e2e.test.js +0 -237
- package/dist/test/mcpl-tool-lifecycle-e2e.test.js.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-emitter.test.d.ts +0 -11
- package/dist/test/mcpl-tool-lifecycle-emitter.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-emitter.test.js +0 -412
- package/dist/test/mcpl-tool-lifecycle-emitter.test.js.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-script.test.d.ts +0 -2
- package/dist/test/mcpl-tool-lifecycle-script.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-lifecycle-script.test.js +0 -288
- package/dist/test/mcpl-tool-lifecycle-script.test.js.map +0 -1
- package/dist/test/mcpl-tool-lifecycle.test.d.ts +0 -11
- package/dist/test/mcpl-tool-lifecycle.test.d.ts.map +0 -1
- package/dist/test/mcpl-tool-lifecycle.test.js +0 -270
- package/dist/test/mcpl-tool-lifecycle.test.js.map +0 -1
- package/dist/test/mcpl-transport-close.test.d.ts +0 -2
- package/dist/test/mcpl-transport-close.test.d.ts.map +0 -1
- package/dist/test/mcpl-transport-close.test.js +0 -373
- package/dist/test/mcpl-transport-close.test.js.map +0 -1
- package/dist/test/mcpl-transport-spawn.test.d.ts +0 -2
- package/dist/test/mcpl-transport-spawn.test.d.ts.map +0 -1
- package/dist/test/mcpl-transport-spawn.test.js +0 -58
- package/dist/test/mcpl-transport-spawn.test.js.map +0 -1
- package/dist/test/mcpl-ws-transport.test.d.ts +0 -2
- package/dist/test/mcpl-ws-transport.test.d.ts.map +0 -1
- package/dist/test/mcpl-ws-transport.test.js +0 -259
- package/dist/test/mcpl-ws-transport.test.js.map +0 -1
- package/dist/test/module-context-integration.test.d.ts +0 -18
- package/dist/test/module-context-integration.test.d.ts.map +0 -1
- package/dist/test/module-context-integration.test.js +0 -181
- package/dist/test/module-context-integration.test.js.map +0 -1
- package/dist/test/offline-recovery-branch.test.d.ts +0 -2
- package/dist/test/offline-recovery-branch.test.d.ts.map +0 -1
- package/dist/test/offline-recovery-branch.test.js +0 -570
- package/dist/test/offline-recovery-branch.test.js.map +0 -1
- package/dist/test/operator-surgery.test.d.ts +0 -2
- package/dist/test/operator-surgery.test.d.ts.map +0 -1
- package/dist/test/operator-surgery.test.js +0 -595
- package/dist/test/operator-surgery.test.js.map +0 -1
- package/dist/test/ops-alert.test.d.ts +0 -2
- package/dist/test/ops-alert.test.d.ts.map +0 -1
- package/dist/test/ops-alert.test.js +0 -153
- package/dist/test/ops-alert.test.js.map +0 -1
- package/dist/test/overbudget-drain-breaker.test.d.ts +0 -2
- package/dist/test/overbudget-drain-breaker.test.d.ts.map +0 -1
- package/dist/test/overbudget-drain-breaker.test.js +0 -198
- package/dist/test/overbudget-drain-breaker.test.js.map +0 -1
- package/dist/test/pack-installs-alone.test.d.ts +0 -2
- package/dist/test/pack-installs-alone.test.d.ts.map +0 -1
- package/dist/test/pack-installs-alone.test.js +0 -284
- package/dist/test/pack-installs-alone.test.js.map +0 -1
- package/dist/test/per-agent-delivery.test.d.ts +0 -2
- package/dist/test/per-agent-delivery.test.d.ts.map +0 -1
- package/dist/test/per-agent-delivery.test.js +0 -108
- package/dist/test/per-agent-delivery.test.js.map +0 -1
- package/dist/test/physical-window-restart.test.d.ts +0 -16
- package/dist/test/physical-window-restart.test.d.ts.map +0 -1
- package/dist/test/physical-window-restart.test.js +0 -487
- package/dist/test/physical-window-restart.test.js.map +0 -1
- package/dist/test/placed-reaction-baseline.test.d.ts +0 -2
- package/dist/test/placed-reaction-baseline.test.d.ts.map +0 -1
- package/dist/test/placed-reaction-baseline.test.js +0 -312
- package/dist/test/placed-reaction-baseline.test.js.map +0 -1
- package/dist/test/present-while-acting.test.d.ts +0 -19
- package/dist/test/present-while-acting.test.d.ts.map +0 -1
- package/dist/test/present-while-acting.test.js +0 -1649
- package/dist/test/present-while-acting.test.js.map +0 -1
- package/dist/test/prose-segments.test.d.ts +0 -2
- package/dist/test/prose-segments.test.d.ts.map +0 -1
- package/dist/test/prose-segments.test.js +0 -52
- package/dist/test/prose-segments.test.js.map +0 -1
- package/dist/test/prose-stream-router.test.d.ts +0 -2
- package/dist/test/prose-stream-router.test.d.ts.map +0 -1
- package/dist/test/prose-stream-router.test.js +0 -171
- package/dist/test/prose-stream-router.test.js.map +0 -1
- package/dist/test/provider-acceleration-cooldown.test.d.ts +0 -2
- package/dist/test/provider-acceleration-cooldown.test.d.ts.map +0 -1
- package/dist/test/provider-acceleration-cooldown.test.js +0 -435
- package/dist/test/provider-acceleration-cooldown.test.js.map +0 -1
- package/dist/test/provider-waits.test.d.ts +0 -2
- package/dist/test/provider-waits.test.d.ts.map +0 -1
- package/dist/test/provider-waits.test.js +0 -2259
- package/dist/test/provider-waits.test.js.map +0 -1
- package/dist/test/puppet-tool-call.test.d.ts +0 -2
- package/dist/test/puppet-tool-call.test.d.ts.map +0 -1
- package/dist/test/puppet-tool-call.test.js +0 -226
- package/dist/test/puppet-tool-call.test.js.map +0 -1
- package/dist/test/puppet-turn-reservation.test.d.ts +0 -2
- package/dist/test/puppet-turn-reservation.test.d.ts.map +0 -1
- package/dist/test/puppet-turn-reservation.test.js +0 -139
- package/dist/test/puppet-turn-reservation.test.js.map +0 -1
- package/dist/test/reaction-baseline-platform.test.d.ts +0 -2
- package/dist/test/reaction-baseline-platform.test.d.ts.map +0 -1
- package/dist/test/reaction-baseline-platform.test.js +0 -124
- package/dist/test/reaction-baseline-platform.test.js.map +0 -1
- package/dist/test/record-journal.test.d.ts +0 -6
- package/dist/test/record-journal.test.d.ts.map +0 -1
- package/dist/test/record-journal.test.js +0 -269
- package/dist/test/record-journal.test.js.map +0 -1
- package/dist/test/refusal-reaction-baseline.test.d.ts +0 -2
- package/dist/test/refusal-reaction-baseline.test.d.ts.map +0 -1
- package/dist/test/refusal-reaction-baseline.test.js +0 -81
- package/dist/test/refusal-reaction-baseline.test.js.map +0 -1
- package/dist/test/refusal-rewind.test.d.ts +0 -2
- package/dist/test/refusal-rewind.test.d.ts.map +0 -1
- package/dist/test/refusal-rewind.test.js +0 -117
- package/dist/test/refusal-rewind.test.js.map +0 -1
- package/dist/test/refusal-single-call.test.d.ts +0 -2
- package/dist/test/refusal-single-call.test.d.ts.map +0 -1
- package/dist/test/refusal-single-call.test.js +0 -177
- package/dist/test/refusal-single-call.test.js.map +0 -1
- package/dist/test/release-bump.test.d.ts +0 -2
- package/dist/test/release-bump.test.d.ts.map +0 -1
- package/dist/test/release-bump.test.js +0 -248
- package/dist/test/release-bump.test.js.map +0 -1
- package/dist/test/release-changelog.test.d.ts +0 -2
- package/dist/test/release-changelog.test.d.ts.map +0 -1
- package/dist/test/release-changelog.test.js +0 -159
- package/dist/test/release-changelog.test.js.map +0 -1
- package/dist/test/release-holds.test.d.ts +0 -2
- package/dist/test/release-holds.test.d.ts.map +0 -1
- package/dist/test/release-holds.test.js +0 -456
- package/dist/test/release-holds.test.js.map +0 -1
- package/dist/test/same-round-think-policy.test.d.ts +0 -2
- package/dist/test/same-round-think-policy.test.d.ts.map +0 -1
- package/dist/test/same-round-think-policy.test.js +0 -853
- package/dist/test/same-round-think-policy.test.js.map +0 -1
- package/dist/test/save-recent-image.test.d.ts +0 -26
- package/dist/test/save-recent-image.test.d.ts.map +0 -1
- package/dist/test/save-recent-image.test.js +0 -974
- package/dist/test/save-recent-image.test.js.map +0 -1
- package/dist/test/shutdown-errors.test.d.ts +0 -2
- package/dist/test/shutdown-errors.test.d.ts.map +0 -1
- package/dist/test/shutdown-errors.test.js +0 -662
- package/dist/test/shutdown-errors.test.js.map +0 -1
- package/dist/test/silent-heartbeat-rows.test.d.ts +0 -2
- package/dist/test/silent-heartbeat-rows.test.d.ts.map +0 -1
- package/dist/test/silent-heartbeat-rows.test.js +0 -451
- package/dist/test/silent-heartbeat-rows.test.js.map +0 -1
- package/dist/test/silent-heartbeat.test.d.ts +0 -2
- package/dist/test/silent-heartbeat.test.d.ts.map +0 -1
- package/dist/test/silent-heartbeat.test.js +0 -165
- package/dist/test/silent-heartbeat.test.js.map +0 -1
- package/dist/test/state-scaling-e2e.test.d.ts +0 -22
- package/dist/test/state-scaling-e2e.test.d.ts.map +0 -1
- package/dist/test/state-scaling-e2e.test.js +0 -206
- package/dist/test/state-scaling-e2e.test.js.map +0 -1
- package/dist/test/state-scaling.test.d.ts +0 -12
- package/dist/test/state-scaling.test.d.ts.map +0 -1
- package/dist/test/state-scaling.test.js +0 -251
- package/dist/test/state-scaling.test.js.map +0 -1
- package/dist/test/stop-with-host-operations.test.d.ts +0 -20
- package/dist/test/stop-with-host-operations.test.d.ts.map +0 -1
- package/dist/test/stop-with-host-operations.test.js +0 -1174
- package/dist/test/stop-with-host-operations.test.js.map +0 -1
- package/dist/test/stop-with-work-in-flight.test.d.ts +0 -23
- package/dist/test/stop-with-work-in-flight.test.d.ts.map +0 -1
- package/dist/test/stop-with-work-in-flight.test.js +0 -784
- package/dist/test/stop-with-work-in-flight.test.js.map +0 -1
- package/dist/test/surgery-marks-receipt.test.d.ts +0 -2
- package/dist/test/surgery-marks-receipt.test.d.ts.map +0 -1
- package/dist/test/surgery-marks-receipt.test.js +0 -540
- package/dist/test/surgery-marks-receipt.test.js.map +0 -1
- package/dist/test/thinking-token-stamp.test.d.ts +0 -12
- package/dist/test/thinking-token-stamp.test.d.ts.map +0 -1
- package/dist/test/thinking-token-stamp.test.js +0 -129
- package/dist/test/thinking-token-stamp.test.js.map +0 -1
- package/dist/test/timezone.test.d.ts +0 -2
- package/dist/test/timezone.test.d.ts.map +0 -1
- package/dist/test/timezone.test.js +0 -18
- package/dist/test/timezone.test.js.map +0 -1
- package/dist/test/tool-batch-hook.test.d.ts +0 -8
- package/dist/test/tool-batch-hook.test.d.ts.map +0 -1
- package/dist/test/tool-batch-hook.test.js +0 -275
- package/dist/test/tool-batch-hook.test.js.map +0 -1
- package/dist/test/tool-policy.test.d.ts +0 -2
- package/dist/test/tool-policy.test.d.ts.map +0 -1
- package/dist/test/tool-policy.test.js +0 -51
- package/dist/test/tool-policy.test.js.map +0 -1
- package/dist/test/tool-presentation.test.d.ts +0 -2
- package/dist/test/tool-presentation.test.d.ts.map +0 -1
- package/dist/test/tool-presentation.test.js +0 -268
- package/dist/test/tool-presentation.test.js.map +0 -1
- package/dist/test/tool-result-content.test.d.ts +0 -2
- package/dist/test/tool-result-content.test.d.ts.map +0 -1
- package/dist/test/tool-result-content.test.js +0 -37
- package/dist/test/tool-result-content.test.js.map +0 -1
- package/dist/test/tool-result-guard.test.d.ts +0 -2
- package/dist/test/tool-result-guard.test.d.ts.map +0 -1
- package/dist/test/tool-result-guard.test.js +0 -3729
- package/dist/test/tool-result-guard.test.js.map +0 -1
- package/dist/test/tool-result-history.test.d.ts +0 -7
- package/dist/test/tool-result-history.test.d.ts.map +0 -1
- package/dist/test/tool-result-history.test.js +0 -156
- package/dist/test/tool-result-history.test.js.map +0 -1
- package/dist/test/tool-result-spill.test.d.ts +0 -13
- package/dist/test/tool-result-spill.test.d.ts.map +0 -1
- package/dist/test/tool-result-spill.test.js +0 -586
- package/dist/test/tool-result-spill.test.js.map +0 -1
- package/dist/test/tool-wrapper-prose-guard-integration.test.d.ts +0 -2
- package/dist/test/tool-wrapper-prose-guard-integration.test.d.ts.map +0 -1
- package/dist/test/tool-wrapper-prose-guard-integration.test.js +0 -485
- package/dist/test/tool-wrapper-prose-guard-integration.test.js.map +0 -1
- package/dist/test/tool-wrapper-prose-guard.test.d.ts +0 -2
- package/dist/test/tool-wrapper-prose-guard.test.d.ts.map +0 -1
- package/dist/test/tool-wrapper-prose-guard.test.js +0 -34
- package/dist/test/tool-wrapper-prose-guard.test.js.map +0 -1
- package/dist/test/tools-observe-parser-conformance.test.d.ts +0 -2
- package/dist/test/tools-observe-parser-conformance.test.d.ts.map +0 -1
- package/dist/test/tools-observe-parser-conformance.test.js +0 -129
- package/dist/test/tools-observe-parser-conformance.test.js.map +0 -1
- package/dist/test/trunk-channel-routing.test.d.ts +0 -19
- package/dist/test/trunk-channel-routing.test.d.ts.map +0 -1
- package/dist/test/trunk-channel-routing.test.js +0 -652
- package/dist/test/trunk-channel-routing.test.js.map +0 -1
- package/dist/test/tune-out-e2e.test.d.ts +0 -2
- package/dist/test/tune-out-e2e.test.d.ts.map +0 -1
- package/dist/test/tune-out-e2e.test.js +0 -142
- package/dist/test/tune-out-e2e.test.js.map +0 -1
- package/dist/test/tune-out-gate-composition.test.d.ts +0 -2
- package/dist/test/tune-out-gate-composition.test.d.ts.map +0 -1
- package/dist/test/tune-out-gate-composition.test.js +0 -221
- package/dist/test/tune-out-gate-composition.test.js.map +0 -1
- package/dist/test/tune-out-lifecycle.test.d.ts +0 -2
- package/dist/test/tune-out-lifecycle.test.d.ts.map +0 -1
- package/dist/test/tune-out-lifecycle.test.js +0 -121
- package/dist/test/tune-out-lifecycle.test.js.map +0 -1
- package/dist/test/turn-trigger-provenance.test.d.ts +0 -2
- package/dist/test/turn-trigger-provenance.test.d.ts.map +0 -1
- package/dist/test/turn-trigger-provenance.test.js +0 -137
- package/dist/test/turn-trigger-provenance.test.js.map +0 -1
- package/dist/test/unconvertible-tool-result.test.d.ts +0 -2
- package/dist/test/unconvertible-tool-result.test.d.ts.map +0 -1
- package/dist/test/unconvertible-tool-result.test.js +0 -358
- package/dist/test/unconvertible-tool-result.test.js.map +0 -1
- package/dist/test/unsent-compiles.test.d.ts +0 -2
- package/dist/test/unsent-compiles.test.d.ts.map +0 -1
- package/dist/test/unsent-compiles.test.js +0 -139
- package/dist/test/unsent-compiles.test.js.map +0 -1
- package/dist/test/usage-accounting.test.d.ts +0 -2
- package/dist/test/usage-accounting.test.d.ts.map +0 -1
- package/dist/test/usage-accounting.test.js +0 -13
- package/dist/test/usage-accounting.test.js.map +0 -1
- package/dist/test/usage-tracker.test.d.ts +0 -2
- package/dist/test/usage-tracker.test.d.ts.map +0 -1
- package/dist/test/usage-tracker.test.js +0 -129
- package/dist/test/usage-tracker.test.js.map +0 -1
- package/dist/test/utils-surface.test.d.ts +0 -2
- package/dist/test/utils-surface.test.d.ts.map +0 -1
- package/dist/test/utils-surface.test.js +0 -145
- package/dist/test/utils-surface.test.js.map +0 -1
- package/dist/test/workspace-branch-continuation.test.d.ts +0 -15
- package/dist/test/workspace-branch-continuation.test.d.ts.map +0 -1
- package/dist/test/workspace-branch-continuation.test.js +0 -183
- package/dist/test/workspace-branch-continuation.test.js.map +0 -1
- package/dist/test/workspace-materialize-freshness.test.d.ts +0 -16
- package/dist/test/workspace-materialize-freshness.test.d.ts.map +0 -1
- package/dist/test/workspace-materialize-freshness.test.js +0 -252
- package/dist/test/workspace-materialize-freshness.test.js.map +0 -1
- package/dist/test/workspace-path-containment.test.d.ts +0 -19
- package/dist/test/workspace-path-containment.test.d.ts.map +0 -1
- package/dist/test/workspace-path-containment.test.js +0 -91
- package/dist/test/workspace-path-containment.test.js.map +0 -1
- package/dist/test/workspace-read-file-from-disk.test.d.ts +0 -17
- package/dist/test/workspace-read-file-from-disk.test.d.ts.map +0 -1
- package/dist/test/workspace-read-file-from-disk.test.js +0 -174
- package/dist/test/workspace-read-file-from-disk.test.js.map +0 -1
- package/dist/test/workspace-read-image.test.d.ts +0 -2
- package/dist/test/workspace-read-image.test.d.ts.map +0 -1
- package/dist/test/workspace-read-image.test.js +0 -597
- package/dist/test/workspace-read-image.test.js.map +0 -1
- package/dist/test/workspace-read-text.test.d.ts +0 -2
- package/dist/test/workspace-read-text.test.d.ts.map +0 -1
- package/dist/test/workspace-read-text.test.js +0 -101
- package/dist/test/workspace-read-text.test.js.map +0 -1
- package/dist/test/workspace-restore-order.test.d.ts +0 -16
- package/dist/test/workspace-restore-order.test.d.ts.map +0 -1
- package/dist/test/workspace-restore-order.test.js +0 -140
- package/dist/test/workspace-restore-order.test.js.map +0 -1
- package/dist/test/workspace-three-way.test.d.ts +0 -12
- package/dist/test/workspace-three-way.test.d.ts.map +0 -1
- package/dist/test/workspace-three-way.test.js +0 -4094
- package/dist/test/workspace-three-way.test.js.map +0 -1
- package/dist/test/workspace-watcher.test.d.ts +0 -2
- package/dist/test/workspace-watcher.test.d.ts.map +0 -1
- package/dist/test/workspace-watcher.test.js +0 -281
- package/dist/test/workspace-watcher.test.js.map +0 -1
- package/dist/test/xml-round-persist.test.d.ts +0 -19
- package/dist/test/xml-round-persist.test.d.ts.map +0 -1
- package/dist/test/xml-round-persist.test.js +0 -235
- package/dist/test/xml-round-persist.test.js.map +0 -1
- package/dist/tsconfig.tsbuildinfo +0 -1
|
@@ -11,10 +11,10 @@
|
|
|
11
11
|
|
|
12
12
|
import { EventEmitter } from 'node:events';
|
|
13
13
|
|
|
14
|
-
import { openTransport, type McplTransport, type TransportCloseInfo } from './transport.js';
|
|
14
|
+
import { openTransport, STDERR_END_WAIT_MS, type McplTransport, type TransportCloseInfo } from './transport.js';
|
|
15
15
|
import { maskNegotiatedCapabilities } from './capability-mask.js';
|
|
16
16
|
import { CapabilityGrant, expandAdvertisementShorthand } from './capability-grant.js';
|
|
17
|
-
import { CAPABILITY_DISABLED } from './errors.js';
|
|
17
|
+
import { CAPABILITY_DISABLED, boundedForLog, describeCause } from './errors.js';
|
|
18
18
|
import { logDetail, logValue } from './log-value.js';
|
|
19
19
|
|
|
20
20
|
import type {
|
|
@@ -95,6 +95,20 @@ export function withStderr(error: unknown): string {
|
|
|
95
95
|
return '. The last of its stderr:' + tail.split('\n').map((line) => `\n stderr: ${logDetail(line)}`).join('');
|
|
96
96
|
}
|
|
97
97
|
|
|
98
|
+
/** A transport close's reason, as an error message gives it: the transport's
|
|
99
|
+
* own words. A WebSocket peer's close reason is the server's text
|
|
100
|
+
* (`reasonFromPeer`), so an error gives the words the transport uses for a
|
|
101
|
+
* close without one, as `mcpl:server-closed` leaves that text out. A
|
|
102
|
+
* WebSocket close's code, a number, says what the server meant (4001: a
|
|
103
|
+
* refused credential), with or without a reason, so each error gives it too:
|
|
104
|
+
* a pending request's error has `code=`, and the handshake's adds it for any
|
|
105
|
+
* WebSocket close, since a close before the handshake completes reaches no
|
|
106
|
+
* 'close' event. A stdio child's exit reads as before. */
|
|
107
|
+
function closeReasonText(info: TransportCloseInfo): string {
|
|
108
|
+
if (info.reasonFromPeer) return 'websocket closed';
|
|
109
|
+
return info.reason ?? 'unknown';
|
|
110
|
+
}
|
|
111
|
+
|
|
98
112
|
/** Default per-request timeout in milliseconds (see McplServerConfig.requestTimeoutMs).
|
|
99
113
|
* A live-but-wedged server (accepts requests, never answers, never closes its
|
|
100
114
|
* transport) would otherwise freeze the awaiting agent turn forever — no
|
|
@@ -105,6 +119,33 @@ const DEFAULT_REQUEST_TIMEOUT_MS = 60_000;
|
|
|
105
119
|
/** MCP protocol version used in the initialize handshake. */
|
|
106
120
|
const MCP_PROTOCOL_VERSION = '2024-11-05';
|
|
107
121
|
|
|
122
|
+
/**
|
|
123
|
+
* Why a request to an MCPL server produced no result, as far as the host can
|
|
124
|
+
* know it. Messages are unchanged from plain errors; the `outcome` makes the
|
|
125
|
+
* difference between "never left the host" and "left, and no answer came
|
|
126
|
+
* back" a fact a caller can act on instead of a string to match:
|
|
127
|
+
* - `not-sent`: the request was refused before anything was written (the
|
|
128
|
+
* connection was already closed);
|
|
129
|
+
* - `error-response`: the server answered with a JSON-RPC error (it may have
|
|
130
|
+
* acted before failing; the error alone does not say);
|
|
131
|
+
* - `no-response`: the request was handed to the transport and no answer
|
|
132
|
+
* came back (timeout, or the connection closed while awaiting). It does
|
|
133
|
+
* not prove the request reached the server — the transport can decline or
|
|
134
|
+
* drop a write — only that the host can no longer say it didn't.
|
|
135
|
+
*/
|
|
136
|
+
export class McplRequestError extends Error {
|
|
137
|
+
constructor(
|
|
138
|
+
message: string,
|
|
139
|
+
readonly outcome: 'not-sent' | 'error-response' | 'no-response',
|
|
140
|
+
/** The JSON-RPC error's `data`, verbatim, when the server supplied one
|
|
141
|
+
* (e.g. which parts of a multi-part send were posted). */
|
|
142
|
+
readonly data?: unknown,
|
|
143
|
+
) {
|
|
144
|
+
super(message);
|
|
145
|
+
this.name = 'McplRequestError';
|
|
146
|
+
}
|
|
147
|
+
}
|
|
148
|
+
|
|
108
149
|
/**
|
|
109
150
|
* Represents a pending JSON-RPC request awaiting a response.
|
|
110
151
|
*/
|
|
@@ -123,6 +164,13 @@ interface RequestOptions {
|
|
|
123
164
|
surfaceOrphanedResponse?: boolean;
|
|
124
165
|
}
|
|
125
166
|
|
|
167
|
+
/** A request's method for a log line, whatever the server sent there. */
|
|
168
|
+
function describeMethod(method: unknown): string {
|
|
169
|
+
return typeof method === 'string'
|
|
170
|
+
? `method ${logValue(method)}`
|
|
171
|
+
: `a method of type ${method === null ? 'null' : typeof method}`;
|
|
172
|
+
}
|
|
173
|
+
|
|
126
174
|
/**
|
|
127
175
|
* McplServerConnection manages a single JSON-RPC 2.0 connection to an
|
|
128
176
|
* MCPL server over stdio. Use the static `connect()` factory to create
|
|
@@ -255,7 +303,10 @@ export class McplServerConnection extends EventEmitter {
|
|
|
255
303
|
private pendingRequests = new Map<string | number, PendingRequest>();
|
|
256
304
|
/** Metadata retained after selected request deadlines so a late response is
|
|
257
305
|
* observable even though its original promise has already been rejected. */
|
|
258
|
-
private orphanedRequests = new Map<string | number, {
|
|
306
|
+
private orphanedRequests = new Map<string | number, {
|
|
307
|
+
method: string;
|
|
308
|
+
renderParams?: { featureSet: string; key: string; eventId: string; channelId?: string };
|
|
309
|
+
}>();
|
|
259
310
|
private closed = false;
|
|
260
311
|
/** Set by `reconnectAfterFailure()` before it closes a live transport, so
|
|
261
312
|
* the transport close handler reports that teardown as `byHost: true`. */
|
|
@@ -266,6 +317,9 @@ export class McplServerConnection extends EventEmitter {
|
|
|
266
317
|
|
|
267
318
|
/** Per-request timeout in ms (0 disables). See McplServerConfig.requestTimeoutMs. */
|
|
268
319
|
private requestTimeoutMs = DEFAULT_REQUEST_TIMEOUT_MS;
|
|
320
|
+
/** The deadline a channels/publish or channels/open request keeps when
|
|
321
|
+
* requestTimeoutMs is 0 (see sendChannelsPublish). */
|
|
322
|
+
private publishDeadlineMs = DEFAULT_REQUEST_TIMEOUT_MS;
|
|
269
323
|
|
|
270
324
|
// Event buffering: control-plane traffic can be released independently from
|
|
271
325
|
// inference-bearing data-plane traffic. This lets a server finish its own
|
|
@@ -274,15 +328,24 @@ export class McplServerConnection extends EventEmitter {
|
|
|
274
328
|
private controlPlaneReady = false;
|
|
275
329
|
private dataPlaneReady = false;
|
|
276
330
|
private bufferedEvents: Array<{ event: string; args: unknown[] }> = [];
|
|
277
|
-
/**
|
|
278
|
-
*
|
|
279
|
-
private
|
|
331
|
+
/** How many of bufferedEvents are server→host requests, each holding a
|
|
332
|
+
* responder its server waits on. Every change to bufferedEvents keeps it. */
|
|
333
|
+
private heldRequests = 0;
|
|
334
|
+
/** Cap on held notifications (responder-less events) during a plane pause
|
|
335
|
+
* (issue #122), counted apart from requests: past it, the oldest held
|
|
336
|
+
* notification is dropped. */
|
|
337
|
+
private static readonly MAX_HELD_NOTIFICATIONS = 1000;
|
|
338
|
+
/** Budget of held requests during a plane pause (#387), counted apart from
|
|
339
|
+
* notifications: past it, a request is refused at once, never dropped. It
|
|
340
|
+
* bounds a server that pipelines requests without waiting for answers. A
|
|
341
|
+
* server that doesn't send a refused request again loses it (discord-mcpl
|
|
342
|
+
* doesn't), so the budget sits far above the notifications' cap, to leave
|
|
343
|
+
* a busy server's long pause room. */
|
|
344
|
+
private static readonly MAX_HELD_REQUESTS = 10_000;
|
|
280
345
|
private droppedBufferedEvents = 0;
|
|
281
|
-
/**
|
|
282
|
-
*
|
|
283
|
-
|
|
284
|
-
* NEW arrivals during a pause, not churn from control-plane flushes). */
|
|
285
|
-
private flushDepth = 0;
|
|
346
|
+
/** Requests refused at the budget since the planes last opened (ready()),
|
|
347
|
+
* so each pause's first refusal is logged. */
|
|
348
|
+
private refusedHeldRequests = 0;
|
|
286
349
|
|
|
287
350
|
// Reconnect state (adapted from Anarchid/agent-framework@mcpl-module-proto)
|
|
288
351
|
private config: McplServerConfig | null = null;
|
|
@@ -301,6 +364,13 @@ export class McplServerConnection extends EventEmitter {
|
|
|
301
364
|
return this.reconnectEnabled;
|
|
302
365
|
}
|
|
303
366
|
|
|
367
|
+
/** Closed with no reconnect to come: after close(), whether or not its
|
|
368
|
+
* transport close succeeded, or a drop with reconnect off. A connection
|
|
369
|
+
* between retries keeps reconnectEnabled, so it isn't closed for good. */
|
|
370
|
+
private get closedForGood(): boolean {
|
|
371
|
+
return this.closed && !this.reconnectEnabled;
|
|
372
|
+
}
|
|
373
|
+
|
|
304
374
|
/**
|
|
305
375
|
* Private constructor. Use `McplServerConnection.connect()` instead.
|
|
306
376
|
*/
|
|
@@ -328,28 +398,38 @@ export class McplServerConnection extends EventEmitter {
|
|
|
328
398
|
* Mark the connection as ready — flushes any events that arrived between
|
|
329
399
|
* construction (when setupMessageRouting starts emitting) and now (when
|
|
330
400
|
* the caller has attached listeners via wireMcplEvents).
|
|
401
|
+
*
|
|
402
|
+
* Does nothing once the connection is closed for good. Its policy was reset
|
|
403
|
+
* when it closed, so what it held that needs a grant would be refused, and a
|
|
404
|
+
* closed connection sends no response, so nothing it held could be answered.
|
|
405
|
+
* Only what needs no grant would pass, to listeners of a server that won't
|
|
406
|
+
* be served again. A connection between retries isn't closed for good: what
|
|
407
|
+
* it held, such as a reconnect stub's connect-failed, still reaches its
|
|
408
|
+
* listeners.
|
|
331
409
|
*/
|
|
332
410
|
ready(): void {
|
|
411
|
+
if (this.closedForGood) return;
|
|
333
412
|
this.controlPlaneReady = true;
|
|
334
413
|
this.dataPlaneReady = true;
|
|
335
414
|
const pending = this.bufferedEvents;
|
|
336
415
|
this.bufferedEvents = [];
|
|
416
|
+
// The cap's drops are counted per pause: this flush ends one, so its line
|
|
417
|
+
// reports that pause's drops, and the next pause counts (and logs) its own.
|
|
418
|
+
const dropped = this.droppedBufferedEvents;
|
|
419
|
+
this.droppedBufferedEvents = 0;
|
|
420
|
+
this.heldRequests = 0;
|
|
421
|
+
this.refusedHeldRequests = 0;
|
|
337
422
|
if (pending.length > 200) {
|
|
338
423
|
console.error(
|
|
339
424
|
`[mcpl] ${this.id}: flushing ${pending.length} buffered event(s) synchronously ` +
|
|
340
|
-
`(long pause backlog${
|
|
425
|
+
`(long pause backlog${dropped > 0 ? `; ${dropped} dropped at cap` : ''})`,
|
|
341
426
|
);
|
|
342
427
|
}
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
// snapshot is being flushed; later data items must observe that pause.
|
|
349
|
-
this.emit(event, ...args);
|
|
350
|
-
}
|
|
351
|
-
} finally {
|
|
352
|
-
this.flushDepth--;
|
|
428
|
+
for (const { event, args } of pending) {
|
|
429
|
+
// Re-enter the gate for every buffered item. A control handler (notably
|
|
430
|
+
// tools/list_changed) may install a newer data-plane barrier while this
|
|
431
|
+
// snapshot is being flushed; later data items must observe that pause.
|
|
432
|
+
this.dispatchInboundEvent(event, ...args);
|
|
353
433
|
}
|
|
354
434
|
}
|
|
355
435
|
|
|
@@ -357,24 +437,22 @@ export class McplServerConnection extends EventEmitter {
|
|
|
357
437
|
* Release only server-establishment and lifecycle/control traffic. Responses
|
|
358
438
|
* to host requests are never event-buffered, so tools/list and tools/call
|
|
359
439
|
* responses remain live as well. Inference-bearing requests stay queued in
|
|
360
|
-
* their original relative order until {@link ready} is called.
|
|
440
|
+
* their original relative order until {@link ready} is called. Like
|
|
441
|
+
* {@link ready}, it does nothing once the connection is closed for good.
|
|
361
442
|
*/
|
|
362
443
|
readyControlPlane(): void {
|
|
444
|
+
if (this.closedForGood) return;
|
|
363
445
|
this.controlPlaneReady = true;
|
|
364
446
|
const pending = this.bufferedEvents;
|
|
365
447
|
this.bufferedEvents = [];
|
|
366
|
-
this.
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
this.emit(item.event, ...item.args);
|
|
375
|
-
}
|
|
376
|
-
} finally {
|
|
377
|
-
this.flushDepth--;
|
|
448
|
+
this.heldRequests = 0;
|
|
449
|
+
for (const item of pending) {
|
|
450
|
+
// Re-enter the ADMISSION gate (this.emit), never super.emit: control
|
|
451
|
+
// events include channels-register/changed, which are grant-gated —
|
|
452
|
+
// the old direct flush bypassed positive-grant enforcement entirely
|
|
453
|
+
// (PR #79 review blocker 3). Data-plane items re-buffer in order via
|
|
454
|
+
// the same call, since dataPlaneReady is still false.
|
|
455
|
+
this.dispatchInboundEvent(item.event, ...item.args);
|
|
378
456
|
}
|
|
379
457
|
}
|
|
380
458
|
|
|
@@ -433,40 +511,80 @@ export class McplServerConnection extends EventEmitter {
|
|
|
433
511
|
}
|
|
434
512
|
return true;
|
|
435
513
|
}
|
|
514
|
+
// §6.6: a request that will never be answered MUST get an error. A
|
|
515
|
+
// request whose event nothing on this host listens for would never be.
|
|
516
|
+
const request = args[1] as {
|
|
517
|
+
respond?: (result: unknown) => void;
|
|
518
|
+
respondError?: (code: number, message: string, data?: unknown) => void;
|
|
519
|
+
} | undefined;
|
|
520
|
+
if (typeof request?.respondError === 'function' && this.listenerCount(event) === 0) {
|
|
521
|
+
request.respondError(-32601, 'Method not found');
|
|
522
|
+
console.error(`[mcpl] ${this.id}: answered -32601 to ${logValue(name)}, which nothing on this host handles`);
|
|
523
|
+
return true;
|
|
524
|
+
}
|
|
525
|
+
// mcpl/manifestChanged (§17.3) and tools/list_changed are notifications.
|
|
526
|
+
// Sent as a request, either is answered with an empty result as it's
|
|
527
|
+
// admitted, and passed on as the notification is, with no responder:
|
|
528
|
+
// the host acts on it the same way, so the answer doesn't depend on what
|
|
529
|
+
// the refresh does, and it's written before any request the refresh
|
|
530
|
+
// sends. This is where live routing and buffer flushes meet, so a request
|
|
531
|
+
// held while its plane is closed is answered only when it's let through,
|
|
532
|
+
// never by a startup that fails first.
|
|
533
|
+
if ((name === 'manifest-changed' || name === 'tools-list-changed') && typeof request?.respond === 'function') {
|
|
534
|
+
request.respond({});
|
|
535
|
+
return super.emit(event, args[0]);
|
|
536
|
+
}
|
|
436
537
|
return super.emit(event, ...args);
|
|
437
538
|
}
|
|
438
|
-
//
|
|
439
|
-
//
|
|
440
|
-
//
|
|
441
|
-
// holds a
|
|
442
|
-
//
|
|
443
|
-
//
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
)
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
if (dropIndex >= 0) {
|
|
459
|
-
this.bufferedEvents.splice(dropIndex, 1); // drop-oldest non-request
|
|
460
|
-
this.bufferedEvents.push({ event: name, args });
|
|
461
|
-
}
|
|
462
|
-
// else: buffer is all held requests — drop the incoming event instead.
|
|
463
|
-
return true;
|
|
539
|
+
// Held until the plane opens. A long pause (a quiesce, say) on a busy or a
|
|
540
|
+
// runaway server would otherwise grow this array without bound, so
|
|
541
|
+
// requests and notifications each have a bound, counted apart. A request
|
|
542
|
+
// holds a responder its server waits on, and dropping it would strand that
|
|
543
|
+
// call, so past MAX_HELD_REQUESTS (#387) it's refused at once with -32000,
|
|
544
|
+
// the code of the host's other transient refusals, and its server can send
|
|
545
|
+
// it again. A notification has no one to tell, so past
|
|
546
|
+
// MAX_HELD_NOTIFICATIONS (issue #122) the oldest held notification is
|
|
547
|
+
// dropped to make room. A flush takes the whole buffer and zeroes its
|
|
548
|
+
// count, so what it holds again was admitted within these bounds and
|
|
549
|
+
// stays within them.
|
|
550
|
+
const responder = args[1] as { respond?: unknown; respondError?: (code: number, message: string) => void } | undefined;
|
|
551
|
+
const isRequest = McplServerConnection.hasResponder({ args });
|
|
552
|
+
if (isRequest && this.heldRequests >= McplServerConnection.MAX_HELD_REQUESTS) {
|
|
553
|
+
this.refusedHeldRequests++;
|
|
554
|
+
if (this.refusedHeldRequests % 100 === 1) {
|
|
555
|
+
console.error(
|
|
556
|
+
`[mcpl] ${this.id}: held-request budget (${McplServerConnection.MAX_HELD_REQUESTS}) — ` +
|
|
557
|
+
`refused ${this.refusedHeldRequests} request(s) with -32000 while the plane is paused`,
|
|
558
|
+
);
|
|
464
559
|
}
|
|
560
|
+
responder?.respondError?.(
|
|
561
|
+
-32000,
|
|
562
|
+
`the host is busy: ${McplServerConnection.MAX_HELD_REQUESTS} of this server's requests are already waiting; send this one again later`,
|
|
563
|
+
);
|
|
564
|
+
return true;
|
|
565
|
+
}
|
|
566
|
+
if (!isRequest && this.bufferedEvents.length - this.heldRequests >= McplServerConnection.MAX_HELD_NOTIFICATIONS) {
|
|
567
|
+
this.droppedBufferedEvents++;
|
|
568
|
+
if (this.droppedBufferedEvents % 100 === 1) {
|
|
569
|
+
console.error(
|
|
570
|
+
`[mcpl] ${this.id}: buffered-event cap (${McplServerConnection.MAX_HELD_NOTIFICATIONS}) — ` +
|
|
571
|
+
`dropped ${this.droppedBufferedEvents} responder-less event(s) while the plane is paused`,
|
|
572
|
+
);
|
|
573
|
+
}
|
|
574
|
+
const oldest = this.bufferedEvents.findIndex((item) => !McplServerConnection.hasResponder(item));
|
|
575
|
+
if (oldest >= 0) this.bufferedEvents.splice(oldest, 1);
|
|
465
576
|
}
|
|
466
577
|
this.bufferedEvents.push({ event: name, args });
|
|
578
|
+
if (isRequest) this.heldRequests++;
|
|
467
579
|
return true;
|
|
468
580
|
}
|
|
469
581
|
|
|
582
|
+
/** A buffered server→host request: it carries a responder its server waits on. */
|
|
583
|
+
private static hasResponder(item: { args: unknown[] }): boolean {
|
|
584
|
+
const responder = item.args[1] as { respond?: unknown } | undefined;
|
|
585
|
+
return typeof responder?.respond === 'function';
|
|
586
|
+
}
|
|
587
|
+
|
|
470
588
|
/** Event-name form of METHOD_TO_REQUIRED_CAPABILITY, for admission-time
|
|
471
589
|
* enforcement in emit(). */
|
|
472
590
|
private static readonly EVENT_TO_REQUIRED_CAPABILITY: Record<string, string> = {
|
|
@@ -533,8 +651,9 @@ export class McplServerConnection extends EventEmitter {
|
|
|
533
651
|
connection.allowHostCommands = config.allowHostCommands === true;
|
|
534
652
|
connection.requestTimeoutMs = config.requestTimeoutMs ?? DEFAULT_REQUEST_TIMEOUT_MS;
|
|
535
653
|
|
|
536
|
-
// Store config for reconnection
|
|
537
|
-
|
|
654
|
+
// Store config for reconnection. Only `true` turns reconnect on, as at
|
|
655
|
+
// every other reader of it.
|
|
656
|
+
if (config.reconnect === true) {
|
|
538
657
|
connection.config = config;
|
|
539
658
|
connection.hostCapabilities = hostCapabilities;
|
|
540
659
|
connection.reconnectEnabled = true;
|
|
@@ -606,10 +725,30 @@ export class McplServerConnection extends EventEmitter {
|
|
|
606
725
|
} catch {
|
|
607
726
|
return; // Ignore non-JSON lines (e.g. logback output from Java servers)
|
|
608
727
|
}
|
|
728
|
+
if (msg === null || typeof msg !== 'object' || Array.isArray(msg)) return;
|
|
729
|
+
// A request or a notification from the server is never the
|
|
730
|
+
// initialize response, whatever its id: a server's own ids can start
|
|
731
|
+
// at 0, this handshake's. MCP lets a server ping before
|
|
732
|
+
// initialization completes, and the ping gets its empty result, as
|
|
733
|
+
// on a connected transport. Anything else it sends now is ignored.
|
|
734
|
+
if ('method' in msg) {
|
|
735
|
+
const request = msg as unknown as JsonRpcRequest;
|
|
736
|
+
if (request.method === 'ping' && request.id != null) {
|
|
737
|
+
transport.writeLine(JSON.stringify({ jsonrpc: '2.0', id: request.id, result: {} }));
|
|
738
|
+
}
|
|
739
|
+
return;
|
|
740
|
+
}
|
|
609
741
|
if (msg.id !== initId) return;
|
|
610
742
|
cleanup();
|
|
611
743
|
if (msg.error) {
|
|
612
|
-
|
|
744
|
+
// describeCause rather than the template's own conversion: the
|
|
745
|
+
// server's `message` can be any JSON value, and one that has no
|
|
746
|
+
// primitive form, such as {"toString":1}, would throw out of this
|
|
747
|
+
// listener after cleanup() has cleared the timeout: an uncaught
|
|
748
|
+
// exception, which ends a host that doesn't catch them, and a
|
|
749
|
+
// handshake left to wait forever. It's the server's text in an
|
|
750
|
+
// error's message, so it's bounded as errors.ts says.
|
|
751
|
+
reject(new Error(`MCPL server "${config.id}" initialize error: ${boundedForLog(describeCause(msg.error.message))}`));
|
|
613
752
|
return;
|
|
614
753
|
}
|
|
615
754
|
const result = msg.result as Record<string, unknown> | undefined;
|
|
@@ -625,7 +764,14 @@ export class McplServerConnection extends EventEmitter {
|
|
|
625
764
|
};
|
|
626
765
|
const onClose = (info: TransportCloseInfo) => {
|
|
627
766
|
cleanup();
|
|
628
|
-
|
|
767
|
+
const code = transport.kind === 'websocket' && typeof info.code === 'number' ? `, code ${info.code}` : '';
|
|
768
|
+
const failure = `MCPL server "${config.id}" transport closed before handshake completed (${closeReasonText(info)}${code})`;
|
|
769
|
+
// The close comes at a stdio child's exit, which Node can emit before
|
|
770
|
+
// it has read the last of the child's stderr, or when the host closes
|
|
771
|
+
// the transport, which then ends the child. The tail is taken once
|
|
772
|
+
// stderr has ended, waiting at most STDERR_END_WAIT_MS. A WebSocket
|
|
773
|
+
// transport has no stderr to wait for.
|
|
774
|
+
void transport.stderrEnded(STDERR_END_WAIT_MS).then(() => reject(failed(failure)));
|
|
629
775
|
};
|
|
630
776
|
const onError = (err: Error) => {
|
|
631
777
|
cleanup();
|
|
@@ -683,7 +829,7 @@ export class McplServerConnection extends EventEmitter {
|
|
|
683
829
|
try {
|
|
684
830
|
return await McplServerConnection.connect(config, hostCapabilities);
|
|
685
831
|
} catch (error) {
|
|
686
|
-
if (
|
|
832
|
+
if (config.reconnect !== true) {
|
|
687
833
|
throw error;
|
|
688
834
|
}
|
|
689
835
|
|
|
@@ -798,9 +944,13 @@ export class McplServerConnection extends EventEmitter {
|
|
|
798
944
|
return this.sendRequest(McplMethod.StateRollback, params as unknown as Record<string, unknown>) as Promise<StateRollbackResult>;
|
|
799
945
|
}
|
|
800
946
|
|
|
801
|
-
/** Send `channels/open` request and await result.
|
|
947
|
+
/** Send `channels/open` request and await result. It keeps a deadline as
|
|
948
|
+
* channels/publish does: a delivery opens a closed channel before it
|
|
949
|
+
* publishes, so an open that is never answered would hold the delivery,
|
|
950
|
+
* and the turn that waits for it, for good. */
|
|
802
951
|
sendChannelsOpen(params: ChannelsOpenParams): Promise<ChannelsOpenResult> {
|
|
803
|
-
|
|
952
|
+
const timeoutMs = this.requestTimeoutMs > 0 ? this.requestTimeoutMs : this.publishDeadlineMs;
|
|
953
|
+
return this.sendRequest(McplMethod.ChannelsOpen, params as unknown as Record<string, unknown>, { timeoutMs }) as Promise<ChannelsOpenResult>;
|
|
804
954
|
}
|
|
805
955
|
|
|
806
956
|
/** Send `channels/close` request and await result. */
|
|
@@ -825,13 +975,20 @@ export class McplServerConnection extends EventEmitter {
|
|
|
825
975
|
* Send `channels/publish`.
|
|
826
976
|
* May be sent as a request (if an ACK is desired) or notification.
|
|
827
977
|
* When `params.stream` is true, sends as a notification (no ACK).
|
|
978
|
+
*
|
|
979
|
+
* A request always has a deadline: the server's requestTimeoutMs, or
|
|
980
|
+
* publishDeadlineMs when that is 0 (disabled). A publish is a side effect
|
|
981
|
+
* whose outcome the resident is told and a held draft's attempt records,
|
|
982
|
+
* so one that is never answered would hold both open for good. Its expiry
|
|
983
|
+
* is a no-response, which the caller reads as unknown.
|
|
828
984
|
*/
|
|
829
985
|
sendChannelsPublish(params: ChannelsPublishParams): Promise<ChannelsPublishResult | void> {
|
|
830
986
|
if (params.stream) {
|
|
831
987
|
this.sendNotification(McplMethod.ChannelsPublish, params as unknown as Record<string, unknown>);
|
|
832
988
|
return Promise.resolve();
|
|
833
989
|
}
|
|
834
|
-
|
|
990
|
+
const timeoutMs = this.requestTimeoutMs > 0 ? this.requestTimeoutMs : this.publishDeadlineMs;
|
|
991
|
+
return this.sendRequest(McplMethod.ChannelsPublish, params as unknown as Record<string, unknown>, { timeoutMs }) as Promise<ChannelsPublishResult>;
|
|
835
992
|
}
|
|
836
993
|
|
|
837
994
|
/** Send `channels/outgoing/chunk` notification. */
|
|
@@ -924,7 +1081,7 @@ export class McplServerConnection extends EventEmitter {
|
|
|
924
1081
|
// Reject all pending requests
|
|
925
1082
|
for (const [id, pending] of this.pendingRequests) {
|
|
926
1083
|
if (pending.timer) clearTimeout(pending.timer);
|
|
927
|
-
pending.reject(new
|
|
1084
|
+
pending.reject(new McplRequestError(`Connection to MCPL server "${this.id}" closed while awaiting response for ${pending.method} (id=${id})`, 'no-response'));
|
|
928
1085
|
}
|
|
929
1086
|
this.pendingRequests.clear();
|
|
930
1087
|
this.orphanedRequests.clear();
|
|
@@ -935,7 +1092,8 @@ export class McplServerConnection extends EventEmitter {
|
|
|
935
1092
|
const attempt = Promise.resolve().then(async () => {
|
|
936
1093
|
// An already opened handshake owns a transport too. It hands that
|
|
937
1094
|
// transport back without admission once reconnect has been disabled.
|
|
938
|
-
//
|
|
1095
|
+
// Only the registry's closeAll bounds its caller's wait for this; retry
|
|
1096
|
+
// reuses this real close attempt.
|
|
939
1097
|
if (this.reconnectPromise) await this.reconnectPromise;
|
|
940
1098
|
if (this.transport) await this.transport.close();
|
|
941
1099
|
this.closeIncomplete = false;
|
|
@@ -1099,7 +1257,7 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1099
1257
|
options: RequestOptions = {},
|
|
1100
1258
|
): Promise<unknown> {
|
|
1101
1259
|
if (this.closed) {
|
|
1102
|
-
return Promise.reject(new
|
|
1260
|
+
return Promise.reject(new McplRequestError(`Cannot send request: connection to "${this.id}" is closed`, 'not-sent'));
|
|
1103
1261
|
}
|
|
1104
1262
|
|
|
1105
1263
|
const id = this.nextRequestId++;
|
|
@@ -1117,23 +1275,47 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1117
1275
|
pending.timer = setTimeout(() => {
|
|
1118
1276
|
this.pendingRequests.delete(id);
|
|
1119
1277
|
if (options.surfaceOrphanedResponse) {
|
|
1120
|
-
this.orphanedRequests.set(id, {
|
|
1278
|
+
this.orphanedRequests.set(id, {
|
|
1279
|
+
method,
|
|
1280
|
+
...(method === 'push/render'
|
|
1281
|
+
? {
|
|
1282
|
+
renderParams: {
|
|
1283
|
+
featureSet: params.featureSet as string,
|
|
1284
|
+
key: params.key as string,
|
|
1285
|
+
eventId: params.eventId as string,
|
|
1286
|
+
...(typeof params.channelId === 'string' ? { channelId: params.channelId } : {}),
|
|
1287
|
+
},
|
|
1288
|
+
}
|
|
1289
|
+
: {}),
|
|
1290
|
+
});
|
|
1121
1291
|
if (this.orphanedRequests.size > 4096) this.orphanedRequests.delete(this.orphanedRequests.keys().next().value!);
|
|
1122
1292
|
}
|
|
1123
|
-
reject(new
|
|
1293
|
+
reject(new McplRequestError(
|
|
1124
1294
|
`MCPL server "${this.id}" did not respond to ${method} (id=${id}) ` +
|
|
1125
1295
|
`within ${timeoutMs}ms — the server may be hung. The response ` +
|
|
1126
1296
|
`outcome is unknown: the request was abandoned locally but was not ` +
|
|
1127
1297
|
`cancelled, so the tool may still have completed server-side; verify ` +
|
|
1128
1298
|
`state before retrying; a blind retry of a stateful/side-effecting ` +
|
|
1129
1299
|
`tool may duplicate it.`,
|
|
1300
|
+
'no-response',
|
|
1130
1301
|
));
|
|
1131
1302
|
}, timeoutMs);
|
|
1132
1303
|
// Don't hold the event loop open for the watchdog alone.
|
|
1133
1304
|
pending.timer.unref?.();
|
|
1134
1305
|
}
|
|
1135
1306
|
this.pendingRequests.set(id, pending);
|
|
1136
|
-
|
|
1307
|
+
try {
|
|
1308
|
+
this.transport!.writeLine(JSON.stringify(request));
|
|
1309
|
+
} catch (err) {
|
|
1310
|
+
// A synchronous write rejection sent no request. Remove its pending
|
|
1311
|
+
// state and watchdog before reporting that it is safe to retry.
|
|
1312
|
+
this.pendingRequests.delete(id);
|
|
1313
|
+
if (pending.timer) clearTimeout(pending.timer);
|
|
1314
|
+
reject(new McplRequestError(
|
|
1315
|
+
`Cannot send ${method} to MCPL server "${this.id}": ${err instanceof Error ? err.message : String(err)}`,
|
|
1316
|
+
'not-sent',
|
|
1317
|
+
));
|
|
1318
|
+
}
|
|
1137
1319
|
});
|
|
1138
1320
|
}
|
|
1139
1321
|
|
|
@@ -1223,7 +1405,9 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1223
1405
|
this.setupLifecycle(transport);
|
|
1224
1406
|
// Surface transport diagnostics (stdio child stderr) as 'stderr' events,
|
|
1225
1407
|
// preserving the `{ line }` payload existing consumers expect.
|
|
1226
|
-
|
|
1408
|
+
// Through the same containment boundary as every inbound event, so a
|
|
1409
|
+
// stderr listener that throws is reported, not thrown into the transport.
|
|
1410
|
+
transport.on('stderr', (line: string) => this.dispatchInboundEvent('stderr', { line }));
|
|
1227
1411
|
}
|
|
1228
1412
|
|
|
1229
1413
|
/**
|
|
@@ -1239,61 +1423,148 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1239
1423
|
return;
|
|
1240
1424
|
}
|
|
1241
1425
|
|
|
1242
|
-
//
|
|
1243
|
-
|
|
1244
|
-
|
|
1245
|
-
|
|
1426
|
+
// JSON-RPC messages must be objects. Ignore unrelated stdout/log values
|
|
1427
|
+
// before property access, just as malformed JSON lines are ignored.
|
|
1428
|
+
if (msg === null || typeof msg !== 'object' || Array.isArray(msg)) return;
|
|
1429
|
+
try {
|
|
1430
|
+
this.dispatchMessage(msg);
|
|
1431
|
+
} catch (error) {
|
|
1432
|
+
const request = msg as { method?: unknown; id?: unknown };
|
|
1433
|
+
this.reportInboundFailure(error, {
|
|
1434
|
+
...(typeof request.method === 'string' ? { event: request.method } : {}),
|
|
1435
|
+
...(typeof request.id === 'string' || typeof request.id === 'number' ? { requestId: request.id } : {}),
|
|
1436
|
+
});
|
|
1246
1437
|
}
|
|
1438
|
+
});
|
|
1439
|
+
}
|
|
1247
1440
|
|
|
1248
|
-
|
|
1249
|
-
|
|
1250
|
-
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1441
|
+
/** Contain synchronous dispatch failures; async RPC handlers own their promises. */
|
|
1442
|
+
private dispatchMessage(msg: JsonRpcRequest | JsonRpcResponse): void {
|
|
1443
|
+
// Is this a response to one of our outbound requests?
|
|
1444
|
+
if ('id' in msg && msg.id != null && !('method' in msg)) {
|
|
1445
|
+
this.handleResponse(msg as JsonRpcResponse);
|
|
1446
|
+
return;
|
|
1447
|
+
}
|
|
1448
|
+
|
|
1449
|
+
// It is an inbound request or notification from the server
|
|
1450
|
+
const request = msg as JsonRpcRequest;
|
|
1451
|
+
|
|
1452
|
+
// MCP's ping, which either side may send: its receiver answers promptly
|
|
1453
|
+
// with an empty result. It's answered as it arrives, before admission and
|
|
1454
|
+
// buffering, since it asks only whether the connection is alive, and a
|
|
1455
|
+
// paused plane mustn't hold that answer. A ping sent as a notification
|
|
1456
|
+
// has nothing to answer. The handshake answers one too.
|
|
1457
|
+
if (request.method === 'ping') {
|
|
1458
|
+
if (request.id != null) this.sendResponse(request.id, {});
|
|
1459
|
+
return;
|
|
1460
|
+
}
|
|
1461
|
+
|
|
1462
|
+
const eventName = typeof request.method === 'string' && Object.hasOwn(McplServerConnection.METHOD_TO_EVENT, request.method)
|
|
1463
|
+
? McplServerConnection.METHOD_TO_EVENT[request.method] : undefined;
|
|
1464
|
+
|
|
1465
|
+
// §7 is removed in 0.5.0: scope/elevate is no longer a method. Answer
|
|
1466
|
+
// rather than hang (§6.6 — a method that will never be answered MUST
|
|
1467
|
+
// return an error).
|
|
1468
|
+
// featureSets/changed is REMOVED in 0.5.0 (§6.7 — it carried a
|
|
1469
|
+
// server-authored change payload, the self-attestation defect; the
|
|
1470
|
+
// need is met by §17's host-diffed manifest fetch). It was still
|
|
1471
|
+
// routed, control-plane classified, and mutating declarations — a
|
|
1472
|
+
// live ungated self-attestation path (PR #79 review blocker 4).
|
|
1473
|
+
if (request.method === McplMethod.FeatureSetsChanged) {
|
|
1474
|
+
if (request.id != null) {
|
|
1475
|
+
this.sendErrorResponse(request.id, -32601, 'featureSets/changed removed in MCPL 0.5.0 (superseded by mcpl/manifestChanged, SPEC §17)');
|
|
1476
|
+
} else {
|
|
1477
|
+
console.error(`[mcpl] ${this.id}: discarded featureSets/changed — removed in 0.5.0 (§6.7/§17)`);
|
|
1267
1478
|
}
|
|
1479
|
+
return;
|
|
1480
|
+
}
|
|
1268
1481
|
|
|
1269
|
-
|
|
1270
|
-
|
|
1271
|
-
|
|
1272
|
-
}
|
|
1273
|
-
return;
|
|
1482
|
+
if (request.method === McplMethod.ScopeElevate) {
|
|
1483
|
+
if (request.id != null) {
|
|
1484
|
+
this.sendErrorResponse(request.id, -32601, 'scope/elevate removed in MCPL 0.5.0 (SPEC §7)');
|
|
1274
1485
|
}
|
|
1486
|
+
return;
|
|
1487
|
+
}
|
|
1275
1488
|
|
|
1276
|
-
|
|
1277
|
-
|
|
1278
|
-
|
|
1279
|
-
|
|
1280
|
-
|
|
1281
|
-
|
|
1282
|
-
|
|
1283
|
-
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
|
|
1287
|
-
|
|
1288
|
-
|
|
1289
|
-
this.sendErrorResponse(request.id!, code, message, data),
|
|
1290
|
-
});
|
|
1291
|
-
} else {
|
|
1292
|
-
// Notification — no response expected
|
|
1293
|
-
this.emit(eventName, request.params);
|
|
1294
|
-
}
|
|
1489
|
+
// Positive-grant enforcement (§5.4, §14.1) happens at ADMISSION, in
|
|
1490
|
+
// the emit() override below — the one choke-point that live routing
|
|
1491
|
+
// and staged-buffer flushes share. See the comment there for why
|
|
1492
|
+
// rejecting here, at line receipt, was wrong for staged connections.
|
|
1493
|
+
|
|
1494
|
+
if (!eventName) {
|
|
1495
|
+
// §6.6: a request that will never be answered MUST get an error, so a
|
|
1496
|
+
// request (it has an id) whose method isn't a string, or isn't one this
|
|
1497
|
+
// host handles, is answered -32601. A notification nobody handles is
|
|
1498
|
+
// ignored, as JSON-RPC asks.
|
|
1499
|
+
if (request.id != null) {
|
|
1500
|
+
this.sendErrorResponse(request.id, -32601, 'Method not found');
|
|
1501
|
+
console.error(`[mcpl] ${this.id}: answered -32601 to a request for ${describeMethod(request.method)}, which this host doesn't handle`);
|
|
1295
1502
|
}
|
|
1296
|
-
|
|
1503
|
+
return;
|
|
1504
|
+
}
|
|
1505
|
+
|
|
1506
|
+
// Emit the typed event with params and (for requests) a respond callback
|
|
1507
|
+
if (request.id != null) {
|
|
1508
|
+
// Server expects a response — provide a respond helper
|
|
1509
|
+
this.dispatchInboundEvent(eventName, request.params, {
|
|
1510
|
+
id: request.id,
|
|
1511
|
+
respond: (result: unknown) => this.sendResponse(request.id!, result),
|
|
1512
|
+
respondError: (code: number, message: string, data?: unknown) =>
|
|
1513
|
+
this.sendErrorResponse(request.id!, code, message, data),
|
|
1514
|
+
});
|
|
1515
|
+
} else {
|
|
1516
|
+
// Notification — no response expected
|
|
1517
|
+
this.dispatchInboundEvent(eventName, request.params);
|
|
1518
|
+
}
|
|
1519
|
+
}
|
|
1520
|
+
|
|
1521
|
+
/** Live delivery and delayed plane flushes share the same containment boundary. */
|
|
1522
|
+
private dispatchInboundEvent(event: string, ...args: unknown[]): void {
|
|
1523
|
+
try {
|
|
1524
|
+
this.emit(event, ...args);
|
|
1525
|
+
} catch (error) {
|
|
1526
|
+
const requestId = (args[1] as { id?: unknown } | undefined)?.id;
|
|
1527
|
+
this.reportInboundFailure(error, {
|
|
1528
|
+
event,
|
|
1529
|
+
...(typeof requestId === 'string' || typeof requestId === 'number' ? { requestId } : {}),
|
|
1530
|
+
});
|
|
1531
|
+
}
|
|
1532
|
+
}
|
|
1533
|
+
|
|
1534
|
+
/** Report a failure the containment boundary caught, naming the event (or
|
|
1535
|
+
* method) and request it was dispatching, and what failed. The message is
|
|
1536
|
+
* what the framework's 'error' listener traces. */
|
|
1537
|
+
private reportInboundFailure(cause: unknown, context: { event?: string; requestId?: string | number } = {}): void {
|
|
1538
|
+
const where = (show: (text: string) => string): string => (context.event === undefined ? '' : ` for ${show(context.event)}`) +
|
|
1539
|
+
(context.requestId === undefined ? '' : ` (request ${show(String(context.requestId))})`);
|
|
1540
|
+
// The error's message is what the 'error' listener traces, as text a
|
|
1541
|
+
// reader parses, so it is bounded rather than escaped (boundedForLog);
|
|
1542
|
+
// the log line prints the same through log-value.
|
|
1543
|
+
const error = new Error(`MCPL server "${this.id}" inbound dispatch failed${where(boundedForLog)}: ${boundedForLog(describeCause(cause))}`, { cause });
|
|
1544
|
+
console.error(`[mcpl] ${this.id}: inbound dispatch failed${where(logValue)}: ${logDetail(describeCause(cause))}`);
|
|
1545
|
+
this.emitToErrorListeners(error);
|
|
1546
|
+
}
|
|
1547
|
+
|
|
1548
|
+
/**
|
|
1549
|
+
* Give an error to the connection's 'error' listeners, and say whether it
|
|
1550
|
+
* has any. EventEmitter throws an 'error' that nothing listens for, and
|
|
1551
|
+
* from a transport's callback, where these errors arise, nothing catches
|
|
1552
|
+
* that throw, so it ends the process. A bare connection has no listener:
|
|
1553
|
+
* the class is exported, and a probe, a playtest or a harness often attaches
|
|
1554
|
+
* none. So with no listener, the error is the caller's to log, unless it
|
|
1555
|
+
* already has. A listener that throws is caught and logged, with the error
|
|
1556
|
+
* it was handling.
|
|
1557
|
+
*/
|
|
1558
|
+
private emitToErrorListeners(error: Error): boolean {
|
|
1559
|
+
if (this.listenerCount('error') === 0) return false;
|
|
1560
|
+
try { this.emit('error', error); }
|
|
1561
|
+
catch (listenerError) {
|
|
1562
|
+
console.error(
|
|
1563
|
+
`[mcpl] ${this.id}: an 'error' listener failed: ${logDetail(describeCause(listenerError))}` +
|
|
1564
|
+
`, handling ${logDetail(error.message)}`,
|
|
1565
|
+
);
|
|
1566
|
+
}
|
|
1567
|
+
return true;
|
|
1297
1568
|
}
|
|
1298
1569
|
|
|
1299
1570
|
/**
|
|
@@ -1310,10 +1581,17 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1310
1581
|
// re-inject either result because the original dispatch context is gone.
|
|
1311
1582
|
const orphaned = this.orphanedRequests.get(response.id);
|
|
1312
1583
|
this.orphanedRequests.delete(response.id);
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
|
|
1316
|
-
|
|
1584
|
+
// A push/render answered after its timeout (RFC-006 §5.3) is reported
|
|
1585
|
+
// with the render's featureSet, key, eventId and, for a channel-scoped
|
|
1586
|
+
// subject, channelId, kept from its request when the timeout fired, so
|
|
1587
|
+
// its discarded answer can be recorded beside its batch's other
|
|
1588
|
+
// coalescing records (§11). It is only reported: the fallback the
|
|
1589
|
+
// timeout materialized stands (§5.4 rule 3). A late JSON-RPC error is
|
|
1590
|
+
// passed on as `error`, so its record can be told from a late result's,
|
|
1591
|
+
// and so is one beside a result, which JSON-RPC forbids: the live path
|
|
1592
|
+
// rejects such an answer as an error.
|
|
1593
|
+
const render = orphaned?.renderParams ?? {};
|
|
1594
|
+
const failure = response.error ? { error: { code: response.error.code, message: response.error.message } } : {};
|
|
1317
1595
|
const result = response.result;
|
|
1318
1596
|
if (result && typeof result === 'object') {
|
|
1319
1597
|
const r = result as { state?: unknown; checkpoint?: unknown };
|
|
@@ -1323,6 +1601,8 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1323
1601
|
method: orphaned?.method,
|
|
1324
1602
|
hadState: r.state !== undefined,
|
|
1325
1603
|
hadCheckpoint: r.checkpoint !== undefined,
|
|
1604
|
+
...render,
|
|
1605
|
+
...failure,
|
|
1326
1606
|
});
|
|
1327
1607
|
}
|
|
1328
1608
|
} else if (orphaned) {
|
|
@@ -1331,6 +1611,8 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1331
1611
|
method: orphaned.method,
|
|
1332
1612
|
hadState: false,
|
|
1333
1613
|
hadCheckpoint: false,
|
|
1614
|
+
...render,
|
|
1615
|
+
...failure,
|
|
1334
1616
|
});
|
|
1335
1617
|
}
|
|
1336
1618
|
return; // Orphaned response — ignore
|
|
@@ -1340,8 +1622,19 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1340
1622
|
if (pending.timer) clearTimeout(pending.timer);
|
|
1341
1623
|
|
|
1342
1624
|
if (response.error) {
|
|
1625
|
+
// describeCause rather than the template's own conversion, as for an
|
|
1626
|
+
// initialize error: the server's code and message can be any JSON
|
|
1627
|
+
// value, and one with no primitive form, such as {"toString":1}, would
|
|
1628
|
+
// throw here, after the request has left pendingRequests and its timer
|
|
1629
|
+
// is cleared, so it would never settle. Both are the server's text, a
|
|
1630
|
+
// code as much as a message, since a server can send a string, so both
|
|
1631
|
+
// are bounded as errors.ts says.
|
|
1343
1632
|
pending.reject(
|
|
1344
|
-
new
|
|
1633
|
+
new McplRequestError(
|
|
1634
|
+
`MCPL server "${this.id}" returned error for ${pending.method}: [${boundedForLog(describeCause(response.error.code))}] ${boundedForLog(describeCause(response.error.message))}`,
|
|
1635
|
+
'error-response',
|
|
1636
|
+
(response.error as { data?: unknown }).data,
|
|
1637
|
+
),
|
|
1345
1638
|
);
|
|
1346
1639
|
} else {
|
|
1347
1640
|
pending.resolve(response.result);
|
|
@@ -1382,7 +1675,8 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1382
1675
|
private setupLifecycle(transport: McplTransport): void {
|
|
1383
1676
|
this.hostCloseRequested = false;
|
|
1384
1677
|
transport.on('error', (err: Error) => {
|
|
1385
|
-
|
|
1678
|
+
const error = new Error(`MCPL server "${this.id}" transport error: ${err.message}`);
|
|
1679
|
+
if (!this.emitToErrorListeners(error)) console.error(`[mcpl] ${this.id}: transport error: ${logDetail(err.message)}`);
|
|
1386
1680
|
});
|
|
1387
1681
|
|
|
1388
1682
|
transport.on('close', (info: TransportCloseInfo) => {
|
|
@@ -1394,8 +1688,9 @@ export class McplServerConnection extends EventEmitter {
|
|
|
1394
1688
|
for (const [id, pending] of this.pendingRequests) {
|
|
1395
1689
|
if (pending.timer) clearTimeout(pending.timer);
|
|
1396
1690
|
pending.reject(
|
|
1397
|
-
new
|
|
1398
|
-
`MCPL server "${this.id}" disconnected unexpectedly (code=${info.code ?? 'n/a'}, signal=${info.signal ?? 'n/a'}, reason=${info
|
|
1691
|
+
new McplRequestError(
|
|
1692
|
+
`MCPL server "${this.id}" disconnected unexpectedly (code=${info.code ?? 'n/a'}, signal=${info.signal ?? 'n/a'}, reason=${closeReasonText(info)}) while awaiting ${pending.method} (id=${id})`,
|
|
1693
|
+
'no-response',
|
|
1399
1694
|
),
|
|
1400
1695
|
);
|
|
1401
1696
|
}
|