attocode 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +48 -0
- package/LICENSE +21 -0
- package/README.md +164 -0
- package/dist/src/adapters.d.ts +83 -0
- package/dist/src/adapters.d.ts.map +1 -0
- package/dist/src/adapters.js +221 -0
- package/dist/src/adapters.js.map +1 -0
- package/dist/src/agent-tools/index.d.ts +7 -0
- package/dist/src/agent-tools/index.d.ts.map +1 -0
- package/dist/src/agent-tools/index.js +8 -0
- package/dist/src/agent-tools/index.js.map +1 -0
- package/dist/src/agent-tools/lsp-file-tools.d.ts +33 -0
- package/dist/src/agent-tools/lsp-file-tools.d.ts.map +1 -0
- package/dist/src/agent-tools/lsp-file-tools.js +200 -0
- package/dist/src/agent-tools/lsp-file-tools.js.map +1 -0
- package/dist/src/agent.d.ts +667 -0
- package/dist/src/agent.d.ts.map +1 -0
- package/dist/src/agent.js +2824 -0
- package/dist/src/agent.js.map +1 -0
- package/dist/src/cli.d.ts +36 -0
- package/dist/src/cli.d.ts.map +1 -0
- package/dist/src/cli.js +176 -0
- package/dist/src/cli.js.map +1 -0
- package/dist/src/commands/handler.d.ts +22 -0
- package/dist/src/commands/handler.d.ts.map +1 -0
- package/dist/src/commands/handler.js +1320 -0
- package/dist/src/commands/handler.js.map +1 -0
- package/dist/src/commands/init.d.ts +7 -0
- package/dist/src/commands/init.d.ts.map +1 -0
- package/dist/src/commands/init.js +153 -0
- package/dist/src/commands/init.js.map +1 -0
- package/dist/src/commands/types.d.ts +70 -0
- package/dist/src/commands/types.d.ts.map +1 -0
- package/dist/src/commands/types.js +8 -0
- package/dist/src/commands/types.js.map +1 -0
- package/dist/src/config.d.ts +22 -0
- package/dist/src/config.d.ts.map +1 -0
- package/dist/src/config.js +25 -0
- package/dist/src/config.js.map +1 -0
- package/dist/src/core/index.d.ts +32 -0
- package/dist/src/core/index.d.ts.map +1 -0
- package/dist/src/core/index.js +35 -0
- package/dist/src/core/index.js.map +1 -0
- package/dist/src/core/process-handlers.d.ts +43 -0
- package/dist/src/core/process-handlers.d.ts.map +1 -0
- package/dist/src/core/process-handlers.js +117 -0
- package/dist/src/core/process-handlers.js.map +1 -0
- package/dist/src/core/protocol/bridge.d.ts +117 -0
- package/dist/src/core/protocol/bridge.d.ts.map +1 -0
- package/dist/src/core/protocol/bridge.js +149 -0
- package/dist/src/core/protocol/bridge.js.map +1 -0
- package/dist/src/core/protocol/index.d.ts +8 -0
- package/dist/src/core/protocol/index.d.ts.map +1 -0
- package/dist/src/core/protocol/index.js +8 -0
- package/dist/src/core/protocol/index.js.map +1 -0
- package/dist/src/core/protocol/types.d.ts +539 -0
- package/dist/src/core/protocol/types.d.ts.map +1 -0
- package/dist/src/core/protocol/types.js +149 -0
- package/dist/src/core/protocol/types.js.map +1 -0
- package/dist/src/core/queues/atomic-counter.d.ts +36 -0
- package/dist/src/core/queues/atomic-counter.d.ts.map +1 -0
- package/dist/src/core/queues/atomic-counter.js +46 -0
- package/dist/src/core/queues/atomic-counter.js.map +1 -0
- package/dist/src/core/queues/event-queue.d.ts +126 -0
- package/dist/src/core/queues/event-queue.d.ts.map +1 -0
- package/dist/src/core/queues/event-queue.js +208 -0
- package/dist/src/core/queues/event-queue.js.map +1 -0
- package/dist/src/core/queues/index.d.ts +12 -0
- package/dist/src/core/queues/index.d.ts.map +1 -0
- package/dist/src/core/queues/index.js +15 -0
- package/dist/src/core/queues/index.js.map +1 -0
- package/dist/src/core/queues/submission-queue.d.ts +116 -0
- package/dist/src/core/queues/submission-queue.d.ts.map +1 -0
- package/dist/src/core/queues/submission-queue.js +236 -0
- package/dist/src/core/queues/submission-queue.js.map +1 -0
- package/dist/src/costs/index.d.ts +22 -0
- package/dist/src/costs/index.d.ts.map +1 -0
- package/dist/src/costs/index.js +22 -0
- package/dist/src/costs/index.js.map +1 -0
- package/dist/src/costs/model-registry.d.ts +80 -0
- package/dist/src/costs/model-registry.d.ts.map +1 -0
- package/dist/src/costs/model-registry.js +237 -0
- package/dist/src/costs/model-registry.js.map +1 -0
- package/dist/src/costs/types.d.ts +50 -0
- package/dist/src/costs/types.d.ts.map +1 -0
- package/dist/src/costs/types.js +2 -0
- package/dist/src/costs/types.js.map +1 -0
- package/dist/src/defaults.d.ts +114 -0
- package/dist/src/defaults.d.ts.map +1 -0
- package/dist/src/defaults.js +457 -0
- package/dist/src/defaults.js.map +1 -0
- package/dist/src/first-run.d.ts +35 -0
- package/dist/src/first-run.d.ts.map +1 -0
- package/dist/src/first-run.js +94 -0
- package/dist/src/first-run.js.map +1 -0
- package/dist/src/hello.d.ts +2 -0
- package/dist/src/hello.d.ts.map +1 -0
- package/dist/src/hello.js +4 -0
- package/dist/src/hello.js.map +1 -0
- package/dist/src/integrations/agent-registry.d.ts +160 -0
- package/dist/src/integrations/agent-registry.d.ts.map +1 -0
- package/dist/src/integrations/agent-registry.js +446 -0
- package/dist/src/integrations/agent-registry.js.map +1 -0
- package/dist/src/integrations/auto-compaction.d.ts +177 -0
- package/dist/src/integrations/auto-compaction.d.ts.map +1 -0
- package/dist/src/integrations/auto-compaction.js +428 -0
- package/dist/src/integrations/auto-compaction.js.map +1 -0
- package/dist/src/integrations/cancellation.d.ts +162 -0
- package/dist/src/integrations/cancellation.d.ts.map +1 -0
- package/dist/src/integrations/cancellation.js +339 -0
- package/dist/src/integrations/cancellation.js.map +1 -0
- package/dist/src/integrations/codebase-context.d.ts +319 -0
- package/dist/src/integrations/codebase-context.d.ts.map +1 -0
- package/dist/src/integrations/codebase-context.js +816 -0
- package/dist/src/integrations/codebase-context.js.map +1 -0
- package/dist/src/integrations/compaction.d.ts +192 -0
- package/dist/src/integrations/compaction.d.ts.map +1 -0
- package/dist/src/integrations/compaction.js +376 -0
- package/dist/src/integrations/compaction.js.map +1 -0
- package/dist/src/integrations/context-engineering.d.ts +246 -0
- package/dist/src/integrations/context-engineering.d.ts.map +1 -0
- package/dist/src/integrations/context-engineering.js +394 -0
- package/dist/src/integrations/context-engineering.js.map +1 -0
- package/dist/src/integrations/diff-utils.d.ts +105 -0
- package/dist/src/integrations/diff-utils.d.ts.map +1 -0
- package/dist/src/integrations/diff-utils.js +497 -0
- package/dist/src/integrations/diff-utils.js.map +1 -0
- package/dist/src/integrations/economics.d.ts +192 -0
- package/dist/src/integrations/economics.d.ts.map +1 -0
- package/dist/src/integrations/economics.js +431 -0
- package/dist/src/integrations/economics.js.map +1 -0
- package/dist/src/integrations/execution-policy.d.ts +189 -0
- package/dist/src/integrations/execution-policy.d.ts.map +1 -0
- package/dist/src/integrations/execution-policy.js +352 -0
- package/dist/src/integrations/execution-policy.js.map +1 -0
- package/dist/src/integrations/file-change-tracker.d.ts +161 -0
- package/dist/src/integrations/file-change-tracker.d.ts.map +1 -0
- package/dist/src/integrations/file-change-tracker.js +520 -0
- package/dist/src/integrations/file-change-tracker.js.map +1 -0
- package/dist/src/integrations/hierarchical-config.d.ts +212 -0
- package/dist/src/integrations/hierarchical-config.d.ts.map +1 -0
- package/dist/src/integrations/hierarchical-config.js +484 -0
- package/dist/src/integrations/hierarchical-config.js.map +1 -0
- package/dist/src/integrations/hooks.d.ts +114 -0
- package/dist/src/integrations/hooks.d.ts.map +1 -0
- package/dist/src/integrations/hooks.js +326 -0
- package/dist/src/integrations/hooks.js.map +1 -0
- package/dist/src/integrations/ignore.d.ts +143 -0
- package/dist/src/integrations/ignore.d.ts.map +1 -0
- package/dist/src/integrations/ignore.js +417 -0
- package/dist/src/integrations/ignore.js.map +1 -0
- package/dist/src/integrations/image-renderer.d.ts +119 -0
- package/dist/src/integrations/image-renderer.d.ts.map +1 -0
- package/dist/src/integrations/image-renderer.js +306 -0
- package/dist/src/integrations/image-renderer.js.map +1 -0
- package/dist/src/integrations/index.d.ts +42 -0
- package/dist/src/integrations/index.d.ts.map +1 -0
- package/dist/src/integrations/index.js +73 -0
- package/dist/src/integrations/index.js.map +1 -0
- package/dist/src/integrations/lsp.d.ts +196 -0
- package/dist/src/integrations/lsp.d.ts.map +1 -0
- package/dist/src/integrations/lsp.js +582 -0
- package/dist/src/integrations/lsp.js.map +1 -0
- package/dist/src/integrations/mcp-client.d.ts +270 -0
- package/dist/src/integrations/mcp-client.d.ts.map +1 -0
- package/dist/src/integrations/mcp-client.js +698 -0
- package/dist/src/integrations/mcp-client.js.map +1 -0
- package/dist/src/integrations/mcp-tool-search.d.ts +77 -0
- package/dist/src/integrations/mcp-tool-search.d.ts.map +1 -0
- package/dist/src/integrations/mcp-tool-search.js +220 -0
- package/dist/src/integrations/mcp-tool-search.js.map +1 -0
- package/dist/src/integrations/memory.d.ts +108 -0
- package/dist/src/integrations/memory.d.ts.map +1 -0
- package/dist/src/integrations/memory.js +288 -0
- package/dist/src/integrations/memory.js.map +1 -0
- package/dist/src/integrations/multi-agent.d.ts +150 -0
- package/dist/src/integrations/multi-agent.d.ts.map +1 -0
- package/dist/src/integrations/multi-agent.js +306 -0
- package/dist/src/integrations/multi-agent.js.map +1 -0
- package/dist/src/integrations/observability.d.ts +162 -0
- package/dist/src/integrations/observability.d.ts.map +1 -0
- package/dist/src/integrations/observability.js +406 -0
- package/dist/src/integrations/observability.js.map +1 -0
- package/dist/src/integrations/openrouter-pricing.d.ts +42 -0
- package/dist/src/integrations/openrouter-pricing.d.ts.map +1 -0
- package/dist/src/integrations/openrouter-pricing.js +124 -0
- package/dist/src/integrations/openrouter-pricing.js.map +1 -0
- package/dist/src/integrations/pending-plan.d.ts +171 -0
- package/dist/src/integrations/pending-plan.d.ts.map +1 -0
- package/dist/src/integrations/pending-plan.js +244 -0
- package/dist/src/integrations/pending-plan.js.map +1 -0
- package/dist/src/integrations/persistence.d.ts +48 -0
- package/dist/src/integrations/persistence.d.ts.map +1 -0
- package/dist/src/integrations/persistence.js +196 -0
- package/dist/src/integrations/persistence.js.map +1 -0
- package/dist/src/integrations/planning.d.ts +96 -0
- package/dist/src/integrations/planning.d.ts.map +1 -0
- package/dist/src/integrations/planning.js +338 -0
- package/dist/src/integrations/planning.js.map +1 -0
- package/dist/src/integrations/pty-shell.d.ts +169 -0
- package/dist/src/integrations/pty-shell.d.ts.map +1 -0
- package/dist/src/integrations/pty-shell.js +367 -0
- package/dist/src/integrations/pty-shell.js.map +1 -0
- package/dist/src/integrations/react.d.ts +139 -0
- package/dist/src/integrations/react.d.ts.map +1 -0
- package/dist/src/integrations/react.js +273 -0
- package/dist/src/integrations/react.js.map +1 -0
- package/dist/src/integrations/resources.d.ts +177 -0
- package/dist/src/integrations/resources.d.ts.map +1 -0
- package/dist/src/integrations/resources.js +311 -0
- package/dist/src/integrations/resources.js.map +1 -0
- package/dist/src/integrations/result-synthesizer.d.ts +389 -0
- package/dist/src/integrations/result-synthesizer.d.ts.map +1 -0
- package/dist/src/integrations/result-synthesizer.js +951 -0
- package/dist/src/integrations/result-synthesizer.js.map +1 -0
- package/dist/src/integrations/routing.d.ts +117 -0
- package/dist/src/integrations/routing.d.ts.map +1 -0
- package/dist/src/integrations/routing.js +347 -0
- package/dist/src/integrations/routing.js.map +1 -0
- package/dist/src/integrations/rules.d.ts +131 -0
- package/dist/src/integrations/rules.d.ts.map +1 -0
- package/dist/src/integrations/rules.js +284 -0
- package/dist/src/integrations/rules.js.map +1 -0
- package/dist/src/integrations/safety.d.ts +142 -0
- package/dist/src/integrations/safety.d.ts.map +1 -0
- package/dist/src/integrations/safety.js +342 -0
- package/dist/src/integrations/safety.js.map +1 -0
- package/dist/src/integrations/sandbox/basic.d.ts +74 -0
- package/dist/src/integrations/sandbox/basic.d.ts.map +1 -0
- package/dist/src/integrations/sandbox/basic.js +310 -0
- package/dist/src/integrations/sandbox/basic.js.map +1 -0
- package/dist/src/integrations/sandbox/docker.d.ts +94 -0
- package/dist/src/integrations/sandbox/docker.d.ts.map +1 -0
- package/dist/src/integrations/sandbox/docker.js +293 -0
- package/dist/src/integrations/sandbox/docker.js.map +1 -0
- package/dist/src/integrations/sandbox/index.d.ts +182 -0
- package/dist/src/integrations/sandbox/index.d.ts.map +1 -0
- package/dist/src/integrations/sandbox/index.js +382 -0
- package/dist/src/integrations/sandbox/index.js.map +1 -0
- package/dist/src/integrations/sandbox/landlock.d.ts +59 -0
- package/dist/src/integrations/sandbox/landlock.d.ts.map +1 -0
- package/dist/src/integrations/sandbox/landlock.js +326 -0
- package/dist/src/integrations/sandbox/landlock.js.map +1 -0
- package/dist/src/integrations/sandbox/seatbelt.d.ts +68 -0
- package/dist/src/integrations/sandbox/seatbelt.d.ts.map +1 -0
- package/dist/src/integrations/sandbox/seatbelt.js +298 -0
- package/dist/src/integrations/sandbox/seatbelt.js.map +1 -0
- package/dist/src/integrations/semantic-cache.d.ts +178 -0
- package/dist/src/integrations/semantic-cache.d.ts.map +1 -0
- package/dist/src/integrations/semantic-cache.js +372 -0
- package/dist/src/integrations/semantic-cache.js.map +1 -0
- package/dist/src/integrations/session-store.d.ts +183 -0
- package/dist/src/integrations/session-store.d.ts.map +1 -0
- package/dist/src/integrations/session-store.js +345 -0
- package/dist/src/integrations/session-store.js.map +1 -0
- package/dist/src/integrations/shared-blackboard.d.ts +403 -0
- package/dist/src/integrations/shared-blackboard.d.ts.map +1 -0
- package/dist/src/integrations/shared-blackboard.js +710 -0
- package/dist/src/integrations/shared-blackboard.js.map +1 -0
- package/dist/src/integrations/skills.d.ts +171 -0
- package/dist/src/integrations/skills.d.ts.map +1 -0
- package/dist/src/integrations/skills.js +403 -0
- package/dist/src/integrations/skills.js.map +1 -0
- package/dist/src/integrations/smart-decomposer.d.ts +322 -0
- package/dist/src/integrations/smart-decomposer.d.ts.map +1 -0
- package/dist/src/integrations/smart-decomposer.js +856 -0
- package/dist/src/integrations/smart-decomposer.js.map +1 -0
- package/dist/src/integrations/sourcegraph.d.ts +169 -0
- package/dist/src/integrations/sourcegraph.d.ts.map +1 -0
- package/dist/src/integrations/sourcegraph.js +379 -0
- package/dist/src/integrations/sourcegraph.js.map +1 -0
- package/dist/src/integrations/sqlite-store.d.ts +518 -0
- package/dist/src/integrations/sqlite-store.d.ts.map +1 -0
- package/dist/src/integrations/sqlite-store.js +1423 -0
- package/dist/src/integrations/sqlite-store.js.map +1 -0
- package/dist/src/integrations/streaming.d.ts +102 -0
- package/dist/src/integrations/streaming.d.ts.map +1 -0
- package/dist/src/integrations/streaming.js +362 -0
- package/dist/src/integrations/streaming.js.map +1 -0
- package/dist/src/integrations/thread-manager.d.ts +199 -0
- package/dist/src/integrations/thread-manager.d.ts.map +1 -0
- package/dist/src/integrations/thread-manager.js +357 -0
- package/dist/src/integrations/thread-manager.js.map +1 -0
- package/dist/src/main.d.ts +26 -0
- package/dist/src/main.d.ts.map +1 -0
- package/dist/src/main.js +170 -0
- package/dist/src/main.js.map +1 -0
- package/dist/src/modes/index.d.ts +10 -0
- package/dist/src/modes/index.d.ts.map +1 -0
- package/dist/src/modes/index.js +10 -0
- package/dist/src/modes/index.js.map +1 -0
- package/dist/src/modes/repl.d.ts +19 -0
- package/dist/src/modes/repl.d.ts.map +1 -0
- package/dist/src/modes/repl.js +393 -0
- package/dist/src/modes/repl.js.map +1 -0
- package/dist/src/modes/tui.d.ts +29 -0
- package/dist/src/modes/tui.d.ts.map +1 -0
- package/dist/src/modes/tui.js +272 -0
- package/dist/src/modes/tui.js.map +1 -0
- package/dist/src/modes.d.ts +179 -0
- package/dist/src/modes.d.ts.map +1 -0
- package/dist/src/modes.js +385 -0
- package/dist/src/modes.js.map +1 -0
- package/dist/src/observability/tracer.d.ts +111 -0
- package/dist/src/observability/tracer.d.ts.map +1 -0
- package/dist/src/observability/tracer.js +300 -0
- package/dist/src/observability/tracer.js.map +1 -0
- package/dist/src/observability/types.d.ts +271 -0
- package/dist/src/observability/types.d.ts.map +1 -0
- package/dist/src/observability/types.js +24 -0
- package/dist/src/observability/types.js.map +1 -0
- package/dist/src/paths.d.ts +101 -0
- package/dist/src/paths.d.ts.map +1 -0
- package/dist/src/paths.js +148 -0
- package/dist/src/paths.js.map +1 -0
- package/dist/src/persistence/index.d.ts +38 -0
- package/dist/src/persistence/index.d.ts.map +1 -0
- package/dist/src/persistence/index.js +48 -0
- package/dist/src/persistence/index.js.map +1 -0
- package/dist/src/persistence/migrator.d.ts +135 -0
- package/dist/src/persistence/migrator.d.ts.map +1 -0
- package/dist/src/persistence/migrator.js +303 -0
- package/dist/src/persistence/migrator.js.map +1 -0
- package/dist/src/persistence/schema.d.ts +101 -0
- package/dist/src/persistence/schema.d.ts.map +1 -0
- package/dist/src/persistence/schema.js +395 -0
- package/dist/src/persistence/schema.js.map +1 -0
- package/dist/src/providers/adapters/anthropic.d.ts +20 -0
- package/dist/src/providers/adapters/anthropic.d.ts.map +1 -0
- package/dist/src/providers/adapters/anthropic.js +124 -0
- package/dist/src/providers/adapters/anthropic.js.map +1 -0
- package/dist/src/providers/adapters/mock.d.ts +25 -0
- package/dist/src/providers/adapters/mock.d.ts.map +1 -0
- package/dist/src/providers/adapters/mock.js +133 -0
- package/dist/src/providers/adapters/mock.js.map +1 -0
- package/dist/src/providers/adapters/openai.d.ts +21 -0
- package/dist/src/providers/adapters/openai.d.ts.map +1 -0
- package/dist/src/providers/adapters/openai.js +126 -0
- package/dist/src/providers/adapters/openai.js.map +1 -0
- package/dist/src/providers/adapters/openrouter.d.ts +49 -0
- package/dist/src/providers/adapters/openrouter.d.ts.map +1 -0
- package/dist/src/providers/adapters/openrouter.js +363 -0
- package/dist/src/providers/adapters/openrouter.js.map +1 -0
- package/dist/src/providers/provider.d.ts +54 -0
- package/dist/src/providers/provider.d.ts.map +1 -0
- package/dist/src/providers/provider.js +111 -0
- package/dist/src/providers/provider.js.map +1 -0
- package/dist/src/providers/resilient-fetch.d.ts +99 -0
- package/dist/src/providers/resilient-fetch.d.ts.map +1 -0
- package/dist/src/providers/resilient-fetch.js +208 -0
- package/dist/src/providers/resilient-fetch.js.map +1 -0
- package/dist/src/providers/types.d.ts +227 -0
- package/dist/src/providers/types.d.ts.map +1 -0
- package/dist/src/providers/types.js +24 -0
- package/dist/src/providers/types.js.map +1 -0
- package/dist/src/session-picker.d.ts +28 -0
- package/dist/src/session-picker.d.ts.map +1 -0
- package/dist/src/session-picker.js +256 -0
- package/dist/src/session-picker.js.map +1 -0
- package/dist/src/test-sqlite.d.ts +2 -0
- package/dist/src/test-sqlite.d.ts.map +1 -0
- package/dist/src/test-sqlite.js +114 -0
- package/dist/src/test-sqlite.js.map +1 -0
- package/dist/src/tools/agent.d.ts +44 -0
- package/dist/src/tools/agent.d.ts.map +1 -0
- package/dist/src/tools/agent.js +110 -0
- package/dist/src/tools/agent.js.map +1 -0
- package/dist/src/tools/bash.d.ts +52 -0
- package/dist/src/tools/bash.d.ts.map +1 -0
- package/dist/src/tools/bash.js +141 -0
- package/dist/src/tools/bash.js.map +1 -0
- package/dist/src/tools/file.d.ts +47 -0
- package/dist/src/tools/file.d.ts.map +1 -0
- package/dist/src/tools/file.js +263 -0
- package/dist/src/tools/file.js.map +1 -0
- package/dist/src/tools/permission.d.ts +43 -0
- package/dist/src/tools/permission.d.ts.map +1 -0
- package/dist/src/tools/permission.js +216 -0
- package/dist/src/tools/permission.js.map +1 -0
- package/dist/src/tools/registry.d.ts +63 -0
- package/dist/src/tools/registry.d.ts.map +1 -0
- package/dist/src/tools/registry.js +250 -0
- package/dist/src/tools/registry.js.map +1 -0
- package/dist/src/tools/standard.d.ts +57 -0
- package/dist/src/tools/standard.d.ts.map +1 -0
- package/dist/src/tools/standard.js +113 -0
- package/dist/src/tools/standard.js.map +1 -0
- package/dist/src/tools/types.d.ts +146 -0
- package/dist/src/tools/types.d.ts.map +1 -0
- package/dist/src/tools/types.js +28 -0
- package/dist/src/tools/types.js.map +1 -0
- package/dist/src/tools/undo.d.ts +71 -0
- package/dist/src/tools/undo.d.ts.map +1 -0
- package/dist/src/tools/undo.js +123 -0
- package/dist/src/tools/undo.js.map +1 -0
- package/dist/src/tracing/cache-boundary-tracker.d.ts +189 -0
- package/dist/src/tracing/cache-boundary-tracker.d.ts.map +1 -0
- package/dist/src/tracing/cache-boundary-tracker.js +411 -0
- package/dist/src/tracing/cache-boundary-tracker.js.map +1 -0
- package/dist/src/tracing/trace-collector.d.ts +274 -0
- package/dist/src/tracing/trace-collector.d.ts.map +1 -0
- package/dist/src/tracing/trace-collector.js +727 -0
- package/dist/src/tracing/trace-collector.js.map +1 -0
- package/dist/src/tracing/types.d.ts +657 -0
- package/dist/src/tracing/types.d.ts.map +1 -0
- package/dist/src/tracing/types.js +39 -0
- package/dist/src/tracing/types.js.map +1 -0
- package/dist/src/tricks/failure-evidence.d.ts +268 -0
- package/dist/src/tricks/failure-evidence.d.ts.map +1 -0
- package/dist/src/tricks/failure-evidence.js +544 -0
- package/dist/src/tricks/failure-evidence.js.map +1 -0
- package/dist/src/tricks/json-utils.d.ts +77 -0
- package/dist/src/tricks/json-utils.d.ts.map +1 -0
- package/dist/src/tricks/json-utils.js +247 -0
- package/dist/src/tricks/json-utils.js.map +1 -0
- package/dist/src/tricks/kv-cache-context.d.ts +227 -0
- package/dist/src/tricks/kv-cache-context.d.ts.map +1 -0
- package/dist/src/tricks/kv-cache-context.js +377 -0
- package/dist/src/tricks/kv-cache-context.js.map +1 -0
- package/dist/src/tricks/recitation.d.ts +208 -0
- package/dist/src/tricks/recitation.d.ts.map +1 -0
- package/dist/src/tricks/recitation.js +374 -0
- package/dist/src/tricks/recitation.js.map +1 -0
- package/dist/src/tricks/reversible-compaction.d.ts +251 -0
- package/dist/src/tricks/reversible-compaction.d.ts.map +1 -0
- package/dist/src/tricks/reversible-compaction.js +555 -0
- package/dist/src/tricks/reversible-compaction.js.map +1 -0
- package/dist/src/tricks/serialization-diversity.d.ts +197 -0
- package/dist/src/tricks/serialization-diversity.d.ts.map +1 -0
- package/dist/src/tricks/serialization-diversity.js +460 -0
- package/dist/src/tricks/serialization-diversity.js.map +1 -0
- package/dist/src/tui/app.d.ts +42 -0
- package/dist/src/tui/app.d.ts.map +1 -0
- package/dist/src/tui/app.js +1076 -0
- package/dist/src/tui/app.js.map +1 -0
- package/dist/src/tui/components/ApprovalDialog.d.ts +28 -0
- package/dist/src/tui/components/ApprovalDialog.d.ts.map +1 -0
- package/dist/src/tui/components/ApprovalDialog.js +59 -0
- package/dist/src/tui/components/ApprovalDialog.js.map +1 -0
- package/dist/src/tui/components/InputArea.d.ts +35 -0
- package/dist/src/tui/components/InputArea.d.ts.map +1 -0
- package/dist/src/tui/components/InputArea.js +144 -0
- package/dist/src/tui/components/InputArea.js.map +1 -0
- package/dist/src/tui/components/MessageItem.d.ts +28 -0
- package/dist/src/tui/components/MessageItem.d.ts.map +1 -0
- package/dist/src/tui/components/MessageItem.js +27 -0
- package/dist/src/tui/components/MessageItem.js.map +1 -0
- package/dist/src/tui/components/ScrollableBox.d.ts +41 -0
- package/dist/src/tui/components/ScrollableBox.d.ts.map +1 -0
- package/dist/src/tui/components/ScrollableBox.js +101 -0
- package/dist/src/tui/components/ScrollableBox.js.map +1 -0
- package/dist/src/tui/components/ToolCallItem.d.ts +33 -0
- package/dist/src/tui/components/ToolCallItem.d.ts.map +1 -0
- package/dist/src/tui/components/ToolCallItem.js +91 -0
- package/dist/src/tui/components/ToolCallItem.js.map +1 -0
- package/dist/src/tui/components/index.d.ts +13 -0
- package/dist/src/tui/components/index.d.ts.map +1 -0
- package/dist/src/tui/components/index.js +15 -0
- package/dist/src/tui/components/index.js.map +1 -0
- package/dist/src/tui/event-display.d.ts +19 -0
- package/dist/src/tui/event-display.d.ts.map +1 -0
- package/dist/src/tui/event-display.js +178 -0
- package/dist/src/tui/event-display.js.map +1 -0
- package/dist/src/tui/index.d.ts +105 -0
- package/dist/src/tui/index.d.ts.map +1 -0
- package/dist/src/tui/index.js +214 -0
- package/dist/src/tui/index.js.map +1 -0
- package/dist/src/tui/input/CommandPalette.d.ts +55 -0
- package/dist/src/tui/input/CommandPalette.d.ts.map +1 -0
- package/dist/src/tui/input/CommandPalette.js +135 -0
- package/dist/src/tui/input/CommandPalette.js.map +1 -0
- package/dist/src/tui/input/index.d.ts +7 -0
- package/dist/src/tui/input/index.d.ts.map +1 -0
- package/dist/src/tui/input/index.js +7 -0
- package/dist/src/tui/input/index.js.map +1 -0
- package/dist/src/tui/theme/index.d.ts +45 -0
- package/dist/src/tui/theme/index.d.ts.map +1 -0
- package/dist/src/tui/theme/index.js +215 -0
- package/dist/src/tui/theme/index.js.map +1 -0
- package/dist/src/tui/types.d.ts +214 -0
- package/dist/src/tui/types.d.ts.map +1 -0
- package/dist/src/tui/types.js +27 -0
- package/dist/src/tui/types.js.map +1 -0
- package/dist/src/types.d.ts +905 -0
- package/dist/src/types.d.ts.map +1 -0
- package/dist/src/types.js +9 -0
- package/dist/src/types.js.map +1 -0
- package/package.json +89 -0
|
@@ -0,0 +1,951 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Result Synthesizer Integration
|
|
3
|
+
*
|
|
4
|
+
* Structured merging of results from multiple agents.
|
|
5
|
+
* Goes beyond simple consensus to intelligently combine outputs.
|
|
6
|
+
*
|
|
7
|
+
* Key features:
|
|
8
|
+
* - Code merging: Intelligent merge of code changes from multiple agents
|
|
9
|
+
* - Finding synthesis: Combine research findings, deduplicate insights
|
|
10
|
+
* - Conflict detection: Identify contradictions between results
|
|
11
|
+
* - Conflict resolution: Strategies for resolving disagreements
|
|
12
|
+
* - Confidence weighting: Weight results by agent confidence and authority
|
|
13
|
+
*/
|
|
14
|
+
// =============================================================================
|
|
15
|
+
// CONSTANTS
|
|
16
|
+
// =============================================================================
|
|
17
|
+
const DEFAULT_CONFIG = {
|
|
18
|
+
defaultMethod: 'deduplicate',
|
|
19
|
+
conflictResolution: 'choose_highest_confidence',
|
|
20
|
+
deduplicationThreshold: 0.8,
|
|
21
|
+
useLLM: false,
|
|
22
|
+
llmSynthesizer: undefined,
|
|
23
|
+
preferHigherConfidence: true,
|
|
24
|
+
preferHigherAuthority: true,
|
|
25
|
+
};
|
|
26
|
+
// =============================================================================
|
|
27
|
+
// RESULT SYNTHESIZER
|
|
28
|
+
// =============================================================================
|
|
29
|
+
/**
|
|
30
|
+
* Synthesizes results from multiple agents into a coherent output.
|
|
31
|
+
*
|
|
32
|
+
* @example
|
|
33
|
+
* ```typescript
|
|
34
|
+
* const synthesizer = createResultSynthesizer();
|
|
35
|
+
*
|
|
36
|
+
* const result = await synthesizer.synthesize([
|
|
37
|
+
* {
|
|
38
|
+
* agentId: 'agent-a',
|
|
39
|
+
* content: 'Found auth logic in src/auth.ts',
|
|
40
|
+
* type: 'research',
|
|
41
|
+
* confidence: 0.9,
|
|
42
|
+
* findings: ['JWT tokens used', 'Session stored in Redis'],
|
|
43
|
+
* },
|
|
44
|
+
* {
|
|
45
|
+
* agentId: 'agent-b',
|
|
46
|
+
* content: 'Auth implemented in src/auth.ts using JWT',
|
|
47
|
+
* type: 'research',
|
|
48
|
+
* confidence: 0.85,
|
|
49
|
+
* findings: ['JWT tokens used', 'Password hashing with bcrypt'],
|
|
50
|
+
* },
|
|
51
|
+
* ]);
|
|
52
|
+
*
|
|
53
|
+
* console.log(result.findings); // Deduplicated findings
|
|
54
|
+
* console.log(result.conflicts); // Any disagreements
|
|
55
|
+
* ```
|
|
56
|
+
*/
|
|
57
|
+
export class ResultSynthesizer {
|
|
58
|
+
config;
|
|
59
|
+
listeners = [];
|
|
60
|
+
conflictCounter = 0;
|
|
61
|
+
constructor(config = {}) {
|
|
62
|
+
this.config = {
|
|
63
|
+
...DEFAULT_CONFIG,
|
|
64
|
+
...config,
|
|
65
|
+
llmSynthesizer: config.llmSynthesizer ?? DEFAULT_CONFIG.llmSynthesizer,
|
|
66
|
+
};
|
|
67
|
+
}
|
|
68
|
+
// ===========================================================================
|
|
69
|
+
// SYNTHESIS
|
|
70
|
+
// ===========================================================================
|
|
71
|
+
/**
|
|
72
|
+
* Synthesize multiple agent outputs into a coherent result.
|
|
73
|
+
*/
|
|
74
|
+
async synthesize(outputs) {
|
|
75
|
+
this.emit({ type: 'synthesis.started', outputCount: outputs.length });
|
|
76
|
+
if (outputs.length === 0) {
|
|
77
|
+
return this.createEmptyResult();
|
|
78
|
+
}
|
|
79
|
+
if (outputs.length === 1) {
|
|
80
|
+
return this.createSingleResult(outputs[0]);
|
|
81
|
+
}
|
|
82
|
+
// Detect conflicts
|
|
83
|
+
const conflicts = this.detectConflicts(outputs);
|
|
84
|
+
for (const conflict of conflicts) {
|
|
85
|
+
this.emit({ type: 'conflict.detected', conflict });
|
|
86
|
+
}
|
|
87
|
+
// Determine synthesis method based on output types
|
|
88
|
+
const method = this.determineMethod(outputs);
|
|
89
|
+
let result;
|
|
90
|
+
switch (method) {
|
|
91
|
+
case 'merge_structured':
|
|
92
|
+
result = await this.mergeStructured(outputs, conflicts);
|
|
93
|
+
break;
|
|
94
|
+
case 'synthesize_llm':
|
|
95
|
+
result = await this.synthesizeLLM(outputs, conflicts);
|
|
96
|
+
break;
|
|
97
|
+
case 'majority_vote':
|
|
98
|
+
result = this.majorityVote(outputs, conflicts);
|
|
99
|
+
break;
|
|
100
|
+
case 'deduplicate':
|
|
101
|
+
result = this.deduplicateMerge(outputs, conflicts);
|
|
102
|
+
break;
|
|
103
|
+
default:
|
|
104
|
+
result = this.concatenateMerge(outputs, conflicts);
|
|
105
|
+
}
|
|
106
|
+
this.emit({ type: 'synthesis.completed', result });
|
|
107
|
+
return result;
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Synthesize code changes from multiple agents.
|
|
111
|
+
*/
|
|
112
|
+
async synthesizeCode(outputs) {
|
|
113
|
+
const codeOutputs = outputs.filter((o) => o.type === 'code' || o.filesModified);
|
|
114
|
+
if (codeOutputs.length === 0) {
|
|
115
|
+
return this.createEmptyResult();
|
|
116
|
+
}
|
|
117
|
+
// Collect all file changes
|
|
118
|
+
const changesByFile = new Map();
|
|
119
|
+
for (const output of codeOutputs) {
|
|
120
|
+
for (const change of output.filesModified ?? []) {
|
|
121
|
+
if (!changesByFile.has(change.path)) {
|
|
122
|
+
changesByFile.set(change.path, []);
|
|
123
|
+
}
|
|
124
|
+
changesByFile.get(change.path).push(change);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
// Merge changes per file
|
|
128
|
+
const mergedChanges = [];
|
|
129
|
+
const conflicts = [];
|
|
130
|
+
for (const [filePath, changes] of changesByFile) {
|
|
131
|
+
if (changes.length === 1) {
|
|
132
|
+
mergedChanges.push(changes[0]);
|
|
133
|
+
}
|
|
134
|
+
else {
|
|
135
|
+
const mergeResult = this.mergeFileChanges(filePath, changes, codeOutputs);
|
|
136
|
+
if (mergeResult.merged) {
|
|
137
|
+
mergedChanges.push(mergeResult.merged);
|
|
138
|
+
}
|
|
139
|
+
conflicts.push(...mergeResult.conflicts);
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
// Build output content
|
|
143
|
+
const outputParts = [];
|
|
144
|
+
for (const change of mergedChanges) {
|
|
145
|
+
outputParts.push(`// File: ${change.path}`);
|
|
146
|
+
outputParts.push(change.newContent);
|
|
147
|
+
outputParts.push('');
|
|
148
|
+
}
|
|
149
|
+
const result = {
|
|
150
|
+
output: outputParts.join('\n'),
|
|
151
|
+
type: 'code',
|
|
152
|
+
confidence: this.calculateCombinedConfidence(codeOutputs),
|
|
153
|
+
fileChanges: mergedChanges,
|
|
154
|
+
findings: [],
|
|
155
|
+
conflicts,
|
|
156
|
+
stats: this.calculateStats(codeOutputs, outputParts.join('\n'), conflicts),
|
|
157
|
+
method: 'merge_structured',
|
|
158
|
+
};
|
|
159
|
+
return result;
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* Synthesize research findings from multiple agents.
|
|
163
|
+
*/
|
|
164
|
+
synthesizeFindings(outputs) {
|
|
165
|
+
const allFindings = [];
|
|
166
|
+
for (const output of outputs) {
|
|
167
|
+
for (const finding of output.findings ?? []) {
|
|
168
|
+
allFindings.push({
|
|
169
|
+
finding,
|
|
170
|
+
agentId: output.agentId,
|
|
171
|
+
confidence: output.confidence,
|
|
172
|
+
});
|
|
173
|
+
}
|
|
174
|
+
// Also extract findings from content
|
|
175
|
+
const extracted = this.extractFindingsFromContent(output.content);
|
|
176
|
+
for (const finding of extracted) {
|
|
177
|
+
allFindings.push({
|
|
178
|
+
finding,
|
|
179
|
+
agentId: output.agentId,
|
|
180
|
+
confidence: output.confidence * 0.8, // Lower confidence for extracted
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
// Deduplicate findings
|
|
185
|
+
const deduplicated = this.deduplicateFindings(allFindings);
|
|
186
|
+
this.emit({
|
|
187
|
+
type: 'deduplication.performed',
|
|
188
|
+
original: allFindings.length,
|
|
189
|
+
deduplicated: deduplicated.length,
|
|
190
|
+
});
|
|
191
|
+
// Build output
|
|
192
|
+
const outputParts = [
|
|
193
|
+
'## Synthesized Findings',
|
|
194
|
+
'',
|
|
195
|
+
...deduplicated.map((f, i) => `${i + 1}. ${f.finding} (confidence: ${(f.confidence * 100).toFixed(0)}%)`),
|
|
196
|
+
];
|
|
197
|
+
// Detect contradictions
|
|
198
|
+
const conflicts = this.detectFindingContradictions(deduplicated);
|
|
199
|
+
return {
|
|
200
|
+
output: outputParts.join('\n'),
|
|
201
|
+
type: 'research',
|
|
202
|
+
confidence: this.calculateCombinedConfidence(outputs),
|
|
203
|
+
fileChanges: [],
|
|
204
|
+
findings: deduplicated.map((f) => f.finding),
|
|
205
|
+
conflicts,
|
|
206
|
+
stats: this.calculateStats(outputs, outputParts.join('\n'), conflicts),
|
|
207
|
+
method: 'deduplicate',
|
|
208
|
+
};
|
|
209
|
+
}
|
|
210
|
+
// ===========================================================================
|
|
211
|
+
// CONFLICT DETECTION
|
|
212
|
+
// ===========================================================================
|
|
213
|
+
/**
|
|
214
|
+
* Detect conflicts between agent outputs.
|
|
215
|
+
*/
|
|
216
|
+
detectConflicts(outputs) {
|
|
217
|
+
const conflicts = [];
|
|
218
|
+
// Check for code overlaps
|
|
219
|
+
conflicts.push(...this.detectCodeOverlaps(outputs));
|
|
220
|
+
// Check for logic contradictions
|
|
221
|
+
conflicts.push(...this.detectLogicContradictions(outputs));
|
|
222
|
+
// Check for approach mismatches
|
|
223
|
+
conflicts.push(...this.detectApproachMismatches(outputs));
|
|
224
|
+
return conflicts;
|
|
225
|
+
}
|
|
226
|
+
/**
|
|
227
|
+
* Detect overlapping code changes.
|
|
228
|
+
*/
|
|
229
|
+
detectCodeOverlaps(outputs) {
|
|
230
|
+
const conflicts = [];
|
|
231
|
+
const changesByFile = new Map();
|
|
232
|
+
// Collect changes by file
|
|
233
|
+
for (const output of outputs) {
|
|
234
|
+
for (const change of output.filesModified ?? []) {
|
|
235
|
+
if (!changesByFile.has(change.path)) {
|
|
236
|
+
changesByFile.set(change.path, []);
|
|
237
|
+
}
|
|
238
|
+
changesByFile.get(change.path).push({ change, agentId: output.agentId });
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
// Check each file for overlaps
|
|
242
|
+
for (const [filePath, changes] of changesByFile) {
|
|
243
|
+
if (changes.length <= 1)
|
|
244
|
+
continue;
|
|
245
|
+
// Compare each pair
|
|
246
|
+
for (let i = 0; i < changes.length; i++) {
|
|
247
|
+
for (let j = i + 1; j < changes.length; j++) {
|
|
248
|
+
const overlap = this.checkCodeOverlap(changes[i].change, changes[j].change);
|
|
249
|
+
if (overlap) {
|
|
250
|
+
conflicts.push({
|
|
251
|
+
id: `conflict-${++this.conflictCounter}`,
|
|
252
|
+
type: 'code_overlap',
|
|
253
|
+
agentIds: [changes[i].agentId, changes[j].agentId],
|
|
254
|
+
description: `Overlapping changes to ${filePath}`,
|
|
255
|
+
conflictingContent: [changes[i].change.newContent, changes[j].change.newContent],
|
|
256
|
+
severity: 'high',
|
|
257
|
+
filePath,
|
|
258
|
+
lines: overlap.lines,
|
|
259
|
+
suggestedResolution: 'Review both changes and merge manually or choose one',
|
|
260
|
+
});
|
|
261
|
+
}
|
|
262
|
+
}
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
return conflicts;
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Check if two file changes overlap.
|
|
269
|
+
*/
|
|
270
|
+
checkCodeOverlap(a, b) {
|
|
271
|
+
// Simple line-based overlap detection
|
|
272
|
+
const aLines = new Set(a.newContent.split('\n').map((_, i) => i));
|
|
273
|
+
const bLines = new Set(b.newContent.split('\n').map((_, i) => i));
|
|
274
|
+
// If both modify similar regions, there's an overlap
|
|
275
|
+
if (a.type === 'modify' && b.type === 'modify') {
|
|
276
|
+
// Check for significantly different content
|
|
277
|
+
const similarity = this.calculateSimilarity(a.newContent, b.newContent);
|
|
278
|
+
if (similarity < 0.9) {
|
|
279
|
+
return { lines: Array.from(aLines).filter((l) => bLines.has(l)) };
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
return null;
|
|
283
|
+
}
|
|
284
|
+
/**
|
|
285
|
+
* Detect logic contradictions in findings.
|
|
286
|
+
*/
|
|
287
|
+
detectLogicContradictions(outputs) {
|
|
288
|
+
const conflicts = [];
|
|
289
|
+
// Check for contradicting findings
|
|
290
|
+
for (let i = 0; i < outputs.length; i++) {
|
|
291
|
+
for (let j = i + 1; j < outputs.length; j++) {
|
|
292
|
+
const contradictions = this.findContradictions(outputs[i].content, outputs[j].content);
|
|
293
|
+
for (const contradiction of contradictions) {
|
|
294
|
+
conflicts.push({
|
|
295
|
+
id: `conflict-${++this.conflictCounter}`,
|
|
296
|
+
type: 'logic_contradiction',
|
|
297
|
+
agentIds: [outputs[i].agentId, outputs[j].agentId],
|
|
298
|
+
description: contradiction.description,
|
|
299
|
+
conflictingContent: [contradiction.contentA, contradiction.contentB],
|
|
300
|
+
severity: 'medium',
|
|
301
|
+
suggestedResolution: 'Verify which conclusion is correct',
|
|
302
|
+
});
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
}
|
|
306
|
+
return conflicts;
|
|
307
|
+
}
|
|
308
|
+
/**
|
|
309
|
+
* Find contradicting statements between two texts.
|
|
310
|
+
*/
|
|
311
|
+
findContradictions(textA, textB) {
|
|
312
|
+
const contradictions = [];
|
|
313
|
+
// Simple heuristic: look for opposite assertions
|
|
314
|
+
const negationPairs = [
|
|
315
|
+
['is', 'is not'],
|
|
316
|
+
['does', 'does not'],
|
|
317
|
+
['can', 'cannot'],
|
|
318
|
+
['should', 'should not'],
|
|
319
|
+
['will', 'will not'],
|
|
320
|
+
['works', 'does not work'],
|
|
321
|
+
['exists', 'does not exist'],
|
|
322
|
+
['found', 'not found'],
|
|
323
|
+
];
|
|
324
|
+
const sentencesA = textA.split(/[.!?]+/).map((s) => s.trim().toLowerCase());
|
|
325
|
+
const sentencesB = textB.split(/[.!?]+/).map((s) => s.trim().toLowerCase());
|
|
326
|
+
for (const sentA of sentencesA) {
|
|
327
|
+
for (const sentB of sentencesB) {
|
|
328
|
+
for (const [pos, neg] of negationPairs) {
|
|
329
|
+
if ((sentA.includes(pos) && sentB.includes(neg)) ||
|
|
330
|
+
(sentA.includes(neg) && sentB.includes(pos))) {
|
|
331
|
+
// Check if they're about the same thing
|
|
332
|
+
const similarity = this.calculateSimilarity(sentA.replace(pos, '').replace(neg, ''), sentB.replace(pos, '').replace(neg, ''));
|
|
333
|
+
if (similarity > 0.5) {
|
|
334
|
+
contradictions.push({
|
|
335
|
+
description: `Contradiction about: "${sentA.slice(0, 50)}..."`,
|
|
336
|
+
contentA: sentA,
|
|
337
|
+
contentB: sentB,
|
|
338
|
+
});
|
|
339
|
+
}
|
|
340
|
+
}
|
|
341
|
+
}
|
|
342
|
+
}
|
|
343
|
+
}
|
|
344
|
+
return contradictions;
|
|
345
|
+
}
|
|
346
|
+
/**
|
|
347
|
+
* Detect different approaches to the same problem.
|
|
348
|
+
*/
|
|
349
|
+
detectApproachMismatches(outputs) {
|
|
350
|
+
const conflicts = [];
|
|
351
|
+
// Check for significantly different code structures
|
|
352
|
+
const codeOutputs = outputs.filter((o) => o.type === 'code');
|
|
353
|
+
if (codeOutputs.length <= 1)
|
|
354
|
+
return conflicts;
|
|
355
|
+
for (let i = 0; i < codeOutputs.length; i++) {
|
|
356
|
+
for (let j = i + 1; j < codeOutputs.length; j++) {
|
|
357
|
+
const similarity = this.calculateSimilarity(codeOutputs[i].content, codeOutputs[j].content);
|
|
358
|
+
// If outputs are similar in length but very different in content
|
|
359
|
+
const lengthRatio = Math.min(codeOutputs[i].content.length, codeOutputs[j].content.length) / Math.max(codeOutputs[i].content.length, codeOutputs[j].content.length);
|
|
360
|
+
if (lengthRatio > 0.5 && similarity < 0.3) {
|
|
361
|
+
conflicts.push({
|
|
362
|
+
id: `conflict-${++this.conflictCounter}`,
|
|
363
|
+
type: 'approach_mismatch',
|
|
364
|
+
agentIds: [codeOutputs[i].agentId, codeOutputs[j].agentId],
|
|
365
|
+
description: 'Different approaches to the same implementation',
|
|
366
|
+
conflictingContent: [
|
|
367
|
+
codeOutputs[i].content.slice(0, 200),
|
|
368
|
+
codeOutputs[j].content.slice(0, 200),
|
|
369
|
+
],
|
|
370
|
+
severity: 'medium',
|
|
371
|
+
suggestedResolution: 'Review both approaches and select the best one',
|
|
372
|
+
});
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
}
|
|
376
|
+
return conflicts;
|
|
377
|
+
}
|
|
378
|
+
// ===========================================================================
|
|
379
|
+
// MERGE STRATEGIES
|
|
380
|
+
// ===========================================================================
|
|
381
|
+
/**
|
|
382
|
+
* Merge with deduplication.
|
|
383
|
+
*/
|
|
384
|
+
deduplicateMerge(outputs, conflicts) {
|
|
385
|
+
// Combine all content
|
|
386
|
+
const allParts = [];
|
|
387
|
+
for (const output of outputs) {
|
|
388
|
+
// Split content into paragraphs/sections
|
|
389
|
+
const parts = output.content.split(/\n\n+/);
|
|
390
|
+
for (const part of parts) {
|
|
391
|
+
if (part.trim().length > 20) {
|
|
392
|
+
allParts.push({ content: part.trim(), confidence: output.confidence });
|
|
393
|
+
}
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
// Deduplicate
|
|
397
|
+
const deduplicated = [];
|
|
398
|
+
for (const part of allParts) {
|
|
399
|
+
const isDuplicate = deduplicated.some((d) => this.calculateSimilarity(d.content, part.content) > this.config.deduplicationThreshold);
|
|
400
|
+
if (!isDuplicate) {
|
|
401
|
+
deduplicated.push(part);
|
|
402
|
+
}
|
|
403
|
+
}
|
|
404
|
+
// Sort by confidence
|
|
405
|
+
deduplicated.sort((a, b) => b.confidence - a.confidence);
|
|
406
|
+
const output = deduplicated.map((d) => d.content).join('\n\n');
|
|
407
|
+
return {
|
|
408
|
+
output,
|
|
409
|
+
type: this.determineOutputType(outputs),
|
|
410
|
+
confidence: this.calculateCombinedConfidence(outputs),
|
|
411
|
+
fileChanges: this.mergeAllFileChanges(outputs),
|
|
412
|
+
findings: this.extractAllFindings(outputs),
|
|
413
|
+
conflicts,
|
|
414
|
+
stats: this.calculateStats(outputs, output, conflicts),
|
|
415
|
+
method: 'deduplicate',
|
|
416
|
+
};
|
|
417
|
+
}
|
|
418
|
+
/**
|
|
419
|
+
* Simple concatenation merge.
|
|
420
|
+
*/
|
|
421
|
+
concatenateMerge(outputs, conflicts) {
|
|
422
|
+
const parts = outputs.map((o) => `## From ${o.agentId}\n\n${o.content}`);
|
|
423
|
+
const output = parts.join('\n\n---\n\n');
|
|
424
|
+
return {
|
|
425
|
+
output,
|
|
426
|
+
type: 'mixed',
|
|
427
|
+
confidence: this.calculateCombinedConfidence(outputs),
|
|
428
|
+
fileChanges: this.mergeAllFileChanges(outputs),
|
|
429
|
+
findings: this.extractAllFindings(outputs),
|
|
430
|
+
conflicts,
|
|
431
|
+
stats: this.calculateStats(outputs, output, conflicts),
|
|
432
|
+
method: 'concatenate',
|
|
433
|
+
};
|
|
434
|
+
}
|
|
435
|
+
/**
|
|
436
|
+
* Structured merge for code.
|
|
437
|
+
*/
|
|
438
|
+
async mergeStructured(outputs, conflicts) {
|
|
439
|
+
// Resolve conflicts first
|
|
440
|
+
for (const conflict of conflicts) {
|
|
441
|
+
if (!conflict.resolution) {
|
|
442
|
+
conflict.resolution = this.resolveConflict(conflict, outputs);
|
|
443
|
+
this.emit({ type: 'conflict.resolved', conflict });
|
|
444
|
+
}
|
|
445
|
+
}
|
|
446
|
+
// Merge file changes
|
|
447
|
+
const mergedChanges = this.mergeAllFileChanges(outputs);
|
|
448
|
+
// Build output
|
|
449
|
+
const outputParts = [];
|
|
450
|
+
for (const change of mergedChanges) {
|
|
451
|
+
outputParts.push(`// File: ${change.path}`);
|
|
452
|
+
outputParts.push(change.newContent);
|
|
453
|
+
}
|
|
454
|
+
const output = outputParts.join('\n\n');
|
|
455
|
+
return {
|
|
456
|
+
output,
|
|
457
|
+
type: 'code',
|
|
458
|
+
confidence: this.calculateCombinedConfidence(outputs),
|
|
459
|
+
fileChanges: mergedChanges,
|
|
460
|
+
findings: [],
|
|
461
|
+
conflicts,
|
|
462
|
+
stats: this.calculateStats(outputs, output, conflicts),
|
|
463
|
+
method: 'merge_structured',
|
|
464
|
+
};
|
|
465
|
+
}
|
|
466
|
+
/**
|
|
467
|
+
* LLM-assisted synthesis.
|
|
468
|
+
*/
|
|
469
|
+
async synthesizeLLM(outputs, conflicts) {
|
|
470
|
+
if (!this.config.llmSynthesizer) {
|
|
471
|
+
return this.deduplicateMerge(outputs, conflicts);
|
|
472
|
+
}
|
|
473
|
+
try {
|
|
474
|
+
const llmResult = await this.config.llmSynthesizer(outputs, conflicts);
|
|
475
|
+
// Apply LLM conflict resolutions
|
|
476
|
+
for (const resolution of llmResult.resolutions) {
|
|
477
|
+
const conflict = conflicts.find((c) => c.id === resolution.conflictId);
|
|
478
|
+
if (conflict && !conflict.resolution) {
|
|
479
|
+
conflict.resolution = {
|
|
480
|
+
strategy: 'llm_decision',
|
|
481
|
+
mergedContent: resolution.resolution,
|
|
482
|
+
explanation: resolution.explanation,
|
|
483
|
+
resolvedAt: new Date(),
|
|
484
|
+
};
|
|
485
|
+
this.emit({ type: 'conflict.resolved', conflict });
|
|
486
|
+
}
|
|
487
|
+
}
|
|
488
|
+
return {
|
|
489
|
+
output: llmResult.content,
|
|
490
|
+
type: this.determineOutputType(outputs),
|
|
491
|
+
confidence: llmResult.confidence,
|
|
492
|
+
fileChanges: this.mergeAllFileChanges(outputs),
|
|
493
|
+
findings: llmResult.findings,
|
|
494
|
+
conflicts,
|
|
495
|
+
stats: this.calculateStats(outputs, llmResult.content, conflicts),
|
|
496
|
+
method: 'synthesize_llm',
|
|
497
|
+
};
|
|
498
|
+
}
|
|
499
|
+
catch {
|
|
500
|
+
// Fall back to deduplication
|
|
501
|
+
return this.deduplicateMerge(outputs, conflicts);
|
|
502
|
+
}
|
|
503
|
+
}
|
|
504
|
+
/**
|
|
505
|
+
* Majority vote synthesis.
|
|
506
|
+
*/
|
|
507
|
+
majorityVote(outputs, conflicts) {
|
|
508
|
+
// Group similar outputs
|
|
509
|
+
const groups = [];
|
|
510
|
+
for (const output of outputs) {
|
|
511
|
+
let addedToGroup = false;
|
|
512
|
+
for (const group of groups) {
|
|
513
|
+
if (this.calculateSimilarity(output.content, group.representative.content) > 0.7) {
|
|
514
|
+
group.outputs.push(output);
|
|
515
|
+
// Update representative if this one has higher confidence
|
|
516
|
+
if (output.confidence > group.representative.confidence) {
|
|
517
|
+
group.representative = output;
|
|
518
|
+
}
|
|
519
|
+
addedToGroup = true;
|
|
520
|
+
break;
|
|
521
|
+
}
|
|
522
|
+
}
|
|
523
|
+
if (!addedToGroup) {
|
|
524
|
+
groups.push({ outputs: [output], representative: output });
|
|
525
|
+
}
|
|
526
|
+
}
|
|
527
|
+
// Choose the largest group
|
|
528
|
+
groups.sort((a, b) => b.outputs.length - a.outputs.length);
|
|
529
|
+
const winner = groups[0].representative;
|
|
530
|
+
return {
|
|
531
|
+
output: winner.content,
|
|
532
|
+
type: winner.type,
|
|
533
|
+
confidence: winner.confidence * (groups[0].outputs.length / outputs.length),
|
|
534
|
+
fileChanges: winner.filesModified ?? [],
|
|
535
|
+
findings: winner.findings ?? [],
|
|
536
|
+
conflicts,
|
|
537
|
+
stats: this.calculateStats(outputs, winner.content, conflicts),
|
|
538
|
+
method: 'majority_vote',
|
|
539
|
+
};
|
|
540
|
+
}
|
|
541
|
+
// ===========================================================================
|
|
542
|
+
// CONFLICT RESOLUTION
|
|
543
|
+
// ===========================================================================
|
|
544
|
+
/**
|
|
545
|
+
* Resolve a conflict using the configured strategy.
|
|
546
|
+
*/
|
|
547
|
+
resolveConflict(conflict, outputs) {
|
|
548
|
+
switch (this.config.conflictResolution) {
|
|
549
|
+
case 'choose_highest_confidence':
|
|
550
|
+
return this.resolveByConfidence(conflict, outputs);
|
|
551
|
+
case 'choose_highest_authority':
|
|
552
|
+
return this.resolveByAuthority(conflict, outputs);
|
|
553
|
+
case 'merge_both':
|
|
554
|
+
return this.resolveMergeBoth(conflict);
|
|
555
|
+
case 'voting':
|
|
556
|
+
return this.resolveByVoting(conflict, outputs);
|
|
557
|
+
default:
|
|
558
|
+
return {
|
|
559
|
+
strategy: 'discard_all',
|
|
560
|
+
explanation: 'No resolution strategy available',
|
|
561
|
+
resolvedAt: new Date(),
|
|
562
|
+
};
|
|
563
|
+
}
|
|
564
|
+
}
|
|
565
|
+
resolveByConfidence(conflict, outputs) {
|
|
566
|
+
const relevant = outputs.filter((o) => conflict.agentIds.includes(o.agentId));
|
|
567
|
+
const winner = relevant.reduce((best, curr) => curr.confidence > best.confidence ? curr : best);
|
|
568
|
+
return {
|
|
569
|
+
strategy: 'choose_highest_confidence',
|
|
570
|
+
chosenAgentId: winner.agentId,
|
|
571
|
+
explanation: `Chose ${winner.agentId} with confidence ${winner.confidence}`,
|
|
572
|
+
resolvedAt: new Date(),
|
|
573
|
+
};
|
|
574
|
+
}
|
|
575
|
+
resolveByAuthority(conflict, outputs) {
|
|
576
|
+
const relevant = outputs.filter((o) => conflict.agentIds.includes(o.agentId));
|
|
577
|
+
const winner = relevant.reduce((best, curr) => (curr.authority ?? 0) > (best.authority ?? 0) ? curr : best);
|
|
578
|
+
return {
|
|
579
|
+
strategy: 'choose_highest_authority',
|
|
580
|
+
chosenAgentId: winner.agentId,
|
|
581
|
+
explanation: `Chose ${winner.agentId} with authority ${winner.authority}`,
|
|
582
|
+
resolvedAt: new Date(),
|
|
583
|
+
};
|
|
584
|
+
}
|
|
585
|
+
resolveMergeBoth(conflict) {
|
|
586
|
+
const merged = conflict.conflictingContent.join('\n\n// --- Alternative ---\n\n');
|
|
587
|
+
return {
|
|
588
|
+
strategy: 'merge_both',
|
|
589
|
+
mergedContent: merged,
|
|
590
|
+
explanation: 'Merged both versions',
|
|
591
|
+
resolvedAt: new Date(),
|
|
592
|
+
};
|
|
593
|
+
}
|
|
594
|
+
resolveByVoting(conflict, _outputs) {
|
|
595
|
+
// Count "votes" for each version
|
|
596
|
+
const votes = new Map();
|
|
597
|
+
for (const agentId of conflict.agentIds) {
|
|
598
|
+
votes.set(agentId, (votes.get(agentId) ?? 0) + 1);
|
|
599
|
+
}
|
|
600
|
+
const winner = Array.from(votes.entries()).reduce((best, curr) => curr[1] > best[1] ? curr : best)[0];
|
|
601
|
+
return {
|
|
602
|
+
strategy: 'voting',
|
|
603
|
+
chosenAgentId: winner,
|
|
604
|
+
explanation: `${winner} won by vote`,
|
|
605
|
+
resolvedAt: new Date(),
|
|
606
|
+
};
|
|
607
|
+
}
|
|
608
|
+
// ===========================================================================
|
|
609
|
+
// UTILITIES
|
|
610
|
+
// ===========================================================================
|
|
611
|
+
/**
|
|
612
|
+
* Calculate content similarity (Jaccard index).
|
|
613
|
+
*/
|
|
614
|
+
calculateSimilarity(a, b) {
|
|
615
|
+
const wordsA = new Set(a.toLowerCase().split(/\s+/));
|
|
616
|
+
const wordsB = new Set(b.toLowerCase().split(/\s+/));
|
|
617
|
+
const intersection = new Set([...wordsA].filter((x) => wordsB.has(x)));
|
|
618
|
+
const union = new Set([...wordsA, ...wordsB]);
|
|
619
|
+
return intersection.size / union.size;
|
|
620
|
+
}
|
|
621
|
+
/**
|
|
622
|
+
* Calculate combined confidence from multiple outputs.
|
|
623
|
+
*/
|
|
624
|
+
calculateCombinedConfidence(outputs) {
|
|
625
|
+
if (outputs.length === 0)
|
|
626
|
+
return 0;
|
|
627
|
+
// Weight by confidence and agreement
|
|
628
|
+
const totalWeight = outputs.reduce((sum, o) => sum + o.confidence, 0);
|
|
629
|
+
const avgConfidence = totalWeight / outputs.length;
|
|
630
|
+
// Boost if agents agree
|
|
631
|
+
const agreementBoost = this.calculateAgreement(outputs) * 0.1;
|
|
632
|
+
return Math.min(1, avgConfidence + agreementBoost);
|
|
633
|
+
}
|
|
634
|
+
/**
|
|
635
|
+
* Calculate agreement rate between outputs.
|
|
636
|
+
*/
|
|
637
|
+
calculateAgreement(outputs) {
|
|
638
|
+
if (outputs.length <= 1)
|
|
639
|
+
return 1;
|
|
640
|
+
let totalSimilarity = 0;
|
|
641
|
+
let pairs = 0;
|
|
642
|
+
for (let i = 0; i < outputs.length; i++) {
|
|
643
|
+
for (let j = i + 1; j < outputs.length; j++) {
|
|
644
|
+
totalSimilarity += this.calculateSimilarity(outputs[i].content, outputs[j].content);
|
|
645
|
+
pairs++;
|
|
646
|
+
}
|
|
647
|
+
}
|
|
648
|
+
return pairs > 0 ? totalSimilarity / pairs : 0;
|
|
649
|
+
}
|
|
650
|
+
/**
|
|
651
|
+
* Determine synthesis method based on output types.
|
|
652
|
+
*/
|
|
653
|
+
determineMethod(outputs) {
|
|
654
|
+
const types = outputs.map((o) => o.type);
|
|
655
|
+
if (types.every((t) => t === 'code')) {
|
|
656
|
+
return 'merge_structured';
|
|
657
|
+
}
|
|
658
|
+
if (types.every((t) => t === 'research')) {
|
|
659
|
+
return 'deduplicate';
|
|
660
|
+
}
|
|
661
|
+
if (this.config.useLLM && this.config.llmSynthesizer !== undefined) {
|
|
662
|
+
return 'synthesize_llm';
|
|
663
|
+
}
|
|
664
|
+
return this.config.defaultMethod;
|
|
665
|
+
}
|
|
666
|
+
/**
|
|
667
|
+
* Determine output type from multiple outputs.
|
|
668
|
+
*/
|
|
669
|
+
determineOutputType(outputs) {
|
|
670
|
+
const types = outputs.map((o) => o.type);
|
|
671
|
+
const uniqueTypes = new Set(types);
|
|
672
|
+
if (uniqueTypes.size === 1) {
|
|
673
|
+
return types[0];
|
|
674
|
+
}
|
|
675
|
+
return 'mixed';
|
|
676
|
+
}
|
|
677
|
+
/**
|
|
678
|
+
* Merge all file changes from outputs.
|
|
679
|
+
*/
|
|
680
|
+
mergeAllFileChanges(outputs) {
|
|
681
|
+
const byFile = new Map();
|
|
682
|
+
for (const output of outputs) {
|
|
683
|
+
for (const change of output.filesModified ?? []) {
|
|
684
|
+
if (!byFile.has(change.path)) {
|
|
685
|
+
byFile.set(change.path, []);
|
|
686
|
+
}
|
|
687
|
+
byFile.get(change.path).push(change);
|
|
688
|
+
}
|
|
689
|
+
}
|
|
690
|
+
const merged = [];
|
|
691
|
+
for (const [_filePath, changes] of byFile) {
|
|
692
|
+
if (changes.length === 1) {
|
|
693
|
+
merged.push(changes[0]);
|
|
694
|
+
}
|
|
695
|
+
else {
|
|
696
|
+
// Take the one with most content or merge
|
|
697
|
+
const best = changes.reduce((a, b) => a.newContent.length > b.newContent.length ? a : b);
|
|
698
|
+
merged.push(best);
|
|
699
|
+
}
|
|
700
|
+
}
|
|
701
|
+
return merged;
|
|
702
|
+
}
|
|
703
|
+
/**
|
|
704
|
+
* Merge file changes for a single file.
|
|
705
|
+
*/
|
|
706
|
+
mergeFileChanges(filePath, changes, outputs) {
|
|
707
|
+
const conflicts = [];
|
|
708
|
+
// Simple strategy: take the change with highest confidence
|
|
709
|
+
let bestChange = changes[0];
|
|
710
|
+
let bestConfidence = 0;
|
|
711
|
+
for (const change of changes) {
|
|
712
|
+
const output = outputs.find((o) => o.filesModified?.some((f) => f.path === filePath && f.newContent === change.newContent));
|
|
713
|
+
if (output && output.confidence > bestConfidence) {
|
|
714
|
+
bestConfidence = output.confidence;
|
|
715
|
+
bestChange = change;
|
|
716
|
+
}
|
|
717
|
+
}
|
|
718
|
+
// Detect if there are significant differences
|
|
719
|
+
for (let i = 0; i < changes.length; i++) {
|
|
720
|
+
for (let j = i + 1; j < changes.length; j++) {
|
|
721
|
+
const similarity = this.calculateSimilarity(changes[i].newContent, changes[j].newContent);
|
|
722
|
+
if (similarity < 0.8) {
|
|
723
|
+
conflicts.push({
|
|
724
|
+
id: `conflict-${++this.conflictCounter}`,
|
|
725
|
+
type: 'code_overlap',
|
|
726
|
+
agentIds: outputs
|
|
727
|
+
.filter((o) => o.filesModified?.some((f) => f.path === filePath))
|
|
728
|
+
.map((o) => o.agentId),
|
|
729
|
+
description: `Different versions of ${filePath}`,
|
|
730
|
+
conflictingContent: [changes[i].newContent.slice(0, 200), changes[j].newContent.slice(0, 200)],
|
|
731
|
+
severity: 'high',
|
|
732
|
+
filePath,
|
|
733
|
+
});
|
|
734
|
+
}
|
|
735
|
+
}
|
|
736
|
+
}
|
|
737
|
+
return { merged: bestChange, conflicts };
|
|
738
|
+
}
|
|
739
|
+
/**
|
|
740
|
+
* Extract all findings from outputs.
|
|
741
|
+
*/
|
|
742
|
+
extractAllFindings(outputs) {
|
|
743
|
+
const all = [];
|
|
744
|
+
for (const output of outputs) {
|
|
745
|
+
all.push(...(output.findings ?? []));
|
|
746
|
+
}
|
|
747
|
+
// Deduplicate
|
|
748
|
+
return [...new Set(all)];
|
|
749
|
+
}
|
|
750
|
+
/**
|
|
751
|
+
* Extract findings from content text.
|
|
752
|
+
*/
|
|
753
|
+
extractFindingsFromContent(content) {
|
|
754
|
+
const findings = [];
|
|
755
|
+
const lines = content.split('\n');
|
|
756
|
+
for (const line of lines) {
|
|
757
|
+
const trimmed = line.trim();
|
|
758
|
+
// Look for bullet points or findings indicators
|
|
759
|
+
if (trimmed.match(/^[-*•]\s+/) ||
|
|
760
|
+
trimmed.match(/^\d+\.\s+/) ||
|
|
761
|
+
trimmed.toLowerCase().includes('found:') ||
|
|
762
|
+
trimmed.toLowerCase().includes('discovered:')) {
|
|
763
|
+
const finding = trimmed.replace(/^[-*•\d.]+\s+/, '');
|
|
764
|
+
if (finding.length > 10) {
|
|
765
|
+
findings.push(finding);
|
|
766
|
+
}
|
|
767
|
+
}
|
|
768
|
+
}
|
|
769
|
+
return findings;
|
|
770
|
+
}
|
|
771
|
+
/**
|
|
772
|
+
* Deduplicate findings.
|
|
773
|
+
*/
|
|
774
|
+
deduplicateFindings(findings) {
|
|
775
|
+
const deduplicated = [];
|
|
776
|
+
for (const f of findings) {
|
|
777
|
+
const existing = deduplicated.find((d) => this.calculateSimilarity(d.finding, f.finding) > this.config.deduplicationThreshold);
|
|
778
|
+
if (existing) {
|
|
779
|
+
// Keep higher confidence
|
|
780
|
+
if (f.confidence > existing.confidence) {
|
|
781
|
+
existing.confidence = f.confidence;
|
|
782
|
+
}
|
|
783
|
+
}
|
|
784
|
+
else {
|
|
785
|
+
deduplicated.push({ finding: f.finding, confidence: f.confidence });
|
|
786
|
+
}
|
|
787
|
+
}
|
|
788
|
+
return deduplicated;
|
|
789
|
+
}
|
|
790
|
+
/**
|
|
791
|
+
* Detect contradictions between findings.
|
|
792
|
+
*/
|
|
793
|
+
detectFindingContradictions(findings) {
|
|
794
|
+
const conflicts = [];
|
|
795
|
+
for (let i = 0; i < findings.length; i++) {
|
|
796
|
+
for (let j = i + 1; j < findings.length; j++) {
|
|
797
|
+
const contradictions = this.findContradictions(findings[i].finding, findings[j].finding);
|
|
798
|
+
for (const c of contradictions) {
|
|
799
|
+
conflicts.push({
|
|
800
|
+
id: `conflict-${++this.conflictCounter}`,
|
|
801
|
+
type: 'fact_disagreement',
|
|
802
|
+
agentIds: [],
|
|
803
|
+
description: c.description,
|
|
804
|
+
conflictingContent: [c.contentA, c.contentB],
|
|
805
|
+
severity: 'medium',
|
|
806
|
+
});
|
|
807
|
+
}
|
|
808
|
+
}
|
|
809
|
+
}
|
|
810
|
+
return conflicts;
|
|
811
|
+
}
|
|
812
|
+
/**
|
|
813
|
+
* Calculate synthesis statistics.
|
|
814
|
+
*/
|
|
815
|
+
calculateStats(outputs, synthesizedContent, conflicts) {
|
|
816
|
+
const totalContentLength = outputs.reduce((sum, o) => sum + o.content.length, 0);
|
|
817
|
+
return {
|
|
818
|
+
inputCount: outputs.length,
|
|
819
|
+
totalContentLength,
|
|
820
|
+
synthesizedLength: synthesizedContent.length,
|
|
821
|
+
deduplicationRate: totalContentLength > 0
|
|
822
|
+
? 1 - (synthesizedContent.length / totalContentLength)
|
|
823
|
+
: 0,
|
|
824
|
+
conflictsDetected: conflicts.length,
|
|
825
|
+
conflictsResolved: conflicts.filter((c) => c.resolution).length,
|
|
826
|
+
agreementRate: this.calculateAgreement(outputs),
|
|
827
|
+
};
|
|
828
|
+
}
|
|
829
|
+
/**
|
|
830
|
+
* Create empty result.
|
|
831
|
+
*/
|
|
832
|
+
createEmptyResult() {
|
|
833
|
+
return {
|
|
834
|
+
output: '',
|
|
835
|
+
type: 'mixed',
|
|
836
|
+
confidence: 0,
|
|
837
|
+
fileChanges: [],
|
|
838
|
+
findings: [],
|
|
839
|
+
conflicts: [],
|
|
840
|
+
stats: {
|
|
841
|
+
inputCount: 0,
|
|
842
|
+
totalContentLength: 0,
|
|
843
|
+
synthesizedLength: 0,
|
|
844
|
+
deduplicationRate: 0,
|
|
845
|
+
conflictsDetected: 0,
|
|
846
|
+
conflictsResolved: 0,
|
|
847
|
+
agreementRate: 1,
|
|
848
|
+
},
|
|
849
|
+
method: 'concatenate',
|
|
850
|
+
};
|
|
851
|
+
}
|
|
852
|
+
/**
|
|
853
|
+
* Create result from single output.
|
|
854
|
+
*/
|
|
855
|
+
createSingleResult(output) {
|
|
856
|
+
return {
|
|
857
|
+
output: output.content,
|
|
858
|
+
type: output.type,
|
|
859
|
+
confidence: output.confidence,
|
|
860
|
+
fileChanges: output.filesModified ?? [],
|
|
861
|
+
findings: output.findings ?? [],
|
|
862
|
+
conflicts: [],
|
|
863
|
+
stats: {
|
|
864
|
+
inputCount: 1,
|
|
865
|
+
totalContentLength: output.content.length,
|
|
866
|
+
synthesizedLength: output.content.length,
|
|
867
|
+
deduplicationRate: 0,
|
|
868
|
+
conflictsDetected: 0,
|
|
869
|
+
conflictsResolved: 0,
|
|
870
|
+
agreementRate: 1,
|
|
871
|
+
},
|
|
872
|
+
method: 'concatenate',
|
|
873
|
+
};
|
|
874
|
+
}
|
|
875
|
+
/**
|
|
876
|
+
* Subscribe to events.
|
|
877
|
+
*/
|
|
878
|
+
on(listener) {
|
|
879
|
+
this.listeners.push(listener);
|
|
880
|
+
return () => {
|
|
881
|
+
const idx = this.listeners.indexOf(listener);
|
|
882
|
+
if (idx >= 0)
|
|
883
|
+
this.listeners.splice(idx, 1);
|
|
884
|
+
};
|
|
885
|
+
}
|
|
886
|
+
emit(event) {
|
|
887
|
+
for (const listener of this.listeners) {
|
|
888
|
+
try {
|
|
889
|
+
listener(event);
|
|
890
|
+
}
|
|
891
|
+
catch {
|
|
892
|
+
// Ignore listener errors
|
|
893
|
+
}
|
|
894
|
+
}
|
|
895
|
+
}
|
|
896
|
+
}
|
|
897
|
+
// =============================================================================
|
|
898
|
+
// FACTORY FUNCTIONS
|
|
899
|
+
// =============================================================================
|
|
900
|
+
/**
|
|
901
|
+
* Create a result synthesizer.
|
|
902
|
+
*
|
|
903
|
+
* @example
|
|
904
|
+
* ```typescript
|
|
905
|
+
* const synthesizer = createResultSynthesizer({
|
|
906
|
+
* conflictResolution: 'choose_highest_confidence',
|
|
907
|
+
* deduplicationThreshold: 0.85,
|
|
908
|
+
* });
|
|
909
|
+
*
|
|
910
|
+
* const result = await synthesizer.synthesize(agentOutputs);
|
|
911
|
+
* ```
|
|
912
|
+
*/
|
|
913
|
+
export function createResultSynthesizer(config = {}) {
|
|
914
|
+
return new ResultSynthesizer(config);
|
|
915
|
+
}
|
|
916
|
+
/**
|
|
917
|
+
* Create an LLM prompt for synthesis.
|
|
918
|
+
*/
|
|
919
|
+
export function createSynthesisPrompt(outputs, conflicts) {
|
|
920
|
+
const parts = [
|
|
921
|
+
'You are synthesizing results from multiple AI agents. Combine their findings into a coherent, unified response.',
|
|
922
|
+
'',
|
|
923
|
+
'## Agent Outputs',
|
|
924
|
+
'',
|
|
925
|
+
];
|
|
926
|
+
for (const output of outputs) {
|
|
927
|
+
parts.push(`### Agent: ${output.agentId} (confidence: ${output.confidence})`);
|
|
928
|
+
parts.push('');
|
|
929
|
+
parts.push(output.content);
|
|
930
|
+
parts.push('');
|
|
931
|
+
}
|
|
932
|
+
if (conflicts.length > 0) {
|
|
933
|
+
parts.push('## Detected Conflicts');
|
|
934
|
+
parts.push('');
|
|
935
|
+
for (const conflict of conflicts) {
|
|
936
|
+
parts.push(`- ${conflict.type}: ${conflict.description}`);
|
|
937
|
+
}
|
|
938
|
+
parts.push('');
|
|
939
|
+
parts.push('Please resolve these conflicts in your synthesis.');
|
|
940
|
+
}
|
|
941
|
+
parts.push('');
|
|
942
|
+
parts.push('## Instructions');
|
|
943
|
+
parts.push('1. Combine the key insights from all agents');
|
|
944
|
+
parts.push('2. Remove duplicate information');
|
|
945
|
+
parts.push('3. Resolve any contradictions');
|
|
946
|
+
parts.push('4. Provide a unified, coherent response');
|
|
947
|
+
parts.push('');
|
|
948
|
+
parts.push('Respond with JSON: { "content": "...", "findings": [...], "resolutions": [...], "confidence": 0.X }');
|
|
949
|
+
return parts.join('\n');
|
|
950
|
+
}
|
|
951
|
+
//# sourceMappingURL=result-synthesizer.js.map
|