homegraph 1.2.0 → 1.5.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/README.md +48 -11
- package/dist/bin/homegraph.js +298 -72
- package/dist/bin/homegraph.js.map +1 -1
- package/dist/context/index.d.ts.map +1 -1
- package/dist/context/index.js +117 -11
- package/dist/context/index.js.map +1 -1
- package/dist/db/index.d.ts +207 -6
- package/dist/db/index.d.ts.map +1 -1
- package/dist/db/index.js +461 -20
- package/dist/db/index.js.map +1 -1
- package/dist/db/migrations.d.ts +1 -1
- package/dist/db/migrations.d.ts.map +1 -1
- package/dist/db/migrations.js +19 -1
- package/dist/db/migrations.js.map +1 -1
- package/dist/db/queries.d.ts +157 -3
- package/dist/db/queries.d.ts.map +1 -1
- package/dist/db/queries.js +426 -9
- package/dist/db/queries.js.map +1 -1
- package/dist/db/schema.sql +32 -1
- package/dist/db/sqlite-adapter.d.ts +24 -17
- package/dist/db/sqlite-adapter.d.ts.map +1 -1
- package/dist/db/sqlite-adapter.js +292 -36
- package/dist/db/sqlite-adapter.js.map +1 -1
- package/dist/db/wal-valve.d.ts +119 -0
- package/dist/db/wal-valve.d.ts.map +1 -0
- package/dist/db/wal-valve.js +290 -0
- package/dist/db/wal-valve.js.map +1 -0
- package/dist/directory.d.ts +9 -5
- package/dist/directory.d.ts.map +1 -1
- package/dist/directory.js +210 -19
- package/dist/directory.js.map +1 -1
- package/dist/extraction/arkts-batch-worker.js +3 -2
- package/dist/extraction/arkts-batch-worker.js.map +1 -1
- package/dist/extraction/cfml-extractor.d.ts +107 -0
- package/dist/extraction/cfml-extractor.d.ts.map +1 -0
- package/dist/extraction/cfml-extractor.js +494 -0
- package/dist/extraction/cfml-extractor.js.map +1 -0
- package/dist/extraction/default-ignore.d.ts +39 -0
- package/dist/extraction/default-ignore.d.ts.map +1 -0
- package/dist/extraction/default-ignore.js +221 -0
- package/dist/extraction/default-ignore.js.map +1 -0
- package/dist/extraction/grammars.d.ts +25 -1
- package/dist/extraction/grammars.d.ts.map +1 -1
- package/dist/extraction/grammars.js +177 -24
- package/dist/extraction/grammars.js.map +1 -1
- package/dist/extraction/index.d.ts +52 -14
- package/dist/extraction/index.d.ts.map +1 -1
- package/dist/extraction/index.js +521 -314
- package/dist/extraction/index.js.map +1 -1
- package/dist/extraction/languages/arkts.d.ts +90 -6
- package/dist/extraction/languages/arkts.d.ts.map +1 -1
- package/dist/extraction/languages/arkts.js +1579 -128
- package/dist/extraction/languages/arkts.js.map +1 -1
- package/dist/extraction/languages/c-cpp.d.ts +42 -0
- package/dist/extraction/languages/c-cpp.d.ts.map +1 -1
- package/dist/extraction/languages/c-cpp.js +369 -4
- package/dist/extraction/languages/c-cpp.js.map +1 -1
- package/dist/extraction/languages/cfquery.d.ts +12 -0
- package/dist/extraction/languages/cfquery.d.ts.map +1 -0
- package/dist/extraction/languages/cfquery.js +28 -0
- package/dist/extraction/languages/cfquery.js.map +1 -0
- package/dist/extraction/languages/cfscript.d.ts +3 -0
- package/dist/extraction/languages/cfscript.d.ts.map +1 -0
- package/dist/extraction/languages/cfscript.js +73 -0
- package/dist/extraction/languages/cfscript.js.map +1 -0
- package/dist/extraction/languages/cobol.d.ts +33 -0
- package/dist/extraction/languages/cobol.d.ts.map +1 -0
- package/dist/extraction/languages/cobol.js +499 -0
- package/dist/extraction/languages/cobol.js.map +1 -0
- package/dist/extraction/languages/erlang.d.ts +3 -0
- package/dist/extraction/languages/erlang.d.ts.map +1 -0
- package/dist/extraction/languages/erlang.js +350 -0
- package/dist/extraction/languages/erlang.js.map +1 -0
- package/dist/extraction/languages/index.d.ts.map +1 -1
- package/dist/extraction/languages/index.js +16 -0
- package/dist/extraction/languages/index.js.map +1 -1
- package/dist/extraction/languages/nix.d.ts +3 -0
- package/dist/extraction/languages/nix.d.ts.map +1 -0
- package/dist/extraction/languages/nix.js +294 -0
- package/dist/extraction/languages/nix.js.map +1 -0
- package/dist/extraction/languages/solidity.d.ts +3 -0
- package/dist/extraction/languages/solidity.d.ts.map +1 -0
- package/dist/extraction/languages/solidity.js +293 -0
- package/dist/extraction/languages/solidity.js.map +1 -0
- package/dist/extraction/languages/terraform.d.ts +3 -0
- package/dist/extraction/languages/terraform.d.ts.map +1 -0
- package/dist/extraction/languages/terraform.js +641 -0
- package/dist/extraction/languages/terraform.js.map +1 -0
- package/dist/extraction/languages/vbnet.d.ts +11 -0
- package/dist/extraction/languages/vbnet.d.ts.map +1 -0
- package/dist/extraction/languages/vbnet.js +141 -0
- package/dist/extraction/languages/vbnet.js.map +1 -0
- package/dist/extraction/mybatis-extractor.d.ts +30 -10
- package/dist/extraction/mybatis-extractor.d.ts.map +1 -1
- package/dist/extraction/mybatis-extractor.js +140 -38
- package/dist/extraction/mybatis-extractor.js.map +1 -1
- package/dist/extraction/parse-pool.d.ts +27 -1
- package/dist/extraction/parse-pool.d.ts.map +1 -1
- package/dist/extraction/parse-pool.js +75 -7
- package/dist/extraction/parse-pool.js.map +1 -1
- package/dist/extraction/parse-worker.js +9 -2
- package/dist/extraction/parse-worker.js.map +1 -1
- package/dist/extraction/store-worker.d.ts +20 -0
- package/dist/extraction/store-worker.d.ts.map +1 -0
- package/dist/extraction/store-worker.js +102 -0
- package/dist/extraction/store-worker.js.map +1 -0
- package/dist/extraction/store-writer.d.ts +48 -0
- package/dist/extraction/store-writer.d.ts.map +1 -0
- package/dist/extraction/store-writer.js +167 -0
- package/dist/extraction/store-writer.js.map +1 -0
- package/dist/extraction/tree-sitter-helpers.d.ts.map +1 -1
- package/dist/extraction/tree-sitter-helpers.js +1 -0
- package/dist/extraction/tree-sitter-helpers.js.map +1 -1
- package/dist/extraction/tree-sitter-types.d.ts +3 -1
- package/dist/extraction/tree-sitter-types.d.ts.map +1 -1
- package/dist/extraction/tree-sitter.d.ts +38 -0
- package/dist/extraction/tree-sitter.d.ts.map +1 -1
- package/dist/extraction/tree-sitter.js +801 -10
- package/dist/extraction/tree-sitter.js.map +1 -1
- package/dist/extraction/wasm/tree-sitter-arkts.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-cfml.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-cfquery.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-cfscript.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-cobol.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-erlang.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-nix.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-terraform.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-vbnet.wasm +0 -0
- package/dist/extraction/wasm-runtime-flags.d.ts +14 -4
- package/dist/extraction/wasm-runtime-flags.d.ts.map +1 -1
- package/dist/extraction/wasm-runtime-flags.js +55 -7
- package/dist/extraction/wasm-runtime-flags.js.map +1 -1
- package/dist/graph/traversal.d.ts.map +1 -1
- package/dist/graph/traversal.js +1 -1
- package/dist/graph/traversal.js.map +1 -1
- package/dist/index.d.ts +74 -5
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +436 -55
- package/dist/index.js.map +1 -1
- package/dist/installer/index.d.ts +42 -0
- package/dist/installer/index.d.ts.map +1 -1
- package/dist/installer/index.js +97 -2
- package/dist/installer/index.js.map +1 -1
- package/dist/mcp/daemon.d.ts +25 -3
- package/dist/mcp/daemon.d.ts.map +1 -1
- package/dist/mcp/daemon.js +62 -8
- package/dist/mcp/daemon.js.map +1 -1
- package/dist/mcp/dynamic-boundaries.d.ts.map +1 -1
- package/dist/mcp/dynamic-boundaries.js +2 -1
- package/dist/mcp/dynamic-boundaries.js.map +1 -1
- package/dist/mcp/early-ppid.d.ts +26 -0
- package/dist/mcp/early-ppid.d.ts.map +1 -0
- package/dist/mcp/early-ppid.js +29 -0
- package/dist/mcp/early-ppid.js.map +1 -0
- package/dist/mcp/engine.d.ts +4 -5
- package/dist/mcp/engine.d.ts.map +1 -1
- package/dist/mcp/engine.js +27 -1
- package/dist/mcp/engine.js.map +1 -1
- package/dist/mcp/index.d.ts.map +1 -1
- package/dist/mcp/index.js +41 -6
- package/dist/mcp/index.js.map +1 -1
- package/dist/mcp/liveness-watchdog.d.ts +18 -1
- package/dist/mcp/liveness-watchdog.d.ts.map +1 -1
- package/dist/mcp/liveness-watchdog.js +73 -13
- package/dist/mcp/liveness-watchdog.js.map +1 -1
- package/dist/mcp/memory-budget.d.ts +30 -0
- package/dist/mcp/memory-budget.d.ts.map +1 -0
- package/dist/mcp/memory-budget.js +123 -0
- package/dist/mcp/memory-budget.js.map +1 -0
- package/dist/mcp/proxy.d.ts.map +1 -1
- package/dist/mcp/proxy.js +88 -4
- package/dist/mcp/proxy.js.map +1 -1
- package/dist/mcp/query-cache.d.ts +35 -4
- package/dist/mcp/query-cache.d.ts.map +1 -1
- package/dist/mcp/query-cache.js +89 -19
- package/dist/mcp/query-cache.js.map +1 -1
- package/dist/mcp/query-pool.d.ts +46 -12
- package/dist/mcp/query-pool.d.ts.map +1 -1
- package/dist/mcp/query-pool.js +100 -23
- package/dist/mcp/query-pool.js.map +1 -1
- package/dist/mcp/query-worker.d.ts +2 -2
- package/dist/mcp/query-worker.js +2 -2
- package/dist/mcp/server-instructions.d.ts +4 -27
- package/dist/mcp/server-instructions.d.ts.map +1 -1
- package/dist/mcp/server-instructions.js +39 -84
- package/dist/mcp/server-instructions.js.map +1 -1
- package/dist/mcp/session.d.ts +14 -0
- package/dist/mcp/session.d.ts.map +1 -1
- package/dist/mcp/session.js +28 -1
- package/dist/mcp/session.js.map +1 -1
- package/dist/mcp/startup-handshake.d.ts +44 -0
- package/dist/mcp/startup-handshake.d.ts.map +1 -0
- package/dist/mcp/startup-handshake.js +73 -0
- package/dist/mcp/startup-handshake.js.map +1 -0
- package/dist/mcp/tools.d.ts +104 -4
- package/dist/mcp/tools.d.ts.map +1 -1
- package/dist/mcp/tools.js +2432 -217
- package/dist/mcp/tools.js.map +1 -1
- package/dist/mcp/transport.d.ts.map +1 -1
- package/dist/mcp/transport.js +18 -0
- package/dist/mcp/transport.js.map +1 -1
- package/dist/project-config.d.ts +38 -0
- package/dist/project-config.d.ts.map +1 -1
- package/dist/project-config.js +101 -2
- package/dist/project-config.js.map +1 -1
- package/dist/resolution/c-fnptr-synthesizer.d.ts +2 -1
- package/dist/resolution/c-fnptr-synthesizer.d.ts.map +1 -1
- package/dist/resolution/c-fnptr-synthesizer.js +178 -146
- package/dist/resolution/c-fnptr-synthesizer.js.map +1 -1
- package/dist/resolution/callback-synthesizer.d.ts +54 -10
- package/dist/resolution/callback-synthesizer.d.ts.map +1 -1
- package/dist/resolution/callback-synthesizer.js +1299 -257
- package/dist/resolution/callback-synthesizer.js.map +1 -1
- package/dist/resolution/cooperative-yield.d.ts +10 -2
- package/dist/resolution/cooperative-yield.d.ts.map +1 -1
- package/dist/resolution/cooperative-yield.js +6 -4
- package/dist/resolution/cooperative-yield.js.map +1 -1
- package/dist/resolution/frameworks/cics.d.ts +20 -0
- package/dist/resolution/frameworks/cics.d.ts.map +1 -0
- package/dist/resolution/frameworks/cics.js +90 -0
- package/dist/resolution/frameworks/cics.js.map +1 -0
- package/dist/resolution/frameworks/go.d.ts.map +1 -1
- package/dist/resolution/frameworks/go.js +29 -6
- package/dist/resolution/frameworks/go.js.map +1 -1
- package/dist/resolution/frameworks/index.d.ts.map +1 -1
- package/dist/resolution/frameworks/index.js +3 -0
- package/dist/resolution/frameworks/index.js.map +1 -1
- package/dist/resolution/frameworks/java.d.ts.map +1 -1
- package/dist/resolution/frameworks/java.js +14 -6
- package/dist/resolution/frameworks/java.js.map +1 -1
- package/dist/resolution/frameworks/terraform.d.ts +38 -0
- package/dist/resolution/frameworks/terraform.d.ts.map +1 -0
- package/dist/resolution/frameworks/terraform.js +277 -0
- package/dist/resolution/frameworks/terraform.js.map +1 -0
- package/dist/resolution/goframe-synthesizer.d.ts +2 -1
- package/dist/resolution/goframe-synthesizer.d.ts.map +1 -1
- package/dist/resolution/goframe-synthesizer.js +8 -3
- package/dist/resolution/goframe-synthesizer.js.map +1 -1
- package/dist/resolution/import-resolver.d.ts +9 -3
- package/dist/resolution/import-resolver.d.ts.map +1 -1
- package/dist/resolution/import-resolver.js +295 -11
- package/dist/resolution/import-resolver.js.map +1 -1
- package/dist/resolution/index.d.ts +146 -8
- package/dist/resolution/index.d.ts.map +1 -1
- package/dist/resolution/index.js +1089 -131
- package/dist/resolution/index.js.map +1 -1
- package/dist/resolution/memory-budget.d.ts +48 -0
- package/dist/resolution/memory-budget.d.ts.map +1 -0
- package/dist/resolution/memory-budget.js +162 -0
- package/dist/resolution/memory-budget.js.map +1 -0
- package/dist/resolution/name-matcher.d.ts +12 -4
- package/dist/resolution/name-matcher.d.ts.map +1 -1
- package/dist/resolution/name-matcher.js +793 -130
- package/dist/resolution/name-matcher.js.map +1 -1
- package/dist/resolution/resolver-pool.d.ts +106 -0
- package/dist/resolution/resolver-pool.d.ts.map +1 -0
- package/dist/resolution/resolver-pool.js +344 -0
- package/dist/resolution/resolver-pool.js.map +1 -0
- package/dist/resolution/resolver-worker.d.ts +17 -0
- package/dist/resolution/resolver-worker.d.ts.map +1 -0
- package/dist/resolution/resolver-worker.js +141 -0
- package/dist/resolution/resolver-worker.js.map +1 -0
- package/dist/resolution/strip-comments.d.ts +1 -1
- package/dist/resolution/strip-comments.d.ts.map +1 -1
- package/dist/resolution/strip-comments.js +49 -0
- package/dist/resolution/strip-comments.js.map +1 -1
- package/dist/resolution/types.d.ts +32 -0
- package/dist/resolution/types.d.ts.map +1 -1
- package/dist/resolution/workspace-packages.d.ts +10 -0
- package/dist/resolution/workspace-packages.d.ts.map +1 -1
- package/dist/resolution/workspace-packages.js +142 -4
- package/dist/resolution/workspace-packages.js.map +1 -1
- package/dist/search/identifier-segments.d.ts +60 -0
- package/dist/search/identifier-segments.d.ts.map +1 -0
- package/dist/search/identifier-segments.js +176 -0
- package/dist/search/identifier-segments.js.map +1 -0
- package/dist/search/query-utils.d.ts +201 -0
- package/dist/search/query-utils.d.ts.map +1 -1
- package/dist/search/query-utils.js +919 -2
- package/dist/search/query-utils.js.map +1 -1
- package/dist/spec/build/diff-parser.d.ts +55 -0
- package/dist/spec/build/diff-parser.d.ts.map +1 -0
- package/dist/spec/build/diff-parser.js +205 -0
- package/dist/spec/build/diff-parser.js.map +1 -0
- package/dist/spec/build/git-scanner.d.ts +93 -0
- package/dist/spec/build/git-scanner.d.ts.map +1 -0
- package/dist/spec/build/git-scanner.js +254 -0
- package/dist/spec/build/git-scanner.js.map +1 -0
- package/dist/spec/build/pipeline.d.ts +54 -0
- package/dist/spec/build/pipeline.d.ts.map +1 -0
- package/dist/spec/build/pipeline.js +170 -0
- package/dist/spec/build/pipeline.js.map +1 -0
- package/dist/spec/build/scan.d.ts +48 -0
- package/dist/spec/build/scan.d.ts.map +1 -0
- package/dist/spec/build/scan.js +89 -0
- package/dist/spec/build/scan.js.map +1 -0
- package/dist/spec/build/scope-resolver.d.ts +50 -0
- package/dist/spec/build/scope-resolver.d.ts.map +1 -0
- package/dist/spec/build/scope-resolver.js +105 -0
- package/dist/spec/build/scope-resolver.js.map +1 -0
- package/dist/spec/build/spec-extractor.d.ts +74 -0
- package/dist/spec/build/spec-extractor.d.ts.map +1 -0
- package/dist/spec/build/spec-extractor.js +344 -0
- package/dist/spec/build/spec-extractor.js.map +1 -0
- package/dist/spec/config.d.ts +35 -1
- package/dist/spec/config.d.ts.map +1 -1
- package/dist/spec/config.js +30 -5
- package/dist/spec/config.js.map +1 -1
- package/dist/spec/db/fts.d.ts.map +1 -1
- package/dist/spec/db/fts.js +19 -50
- package/dist/spec/db/fts.js.map +1 -1
- package/dist/spec/db/index.d.ts +5 -3
- package/dist/spec/db/index.d.ts.map +1 -1
- package/dist/spec/db/index.js +16 -1
- package/dist/spec/db/index.js.map +1 -1
- package/dist/spec/db/persist.d.ts +45 -0
- package/dist/spec/db/persist.d.ts.map +1 -0
- package/dist/spec/db/persist.js +66 -0
- package/dist/spec/db/persist.js.map +1 -0
- package/dist/spec/db/relations.d.ts +80 -1
- package/dist/spec/db/relations.d.ts.map +1 -1
- package/dist/spec/db/relations.js +175 -4
- package/dist/spec/db/relations.js.map +1 -1
- package/dist/spec/db/schema.d.ts +4 -0
- package/dist/spec/db/schema.d.ts.map +1 -1
- package/dist/spec/db/schema.js +4 -0
- package/dist/spec/db/schema.js.map +1 -1
- package/dist/spec/db/schema.sql +5 -1
- package/dist/spec/db/spec-node.d.ts +5 -0
- package/dist/spec/db/spec-node.d.ts.map +1 -1
- package/dist/spec/db/spec-node.js +11 -5
- package/dist/spec/db/spec-node.js.map +1 -1
- package/dist/spec/db/sql-utils.d.ts +11 -0
- package/dist/spec/db/sql-utils.d.ts.map +1 -0
- package/dist/spec/db/sql-utils.js +19 -0
- package/dist/spec/db/sql-utils.js.map +1 -0
- package/dist/spec/evolve/cluster-context.d.ts +30 -0
- package/dist/spec/evolve/cluster-context.d.ts.map +1 -0
- package/dist/spec/evolve/cluster-context.js +78 -0
- package/dist/spec/evolve/cluster-context.js.map +1 -0
- package/dist/spec/evolve/commit-spec-analyzer.d.ts +51 -0
- package/dist/spec/evolve/commit-spec-analyzer.d.ts.map +1 -0
- package/dist/spec/evolve/commit-spec-analyzer.js +88 -0
- package/dist/spec/evolve/commit-spec-analyzer.js.map +1 -0
- package/dist/spec/evolve/commit-spec-persister.d.ts +53 -0
- package/dist/spec/evolve/commit-spec-persister.d.ts.map +1 -0
- package/dist/spec/evolve/commit-spec-persister.js +93 -0
- package/dist/spec/evolve/commit-spec-persister.js.map +1 -0
- package/dist/spec/evolve/impact-locator.d.ts +23 -7
- package/dist/spec/evolve/impact-locator.d.ts.map +1 -1
- package/dist/spec/evolve/impact-locator.js +58 -14
- package/dist/spec/evolve/impact-locator.js.map +1 -1
- package/dist/spec/evolve/pipeline.d.ts +62 -25
- package/dist/spec/evolve/pipeline.d.ts.map +1 -1
- package/dist/spec/evolve/pipeline.js +436 -457
- package/dist/spec/evolve/pipeline.js.map +1 -1
- package/dist/spec/evolve/spec-rewriter.d.ts +13 -13
- package/dist/spec/evolve/spec-rewriter.d.ts.map +1 -1
- package/dist/spec/evolve/spec-rewriter.js +45 -45
- package/dist/spec/evolve/spec-rewriter.js.map +1 -1
- package/dist/spec/git/commits.d.ts +85 -0
- package/dist/spec/git/commits.d.ts.map +1 -0
- package/dist/spec/git/commits.js +218 -0
- package/dist/spec/git/commits.js.map +1 -0
- package/dist/spec/git/exec.d.ts +13 -0
- package/dist/spec/git/exec.d.ts.map +1 -0
- package/dist/spec/git/exec.js +19 -0
- package/dist/spec/git/exec.js.map +1 -0
- package/dist/spec/git/index.d.ts +9 -0
- package/dist/spec/git/index.d.ts.map +1 -0
- package/dist/spec/git/index.js +22 -0
- package/dist/spec/git/index.js.map +1 -0
- package/dist/spec/git-utils.d.ts +8 -0
- package/dist/spec/git-utils.d.ts.map +1 -0
- package/dist/spec/git-utils.js +14 -0
- package/dist/spec/git-utils.js.map +1 -0
- package/dist/spec/graph/index.d.ts +8 -0
- package/dist/spec/graph/index.d.ts.map +1 -0
- package/dist/spec/graph/index.js +17 -0
- package/dist/spec/graph/index.js.map +1 -0
- package/dist/spec/graph/queries.d.ts +6 -35
- package/dist/spec/graph/queries.d.ts.map +1 -1
- package/dist/spec/graph/queries.js +71 -248
- package/dist/spec/graph/queries.js.map +1 -1
- package/dist/spec/llm/agent-client.d.ts +59 -0
- package/dist/spec/llm/agent-client.d.ts.map +1 -0
- package/dist/spec/llm/agent-client.js +213 -0
- package/dist/spec/llm/agent-client.js.map +1 -0
- package/dist/spec/llm/agents/claude-code.d.ts +32 -0
- package/dist/spec/llm/agents/claude-code.d.ts.map +1 -0
- package/dist/spec/llm/agents/claude-code.js +125 -0
- package/dist/spec/llm/agents/claude-code.js.map +1 -0
- package/dist/spec/llm/agents/codex.d.ts +32 -0
- package/dist/spec/llm/agents/codex.d.ts.map +1 -0
- package/dist/spec/llm/agents/codex.js +145 -0
- package/dist/spec/llm/agents/codex.js.map +1 -0
- package/dist/spec/llm/agents/detect-utils.d.ts +28 -0
- package/dist/spec/llm/agents/detect-utils.d.ts.map +1 -0
- package/dist/spec/llm/agents/detect-utils.js +91 -0
- package/dist/spec/llm/agents/detect-utils.js.map +1 -0
- package/dist/spec/llm/agents/deveco-code.d.ts +33 -0
- package/dist/spec/llm/agents/deveco-code.d.ts.map +1 -0
- package/dist/spec/llm/agents/deveco-code.js +165 -0
- package/dist/spec/llm/agents/deveco-code.js.map +1 -0
- package/dist/spec/llm/agents/index.d.ts +31 -0
- package/dist/spec/llm/agents/index.d.ts.map +1 -0
- package/dist/spec/llm/agents/index.js +65 -0
- package/dist/spec/llm/agents/index.js.map +1 -0
- package/dist/spec/llm/agents/types.d.ts +76 -0
- package/dist/spec/llm/agents/types.d.ts.map +1 -0
- package/dist/spec/llm/agents/types.js +15 -0
- package/dist/spec/llm/agents/types.js.map +1 -0
- package/dist/spec/llm/client.d.ts +31 -11
- package/dist/spec/llm/client.d.ts.map +1 -1
- package/dist/spec/llm/client.js +143 -81
- package/dist/spec/llm/client.js.map +1 -1
- package/dist/spec/llm/factory.d.ts +41 -0
- package/dist/spec/llm/factory.d.ts.map +1 -0
- package/dist/spec/llm/factory.js +80 -0
- package/dist/spec/llm/factory.js.map +1 -0
- package/dist/spec/llm/prompts.d.ts +24 -8
- package/dist/spec/llm/prompts.d.ts.map +1 -1
- package/dist/spec/llm/prompts.js +100 -50
- package/dist/spec/llm/prompts.js.map +1 -1
- package/dist/spec/llm/retry.d.ts +53 -0
- package/dist/spec/llm/retry.d.ts.map +1 -0
- package/dist/spec/llm/retry.js +153 -0
- package/dist/spec/llm/retry.js.map +1 -0
- package/dist/spec/mine/clusterer.d.ts +63 -0
- package/dist/spec/mine/clusterer.d.ts.map +1 -0
- package/dist/spec/mine/clusterer.js +904 -0
- package/dist/spec/mine/clusterer.js.map +1 -0
- package/dist/spec/mine/clustering/features.d.ts +38 -0
- package/dist/spec/mine/clustering/features.d.ts.map +1 -0
- package/dist/spec/mine/clustering/features.js +108 -0
- package/dist/spec/mine/clustering/features.js.map +1 -0
- package/dist/spec/mine/clustering/index.d.ts +62 -0
- package/dist/spec/mine/clustering/index.d.ts.map +1 -0
- package/dist/spec/mine/clustering/index.js +259 -0
- package/dist/spec/mine/clustering/index.js.map +1 -0
- package/dist/spec/mine/clustering/leiden.d.ts +61 -0
- package/dist/spec/mine/clustering/leiden.d.ts.map +1 -0
- package/dist/spec/mine/clustering/leiden.js +489 -0
- package/dist/spec/mine/clustering/leiden.js.map +1 -0
- package/dist/spec/mine/clustering/text-similarity.d.ts +22 -0
- package/dist/spec/mine/clustering/text-similarity.d.ts.map +1 -0
- package/dist/spec/mine/clustering/text-similarity.js +98 -0
- package/dist/spec/mine/clustering/text-similarity.js.map +1 -0
- package/dist/spec/mine/generator.d.ts +54 -0
- package/dist/spec/mine/generator.d.ts.map +1 -0
- package/dist/spec/mine/generator.js +267 -0
- package/dist/spec/mine/generator.js.map +1 -0
- package/dist/spec/mine/persist.d.ts +37 -0
- package/dist/spec/mine/persist.d.ts.map +1 -0
- package/dist/spec/mine/persist.js +170 -0
- package/dist/spec/mine/persist.js.map +1 -0
- package/dist/spec/mine/pipeline.d.ts +41 -0
- package/dist/spec/mine/pipeline.d.ts.map +1 -0
- package/dist/spec/mine/pipeline.js +236 -0
- package/dist/spec/mine/pipeline.js.map +1 -0
- package/dist/spec/mine/progress-handler.d.ts +22 -0
- package/dist/spec/mine/progress-handler.d.ts.map +1 -0
- package/dist/spec/mine/progress-handler.js +108 -0
- package/dist/spec/mine/progress-handler.js.map +1 -0
- package/dist/spec/mine/progress.d.ts +23 -0
- package/dist/spec/mine/progress.d.ts.map +1 -0
- package/dist/spec/mine/progress.js +12 -0
- package/dist/spec/mine/progress.js.map +1 -0
- package/dist/spec/mine/scanner.d.ts +59 -0
- package/dist/spec/mine/scanner.d.ts.map +1 -0
- package/dist/spec/mine/scanner.js +383 -0
- package/dist/spec/mine/scanner.js.map +1 -0
- package/dist/spec/types.d.ts +32 -0
- package/dist/spec/types.d.ts.map +1 -1
- package/dist/spec/ui/index.d.ts +9 -0
- package/dist/spec/ui/index.d.ts.map +1 -0
- package/dist/spec/ui/index.js +16 -0
- package/dist/spec/ui/index.js.map +1 -0
- package/dist/spec/ui/progress-handler.d.ts +33 -0
- package/dist/spec/ui/progress-handler.d.ts.map +1 -0
- package/dist/spec/ui/progress-handler.js +132 -0
- package/dist/spec/ui/progress-handler.js.map +1 -0
- package/dist/spec/ui/progress.d.ts +24 -0
- package/dist/spec/ui/progress.d.ts.map +1 -0
- package/dist/spec/ui/progress.js +13 -0
- package/dist/spec/ui/progress.js.map +1 -0
- package/dist/spec/utils/fs.d.ts +45 -0
- package/dist/spec/utils/fs.d.ts.map +1 -0
- package/dist/spec/utils/fs.js +163 -0
- package/dist/spec/utils/fs.js.map +1 -0
- package/dist/spec/utils/index.d.ts +12 -0
- package/dist/spec/utils/index.d.ts.map +1 -0
- package/dist/spec/utils/index.js +26 -0
- package/dist/spec/utils/index.js.map +1 -0
- package/dist/spec/utils/meta.d.ts +32 -0
- package/dist/spec/utils/meta.d.ts.map +1 -0
- package/dist/spec/utils/meta.js +122 -0
- package/dist/spec/utils/meta.js.map +1 -0
- package/dist/spec/utils/truncate.d.ts +86 -0
- package/dist/spec/utils/truncate.d.ts.map +1 -0
- package/dist/spec/utils/truncate.js +172 -0
- package/dist/spec/utils/truncate.js.map +1 -0
- package/dist/spec/utils.d.ts +4 -16
- package/dist/spec/utils.d.ts.map +1 -1
- package/dist/spec/utils.js +6 -58
- package/dist/spec/utils.js.map +1 -1
- package/dist/sync/git-hooks.d.ts.map +1 -1
- package/dist/sync/git-hooks.js +2 -0
- package/dist/sync/git-hooks.js.map +1 -1
- package/dist/sync/watcher.d.ts +35 -6
- package/dist/sync/watcher.d.ts.map +1 -1
- package/dist/sync/watcher.js +127 -17
- package/dist/sync/watcher.js.map +1 -1
- package/dist/sync/worktree.d.ts.map +1 -1
- package/dist/sync/worktree.js +5 -0
- package/dist/sync/worktree.js.map +1 -1
- package/dist/telemetry/index.js +3 -3
- package/dist/telemetry/index.js.map +1 -1
- package/dist/types.d.ts +22 -1
- package/dist/types.d.ts.map +1 -1
- package/dist/types.js +10 -0
- package/dist/types.js.map +1 -1
- package/dist/upgrade/index.d.ts +32 -0
- package/dist/upgrade/index.d.ts.map +1 -1
- package/dist/upgrade/index.js +162 -14
- package/dist/upgrade/index.js.map +1 -1
- package/dist/upgrade/remove-binary.d.ts +87 -0
- package/dist/upgrade/remove-binary.d.ts.map +1 -0
- package/dist/upgrade/remove-binary.js +289 -0
- package/dist/upgrade/remove-binary.js.map +1 -0
- package/dist/upgrade/update-check.d.ts +92 -0
- package/dist/upgrade/update-check.d.ts.map +1 -0
- package/dist/upgrade/update-check.js +258 -0
- package/dist/upgrade/update-check.js.map +1 -0
- package/package.json +6 -2
- package/scripts/agent-eval/run-all.sh +6 -0
- package/scripts/build-bundle.sh +5 -0
- package/scripts/npm-shim.js +8 -1
- package/scripts/exp_boundary_eval/__pycache__/_utils.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/__pycache__/analyze.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/__pycache__/deveco_arm.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/__pycache__/run_one.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/__pycache__/run_session.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/__pycache__/setup.cpython-310.pyc +0 -0
- package/scripts/exp_boundary_eval/data/agents.json +0 -109
- package/scripts/exp_boundary_eval/data/experiments.json +0 -140
- package/scripts/qa_eval/README.md +0 -407
- package/scripts/qa_eval/_test_deveco_probe.py +0 -41
- package/scripts/qa_eval/agent_runner.py +0 -526
- package/scripts/qa_eval/data/.gitignore +0 -4
- package/scripts/qa_eval/data/test-set.jsonl +0 -2
- package/scripts/qa_eval/eval_metrics.py +0 -274
- package/scripts/qa_eval/external_agent.py +0 -976
- package/scripts/qa_eval/llm_config.py +0 -92
- package/scripts/qa_eval/memory_monitor.py +0 -132
- package/scripts/qa_eval/my_answer_accuracy.py +0 -187
- package/scripts/qa_eval/requirements.txt +0 -2
- package/scripts/qa_eval/run_pipeline.py +0 -804
- package/scripts/qa_eval/stats_efficiency.py +0 -279
- package/scripts/qa_eval/stats_scores.py +0 -207
|
@@ -1,9 +1,16 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* MCP query cache —
|
|
2
|
+
* MCP query cache — memory key index + serialized tool responses in homegraph.db.
|
|
3
|
+
*
|
|
4
|
+
* A per-project in-memory Set of cache keys gives O(1) negative lookup so misses
|
|
5
|
+
* skip the SQLite SELECT. Payloads stay in homegraph.db; the Set is warmed from
|
|
6
|
+
* DB on first use after daemon restart when the index stamp is still valid.
|
|
3
7
|
*
|
|
4
8
|
* Invalidated wholesale when the index stamp or cache format version changes.
|
|
5
9
|
* Per-call staleness/worktree notices are applied AFTER cache lookup so hits
|
|
6
10
|
* stay fresh.
|
|
11
|
+
*
|
|
12
|
+
* The key Set lives on the daemon main thread only (cache read/write runs there
|
|
13
|
+
* before/after worker-pool explore dispatch), so no cross-thread locking is needed.
|
|
7
14
|
*/
|
|
8
15
|
import type { QueryBuilder } from '../db/queries';
|
|
9
16
|
import type { ToolResult } from './tools';
|
|
@@ -11,6 +18,33 @@ import type { ToolResult } from './tools';
|
|
|
11
18
|
export declare const QUERY_CACHE_FORMAT_VERSION = 1;
|
|
12
19
|
export declare function isMcpQueryCacheEnabled(): boolean;
|
|
13
20
|
export declare function isCacheableMcpTool(toolName: string): boolean;
|
|
21
|
+
/**
|
|
22
|
+
* In-memory index of cache keys for one project. Negative lookup (key absent)
|
|
23
|
+
* returns immediately without touching SQLite; positive lookup fetches the
|
|
24
|
+
* JSON payload from mcp_query_cache.
|
|
25
|
+
*/
|
|
26
|
+
export declare class McpQueryCacheIndex {
|
|
27
|
+
private keys;
|
|
28
|
+
/** Stamp/format this Set was last synchronized against (null = cold). */
|
|
29
|
+
private syncedStamp;
|
|
30
|
+
private syncedFormat;
|
|
31
|
+
/** Whether `cacheKey` is known to exist — O(1), no DB I/O. */
|
|
32
|
+
has(cacheKey: string): boolean;
|
|
33
|
+
/**
|
|
34
|
+
* Align the in-memory key Set with DB metadata. Clears both layers when the
|
|
35
|
+
* index stamp or format version changed; otherwise warms keys from DB on first
|
|
36
|
+
* use after process restart.
|
|
37
|
+
*/
|
|
38
|
+
ensureValid(queries: QueryBuilder, getIndexStamp: () => number | null): void;
|
|
39
|
+
/** Drop in-memory keys (e.g. after the DB file was replaced on disk). */
|
|
40
|
+
reset(): void;
|
|
41
|
+
getEntry(queries: QueryBuilder, cacheKey: string): ToolResult | null;
|
|
42
|
+
setEntry(queries: QueryBuilder, cacheKey: string, toolName: string, result: ToolResult): void;
|
|
43
|
+
private loadKeysFromDb;
|
|
44
|
+
}
|
|
45
|
+
export declare function getMcpQueryCacheIndex(projectRoot: string): McpQueryCacheIndex;
|
|
46
|
+
/** Test helper — drop all per-project indices between cases. */
|
|
47
|
+
export declare function resetMcpQueryCacheIndices(): void;
|
|
14
48
|
/**
|
|
15
49
|
* Tokenize a natural-language explore query into a stable, order-independent
|
|
16
50
|
* symbol bag for cache keys — different phrasing, same symbols → same key.
|
|
@@ -19,7 +53,4 @@ export declare function normalizeExploreQueryTerms(query: string): string[];
|
|
|
19
53
|
/** Build the pre-hash fingerprint string for a tool + args pair. */
|
|
20
54
|
export declare function buildMcpQueryCacheFingerprint(toolName: string, args: Record<string, unknown>, fileCount?: number): string;
|
|
21
55
|
export declare function buildMcpQueryCacheKey(toolName: string, args: Record<string, unknown>, fileCount?: number): string;
|
|
22
|
-
export declare function ensureMcpQueryCacheValid(queries: QueryBuilder, getIndexStamp: () => number | null): void;
|
|
23
|
-
export declare function getMcpQueryCacheEntry(queries: QueryBuilder, cacheKey: string): ToolResult | null;
|
|
24
|
-
export declare function setMcpQueryCacheEntry(queries: QueryBuilder, cacheKey: string, toolName: string, result: ToolResult): void;
|
|
25
56
|
//# sourceMappingURL=query-cache.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"query-cache.d.ts","sourceRoot":"","sources":["../../src/mcp/query-cache.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"query-cache.d.ts","sourceRoot":"","sources":["../../src/mcp/query-cache.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAClD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAS1C,yEAAyE;AACzE,eAAO,MAAM,0BAA0B,IAAI,CAAC;AAW5C,wBAAgB,sBAAsB,IAAI,OAAO,CAGhD;AAED,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAE5D;AAED;;;;GAIG;AACH,qBAAa,kBAAkB;IAC7B,OAAO,CAAC,IAAI,CAAqB;IACjC,yEAAyE;IACzE,OAAO,CAAC,WAAW,CAAuB;IAC1C,OAAO,CAAC,YAAY,CAAuB;IAE3C,8DAA8D;IAC9D,GAAG,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO;IAI9B;;;;OAIG;IACH,WAAW,CAAC,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,MAAM,MAAM,GAAG,IAAI,GAAG,IAAI;IAuB5E,yEAAyE;IACzE,KAAK,IAAI,IAAI;IAMb,QAAQ,CAAC,OAAO,EAAE,YAAY,EAAE,QAAQ,EAAE,MAAM,GAAG,UAAU,GAAG,IAAI;IAKpE,QAAQ,CACN,OAAO,EAAE,YAAY,EACrB,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,MAAM,EAChB,MAAM,EAAE,UAAU,GACjB,IAAI;IAKP,OAAO,CAAC,cAAc;CAMvB;AAED,wBAAgB,qBAAqB,CAAC,WAAW,EAAE,MAAM,GAAG,kBAAkB,CAO7E;AAED,gEAAgE;AAChE,wBAAgB,yBAAyB,IAAI,IAAI,CAEhD;AAED;;;GAGG;AACH,wBAAgB,0BAA0B,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,EAAE,CAQlE;AAwBD,oEAAoE;AACpE,wBAAgB,6BAA6B,CAC3C,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,SAAS,CAAC,EAAE,MAAM,GACjB,MAAM,CAqER;AAUD,wBAAgB,qBAAqB,CACnC,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,SAAS,CAAC,EAAE,MAAM,GACjB,MAAM,CAGR"}
|
package/dist/mcp/query-cache.js
CHANGED
|
@@ -1,21 +1,27 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
/**
|
|
3
|
-
* MCP query cache —
|
|
3
|
+
* MCP query cache — memory key index + serialized tool responses in homegraph.db.
|
|
4
|
+
*
|
|
5
|
+
* A per-project in-memory Set of cache keys gives O(1) negative lookup so misses
|
|
6
|
+
* skip the SQLite SELECT. Payloads stay in homegraph.db; the Set is warmed from
|
|
7
|
+
* DB on first use after daemon restart when the index stamp is still valid.
|
|
4
8
|
*
|
|
5
9
|
* Invalidated wholesale when the index stamp or cache format version changes.
|
|
6
10
|
* Per-call staleness/worktree notices are applied AFTER cache lookup so hits
|
|
7
11
|
* stay fresh.
|
|
12
|
+
*
|
|
13
|
+
* The key Set lives on the daemon main thread only (cache read/write runs there
|
|
14
|
+
* before/after worker-pool explore dispatch), so no cross-thread locking is needed.
|
|
8
15
|
*/
|
|
9
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
10
|
-
exports.QUERY_CACHE_FORMAT_VERSION = void 0;
|
|
17
|
+
exports.McpQueryCacheIndex = exports.QUERY_CACHE_FORMAT_VERSION = void 0;
|
|
11
18
|
exports.isMcpQueryCacheEnabled = isMcpQueryCacheEnabled;
|
|
12
19
|
exports.isCacheableMcpTool = isCacheableMcpTool;
|
|
20
|
+
exports.getMcpQueryCacheIndex = getMcpQueryCacheIndex;
|
|
21
|
+
exports.resetMcpQueryCacheIndices = resetMcpQueryCacheIndices;
|
|
13
22
|
exports.normalizeExploreQueryTerms = normalizeExploreQueryTerms;
|
|
14
23
|
exports.buildMcpQueryCacheFingerprint = buildMcpQueryCacheFingerprint;
|
|
15
24
|
exports.buildMcpQueryCacheKey = buildMcpQueryCacheKey;
|
|
16
|
-
exports.ensureMcpQueryCacheValid = ensureMcpQueryCacheValid;
|
|
17
|
-
exports.getMcpQueryCacheEntry = getMcpQueryCacheEntry;
|
|
18
|
-
exports.setMcpQueryCacheEntry = setMcpQueryCacheEntry;
|
|
19
25
|
const node_crypto_1 = require("node:crypto");
|
|
20
26
|
/** Mirrors `getExploreOutputBudget` tier breakpoints — cache-key only. */
|
|
21
27
|
function defaultExploreMaxFiles(fileCount) {
|
|
@@ -31,6 +37,8 @@ const METADATA_INDEX_STAMP = 'query_cache_index_stamp';
|
|
|
31
37
|
const METADATA_FORMAT_VERSION = 'query_cache_format_version';
|
|
32
38
|
/** Tools that must stay live — never cached. */
|
|
33
39
|
const NON_CACHEABLE_TOOLS = new Set(['homegraph_status', 'homegraph_spec_match']);
|
|
40
|
+
/** Per resolved project root — one index per homegraph.db. */
|
|
41
|
+
const cacheIndices = new Map();
|
|
34
42
|
function isMcpQueryCacheEnabled() {
|
|
35
43
|
const raw = process.env.HOMEGRAPH_MCP_CACHE;
|
|
36
44
|
return raw === '1' || raw === 'true';
|
|
@@ -38,6 +46,80 @@ function isMcpQueryCacheEnabled() {
|
|
|
38
46
|
function isCacheableMcpTool(toolName) {
|
|
39
47
|
return !NON_CACHEABLE_TOOLS.has(toolName);
|
|
40
48
|
}
|
|
49
|
+
/**
|
|
50
|
+
* In-memory index of cache keys for one project. Negative lookup (key absent)
|
|
51
|
+
* returns immediately without touching SQLite; positive lookup fetches the
|
|
52
|
+
* JSON payload from mcp_query_cache.
|
|
53
|
+
*/
|
|
54
|
+
class McpQueryCacheIndex {
|
|
55
|
+
keys = new Set();
|
|
56
|
+
/** Stamp/format this Set was last synchronized against (null = cold). */
|
|
57
|
+
syncedStamp = null;
|
|
58
|
+
syncedFormat = null;
|
|
59
|
+
/** Whether `cacheKey` is known to exist — O(1), no DB I/O. */
|
|
60
|
+
has(cacheKey) {
|
|
61
|
+
return this.keys.has(cacheKey);
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Align the in-memory key Set with DB metadata. Clears both layers when the
|
|
65
|
+
* index stamp or format version changed; otherwise warms keys from DB on first
|
|
66
|
+
* use after process restart.
|
|
67
|
+
*/
|
|
68
|
+
ensureValid(queries, getIndexStamp) {
|
|
69
|
+
const currentStamp = String(getIndexStamp() ?? 0);
|
|
70
|
+
const currentFormat = String(exports.QUERY_CACHE_FORMAT_VERSION);
|
|
71
|
+
const storedStamp = queries.getMetadata(METADATA_INDEX_STAMP);
|
|
72
|
+
const storedFormat = queries.getMetadata(METADATA_FORMAT_VERSION);
|
|
73
|
+
if (storedStamp === currentStamp && storedFormat === currentFormat) {
|
|
74
|
+
if (this.syncedStamp !== currentStamp || this.syncedFormat !== currentFormat) {
|
|
75
|
+
this.loadKeysFromDb(queries);
|
|
76
|
+
this.syncedStamp = currentStamp;
|
|
77
|
+
this.syncedFormat = currentFormat;
|
|
78
|
+
}
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
queries.clearMcpQueryCache();
|
|
82
|
+
queries.setMetadata(METADATA_INDEX_STAMP, currentStamp);
|
|
83
|
+
queries.setMetadata(METADATA_FORMAT_VERSION, currentFormat);
|
|
84
|
+
this.keys.clear();
|
|
85
|
+
this.syncedStamp = currentStamp;
|
|
86
|
+
this.syncedFormat = currentFormat;
|
|
87
|
+
}
|
|
88
|
+
/** Drop in-memory keys (e.g. after the DB file was replaced on disk). */
|
|
89
|
+
reset() {
|
|
90
|
+
this.keys.clear();
|
|
91
|
+
this.syncedStamp = null;
|
|
92
|
+
this.syncedFormat = null;
|
|
93
|
+
}
|
|
94
|
+
getEntry(queries, cacheKey) {
|
|
95
|
+
if (!this.keys.has(cacheKey))
|
|
96
|
+
return null;
|
|
97
|
+
return readMcpQueryCachePayload(queries, cacheKey);
|
|
98
|
+
}
|
|
99
|
+
setEntry(queries, cacheKey, toolName, result) {
|
|
100
|
+
writeMcpQueryCachePayload(queries, cacheKey, toolName, result);
|
|
101
|
+
this.keys.add(cacheKey);
|
|
102
|
+
}
|
|
103
|
+
loadKeysFromDb(queries) {
|
|
104
|
+
this.keys.clear();
|
|
105
|
+
for (const key of queries.listMcpQueryCacheKeys()) {
|
|
106
|
+
this.keys.add(key);
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
exports.McpQueryCacheIndex = McpQueryCacheIndex;
|
|
111
|
+
function getMcpQueryCacheIndex(projectRoot) {
|
|
112
|
+
let index = cacheIndices.get(projectRoot);
|
|
113
|
+
if (!index) {
|
|
114
|
+
index = new McpQueryCacheIndex();
|
|
115
|
+
cacheIndices.set(projectRoot, index);
|
|
116
|
+
}
|
|
117
|
+
return index;
|
|
118
|
+
}
|
|
119
|
+
/** Test helper — drop all per-project indices between cases. */
|
|
120
|
+
function resetMcpQueryCacheIndices() {
|
|
121
|
+
cacheIndices.clear();
|
|
122
|
+
}
|
|
41
123
|
/**
|
|
42
124
|
* Tokenize a natural-language explore query into a stable, order-independent
|
|
43
125
|
* symbol bag for cache keys — different phrasing, same symbols → same key.
|
|
@@ -158,19 +240,7 @@ function buildMcpQueryCacheKey(toolName, args, fileCount) {
|
|
|
158
240
|
const fingerprint = buildMcpQueryCacheFingerprint(toolName, args, fileCount);
|
|
159
241
|
return (0, node_crypto_1.createHash)('sha256').update(fingerprint, 'utf8').digest('hex');
|
|
160
242
|
}
|
|
161
|
-
function
|
|
162
|
-
const currentStamp = String(getIndexStamp() ?? 0);
|
|
163
|
-
const storedStamp = queries.getMetadata(METADATA_INDEX_STAMP);
|
|
164
|
-
const storedFormat = queries.getMetadata(METADATA_FORMAT_VERSION);
|
|
165
|
-
const currentFormat = String(exports.QUERY_CACHE_FORMAT_VERSION);
|
|
166
|
-
if (storedStamp === currentStamp && storedFormat === currentFormat) {
|
|
167
|
-
return;
|
|
168
|
-
}
|
|
169
|
-
queries.clearMcpQueryCache();
|
|
170
|
-
queries.setMetadata(METADATA_INDEX_STAMP, currentStamp);
|
|
171
|
-
queries.setMetadata(METADATA_FORMAT_VERSION, currentFormat);
|
|
172
|
-
}
|
|
173
|
-
function getMcpQueryCacheEntry(queries, cacheKey) {
|
|
243
|
+
function readMcpQueryCachePayload(queries, cacheKey) {
|
|
174
244
|
const row = queries.getMcpQueryCache(cacheKey);
|
|
175
245
|
if (!row)
|
|
176
246
|
return null;
|
|
@@ -184,7 +254,7 @@ function getMcpQueryCacheEntry(queries, cacheKey) {
|
|
|
184
254
|
return null;
|
|
185
255
|
}
|
|
186
256
|
}
|
|
187
|
-
function
|
|
257
|
+
function writeMcpQueryCachePayload(queries, cacheKey, toolName, result) {
|
|
188
258
|
const shortTool = toolName.replace(/^homegraph_/, '');
|
|
189
259
|
queries.setMcpQueryCache(cacheKey, shortTool, JSON.stringify(result), Date.now());
|
|
190
260
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"query-cache.js","sourceRoot":"","sources":["../../src/mcp/query-cache.ts"],"names":[],"mappings":";AAAA
|
|
1
|
+
{"version":3,"file":"query-cache.js","sourceRoot":"","sources":["../../src/mcp/query-cache.ts"],"names":[],"mappings":"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"}
|
package/dist/mcp/query-pool.d.ts
CHANGED
|
@@ -10,17 +10,25 @@
|
|
|
10
10
|
* connection) restores true multi-core parallelism and an idle main loop.
|
|
11
11
|
*
|
|
12
12
|
* Properties:
|
|
13
|
-
* - lazy growth:
|
|
14
|
-
*
|
|
15
|
-
*
|
|
13
|
+
* - lazy growth: **no worker until the first heavy call**, then grows to
|
|
14
|
+
* `size` on demand. Eager warm-start used to open a second full DB on every
|
|
15
|
+
* MCP session and balloon RSS (~5GB on ~800MB indexes).
|
|
16
|
+
* - **default concurrency is 1** — each worker is another V8 + WAL open; on
|
|
17
|
+
* large indexes two workers routinely doubled working-set into multi-GB.
|
|
18
|
+
* Override with `CODEGRAPH_QUERY_POOL_SIZE` when you truly need more.
|
|
19
|
+
* - **admission**: when outstanding work already fills `size` in-flight plus
|
|
20
|
+
* another `size` waiting, further calls resolve immediately with
|
|
21
|
+
* success-shaped busy/partial guidance instead of queuing up to die at the
|
|
22
|
+
* client hard timeout.
|
|
16
23
|
* - crash recovery: a dead worker is respawned and its in-flight call retried
|
|
17
24
|
* once; a poison call that keeps crashing fails gracefully (never wedges the
|
|
18
25
|
* pool). A crash budget trips a circuit breaker (`healthy` → false) so the
|
|
19
26
|
* caller falls back to in-process dispatch instead of thrashing respawns.
|
|
20
27
|
* - graceful backstop: a call that can't be served within `softTimeoutMs`
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
*
|
|
28
|
+
* (default 20s, clamped ≤30s — well under typical ~60s MCP client timeouts)
|
|
29
|
+
* resolves with SUCCESS-shaped static "Partial / busy, retry" guidance —
|
|
30
|
+
* never `isError`, and never DB/FTS work on the timeout callback (that
|
|
31
|
+
* can freeze the transport so the client still sees empty `-32001`).
|
|
24
32
|
*/
|
|
25
33
|
import type { ToolResult } from './tools';
|
|
26
34
|
/**
|
|
@@ -39,9 +47,9 @@ export interface PoolWorker {
|
|
|
39
47
|
export interface QueryPoolOptions {
|
|
40
48
|
/** Default project root each worker opens at spawn. */
|
|
41
49
|
root: string;
|
|
42
|
-
/** Max worker threads. Defaults to `clamp(cores-1, 1,
|
|
50
|
+
/** Max worker threads. Defaults to `clamp(cores-1, 1, DEFAULT_POOL_CAP)`. */
|
|
43
51
|
size?: number;
|
|
44
|
-
/** Linger before a queued call gets busy-guidance. Default
|
|
52
|
+
/** Linger before a queued/in-flight call gets busy-guidance. Default 20s (≤30s clamp). */
|
|
45
53
|
softTimeoutMs?: number;
|
|
46
54
|
/** Retries for an in-flight call whose worker crashed. Default 1. */
|
|
47
55
|
maxRetries?: number;
|
|
@@ -51,11 +59,19 @@ export interface QueryPoolOptions {
|
|
|
51
59
|
/**
|
|
52
60
|
* Resolve the pool size from the `CODEGRAPH_QUERY_POOL_SIZE` override and the
|
|
53
61
|
* machine's core count. `0` (or a negative) explicitly disables the pool (the
|
|
54
|
-
* caller serves in-process — today's behavior). Unset → `clamp(cores-1, 1,
|
|
55
|
-
*
|
|
56
|
-
*
|
|
62
|
+
* caller serves in-process — today's behavior). Unset → `clamp(cores-1, 1, 1)`:
|
|
63
|
+
* one parallel explore without a second full-DB RSS hit. Explicit overrides still
|
|
64
|
+
* honor up to {@link MAX_POOL_SIZE}.
|
|
57
65
|
*/
|
|
58
66
|
export declare function resolvePoolSize(envVal: string | undefined, cpuCount: number): number;
|
|
67
|
+
/**
|
|
68
|
+
* Soft / tool deadline. Env `CODEGRAPH_QUERY_BUSY_TIMEOUT_MS` may raise or
|
|
69
|
+
* lower it, but is always clamped into `[1000, MAX_BUSY_TIMEOUT_MS]` so a
|
|
70
|
+
* mistaken `60000` cannot race DevEco/Cursor's ~60s MCP hard timeout.
|
|
71
|
+
*/
|
|
72
|
+
export declare function resolveBusyTimeoutMs(): number;
|
|
73
|
+
/** Same as {@link resolveBusyTimeoutMs} — used by ToolHandler for all tools. */
|
|
74
|
+
export declare function resolveToolDeadlineMs(): number;
|
|
59
75
|
export declare class QueryPool {
|
|
60
76
|
private idle;
|
|
61
77
|
private queue;
|
|
@@ -70,7 +86,14 @@ export declare class QueryPool {
|
|
|
70
86
|
private readonly softTimeoutMs;
|
|
71
87
|
private readonly maxRetries;
|
|
72
88
|
private readonly createWorker;
|
|
89
|
+
private everReady;
|
|
73
90
|
constructor(opts: QueryPoolOptions);
|
|
91
|
+
/**
|
|
92
|
+
* True once at least one worker has completed a successful cold-start handshake.
|
|
93
|
+
* False during the cold-start window (and after destroy) so ToolHandler can
|
|
94
|
+
* fall back to in-process dispatch instead of queuing behind a busy backstop.
|
|
95
|
+
*/
|
|
96
|
+
get ready(): boolean;
|
|
74
97
|
/** Pool size cap (for logging/status). */
|
|
75
98
|
get size(): number;
|
|
76
99
|
/** Live worker count (for tests/status). */
|
|
@@ -81,13 +104,24 @@ export declare class QueryPool {
|
|
|
81
104
|
* degrades to today's behavior instead of failing tool calls.
|
|
82
105
|
*/
|
|
83
106
|
get healthy(): boolean;
|
|
107
|
+
/** In-flight + unsettled queued jobs (for admission / tests). */
|
|
108
|
+
outstandingCount(): number;
|
|
109
|
+
/**
|
|
110
|
+
* How many unsettled jobs we tolerate before refusing new ones immediately.
|
|
111
|
+
* One full wave running + one full wave waiting — further fan-out gets
|
|
112
|
+
* busy/partial guidance instead of stacking up to the soft timeout.
|
|
113
|
+
*/
|
|
114
|
+
private admissionLimit;
|
|
84
115
|
private spawnOne;
|
|
85
116
|
private onMessage;
|
|
86
117
|
private onWorkerGone;
|
|
87
118
|
private drain;
|
|
88
119
|
private settle;
|
|
120
|
+
private settleBusyOrPartial;
|
|
89
121
|
/** Run a read tool on the pool. Always resolves (never rejects). */
|
|
90
|
-
run(toolName: string, args: Record<string, unknown
|
|
122
|
+
run(toolName: string, args: Record<string, unknown>, opts?: {
|
|
123
|
+
onSoftTimeout?: () => ToolResult | null | undefined;
|
|
124
|
+
}): Promise<ToolResult>;
|
|
91
125
|
/** Terminate all workers and answer any outstanding calls gracefully. */
|
|
92
126
|
destroy(): Promise<void>;
|
|
93
127
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"query-pool.d.ts","sourceRoot":"","sources":["../../src/mcp/query-pool.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"query-pool.d.ts","sourceRoot":"","sources":["../../src/mcp/query-pool.ts"],"names":[],"mappings":"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"}
|
package/dist/mcp/query-pool.js
CHANGED
|
@@ -11,17 +11,25 @@
|
|
|
11
11
|
* connection) restores true multi-core parallelism and an idle main loop.
|
|
12
12
|
*
|
|
13
13
|
* Properties:
|
|
14
|
-
* - lazy growth:
|
|
15
|
-
*
|
|
16
|
-
*
|
|
14
|
+
* - lazy growth: **no worker until the first heavy call**, then grows to
|
|
15
|
+
* `size` on demand. Eager warm-start used to open a second full DB on every
|
|
16
|
+
* MCP session and balloon RSS (~5GB on ~800MB indexes).
|
|
17
|
+
* - **default concurrency is 1** — each worker is another V8 + WAL open; on
|
|
18
|
+
* large indexes two workers routinely doubled working-set into multi-GB.
|
|
19
|
+
* Override with `CODEGRAPH_QUERY_POOL_SIZE` when you truly need more.
|
|
20
|
+
* - **admission**: when outstanding work already fills `size` in-flight plus
|
|
21
|
+
* another `size` waiting, further calls resolve immediately with
|
|
22
|
+
* success-shaped busy/partial guidance instead of queuing up to die at the
|
|
23
|
+
* client hard timeout.
|
|
17
24
|
* - crash recovery: a dead worker is respawned and its in-flight call retried
|
|
18
25
|
* once; a poison call that keeps crashing fails gracefully (never wedges the
|
|
19
26
|
* pool). A crash budget trips a circuit breaker (`healthy` → false) so the
|
|
20
27
|
* caller falls back to in-process dispatch instead of thrashing respawns.
|
|
21
28
|
* - graceful backstop: a call that can't be served within `softTimeoutMs`
|
|
22
|
-
*
|
|
23
|
-
*
|
|
24
|
-
*
|
|
29
|
+
* (default 20s, clamped ≤30s — well under typical ~60s MCP client timeouts)
|
|
30
|
+
* resolves with SUCCESS-shaped static "Partial / busy, retry" guidance —
|
|
31
|
+
* never `isError`, and never DB/FTS work on the timeout callback (that
|
|
32
|
+
* can freeze the transport so the client still sees empty `-32001`).
|
|
25
33
|
*/
|
|
26
34
|
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
27
35
|
if (k2 === undefined) k2 = k;
|
|
@@ -59,13 +67,29 @@ var __importStar = (this && this.__importStar) || (function () {
|
|
|
59
67
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
60
68
|
exports.QueryPool = void 0;
|
|
61
69
|
exports.resolvePoolSize = resolvePoolSize;
|
|
70
|
+
exports.resolveBusyTimeoutMs = resolveBusyTimeoutMs;
|
|
71
|
+
exports.resolveToolDeadlineMs = resolveToolDeadlineMs;
|
|
62
72
|
const worker_threads_1 = require("worker_threads");
|
|
63
73
|
const path = __importStar(require("path"));
|
|
64
74
|
const os = __importStar(require("os"));
|
|
65
75
|
/** Compiled sibling — `query-worker.js` lives next to this file in `dist/mcp/`. */
|
|
66
76
|
const WORKER_FILE = path.join(__dirname, 'query-worker.js');
|
|
67
|
-
/**
|
|
68
|
-
|
|
77
|
+
/**
|
|
78
|
+
* Default soft backstop — must stay **well below** typical MCP client hard
|
|
79
|
+
* timeouts (~60s). Eval / agent configs sometimes set the env to 60000, which
|
|
80
|
+
* races the client and yields empty `-32001`; we clamp to
|
|
81
|
+
* {@link MAX_BUSY_TIMEOUT_MS} regardless. Prefer returning busy/partial early
|
|
82
|
+
* so the agent can retry once instead of waiting out the client hard cut.
|
|
83
|
+
*/
|
|
84
|
+
const DEFAULT_BUSY_TIMEOUT_MS = 15_000;
|
|
85
|
+
/** Hard ceiling — leave headroom under ~30–60s client timeouts (flush / scheduling). */
|
|
86
|
+
const MAX_BUSY_TIMEOUT_MS = 20_000;
|
|
87
|
+
/**
|
|
88
|
+
* Default concurrent workers when env is unset. Keep at 1: a second connection
|
|
89
|
+
* on a large index is a multi-GB RSS hit. Explicit env overrides still go up to
|
|
90
|
+
* {@link MAX_POOL_SIZE}.
|
|
91
|
+
*/
|
|
92
|
+
const DEFAULT_POOL_CAP = 1;
|
|
69
93
|
/** Hard ceiling on pool size regardless of core count / env. */
|
|
70
94
|
const MAX_POOL_SIZE = 16;
|
|
71
95
|
/**
|
|
@@ -87,9 +111,9 @@ const MAX_CONCURRENT_SPAWN = 2;
|
|
|
87
111
|
/**
|
|
88
112
|
* Resolve the pool size from the `CODEGRAPH_QUERY_POOL_SIZE` override and the
|
|
89
113
|
* machine's core count. `0` (or a negative) explicitly disables the pool (the
|
|
90
|
-
* caller serves in-process — today's behavior). Unset → `clamp(cores-1, 1,
|
|
91
|
-
*
|
|
92
|
-
*
|
|
114
|
+
* caller serves in-process — today's behavior). Unset → `clamp(cores-1, 1, 1)`:
|
|
115
|
+
* one parallel explore without a second full-DB RSS hit. Explicit overrides still
|
|
116
|
+
* honor up to {@link MAX_POOL_SIZE}.
|
|
93
117
|
*/
|
|
94
118
|
function resolvePoolSize(envVal, cpuCount) {
|
|
95
119
|
if (envVal !== undefined && envVal !== '') {
|
|
@@ -98,8 +122,13 @@ function resolvePoolSize(envVal, cpuCount) {
|
|
|
98
122
|
return Math.min(Math.floor(n), MAX_POOL_SIZE);
|
|
99
123
|
// non-numeric / negative → fall through to the default
|
|
100
124
|
}
|
|
101
|
-
return Math.max(1, Math.min(cpuCount - 1,
|
|
125
|
+
return Math.max(1, Math.min(cpuCount - 1, DEFAULT_POOL_CAP));
|
|
102
126
|
}
|
|
127
|
+
/**
|
|
128
|
+
* Soft / tool deadline. Env `CODEGRAPH_QUERY_BUSY_TIMEOUT_MS` may raise or
|
|
129
|
+
* lower it, but is always clamped into `[1000, MAX_BUSY_TIMEOUT_MS]` so a
|
|
130
|
+
* mistaken `60000` cannot race DevEco/Cursor's ~60s MCP hard timeout.
|
|
131
|
+
*/
|
|
103
132
|
function resolveBusyTimeoutMs() {
|
|
104
133
|
const raw = process.env.CODEGRAPH_QUERY_BUSY_TIMEOUT_MS;
|
|
105
134
|
if (raw === undefined || raw === '')
|
|
@@ -107,17 +136,25 @@ function resolveBusyTimeoutMs() {
|
|
|
107
136
|
const n = Number(raw);
|
|
108
137
|
if (!Number.isFinite(n) || n < 1000)
|
|
109
138
|
return DEFAULT_BUSY_TIMEOUT_MS;
|
|
110
|
-
return Math.floor(n);
|
|
139
|
+
return Math.min(Math.floor(n), MAX_BUSY_TIMEOUT_MS);
|
|
140
|
+
}
|
|
141
|
+
/** Same as {@link resolveBusyTimeoutMs} — used by ToolHandler for all tools. */
|
|
142
|
+
function resolveToolDeadlineMs() {
|
|
143
|
+
return resolveBusyTimeoutMs();
|
|
111
144
|
}
|
|
112
145
|
/** Success-shaped overload guidance (NEVER isError — see the abandonment rule). */
|
|
113
|
-
function busyGuidance(waitedMs) {
|
|
146
|
+
function busyGuidance(waitedMs, reason = 'timeout') {
|
|
114
147
|
const secs = Math.max(1, Math.round(waitedMs / 1000));
|
|
148
|
+
const why = reason === 'admission'
|
|
149
|
+
? 'too many concurrent HomeGraph queries are already in flight'
|
|
150
|
+
: `this call waited ${secs}s in the queue / on a worker`;
|
|
115
151
|
return {
|
|
116
152
|
content: [{
|
|
117
153
|
type: 'text',
|
|
118
|
-
text:
|
|
119
|
-
`
|
|
120
|
-
`
|
|
154
|
+
text: `⚠️ **Partial result** — HomeGraph is busy (${why}). This is NOT an error. ` +
|
|
155
|
+
`Retry ONE \`homegraph_explore\` with the concrete symbol/file names from the question — ` +
|
|
156
|
+
`do not fire search+explore or node+callers+callees in parallel, and do not fall back to grep/read ` +
|
|
157
|
+
`for symbols you already named (that duplicates tokens). A single retry usually returns full source.`,
|
|
121
158
|
}],
|
|
122
159
|
};
|
|
123
160
|
}
|
|
@@ -140,13 +177,23 @@ class QueryPool {
|
|
|
140
177
|
softTimeoutMs;
|
|
141
178
|
maxRetries;
|
|
142
179
|
createWorker;
|
|
180
|
+
everReady = false;
|
|
143
181
|
constructor(opts) {
|
|
144
182
|
this.root = opts.root;
|
|
145
|
-
this.maxSize = Math.max(1, Math.min(opts.size ?? Math.max(1, os.cpus().length - 1), MAX_POOL_SIZE));
|
|
183
|
+
this.maxSize = Math.max(1, Math.min(opts.size ?? Math.min(DEFAULT_POOL_CAP, Math.max(1, os.cpus().length - 1)), MAX_POOL_SIZE));
|
|
146
184
|
this.softTimeoutMs = opts.softTimeoutMs ?? resolveBusyTimeoutMs();
|
|
147
185
|
this.maxRetries = opts.maxRetries ?? 1;
|
|
148
186
|
this.createWorker = opts.createWorker ?? (() => new worker_threads_1.Worker(WORKER_FILE, { workerData: { root: this.root } }));
|
|
149
|
-
|
|
187
|
+
// One eager warm worker so the first tool call isn't queued behind a cold start (#662).
|
|
188
|
+
this.spawnOne();
|
|
189
|
+
}
|
|
190
|
+
/**
|
|
191
|
+
* True once at least one worker has completed a successful cold-start handshake.
|
|
192
|
+
* False during the cold-start window (and after destroy) so ToolHandler can
|
|
193
|
+
* fall back to in-process dispatch instead of queuing behind a busy backstop.
|
|
194
|
+
*/
|
|
195
|
+
get ready() {
|
|
196
|
+
return this.everReady && !this.destroyed;
|
|
150
197
|
}
|
|
151
198
|
/** Pool size cap (for logging/status). */
|
|
152
199
|
get size() { return this.maxSize; }
|
|
@@ -160,6 +207,18 @@ class QueryPool {
|
|
|
160
207
|
get healthy() {
|
|
161
208
|
return !this.destroyed && this.totalCrashes < CRASH_BUDGET;
|
|
162
209
|
}
|
|
210
|
+
/** In-flight + unsettled queued jobs (for admission / tests). */
|
|
211
|
+
outstandingCount() {
|
|
212
|
+
return this.inflight.size + this.queue.filter((j) => !j.settled).length;
|
|
213
|
+
}
|
|
214
|
+
/**
|
|
215
|
+
* How many unsettled jobs we tolerate before refusing new ones immediately.
|
|
216
|
+
* One full wave running + one full wave waiting — further fan-out gets
|
|
217
|
+
* busy/partial guidance instead of stacking up to the soft timeout.
|
|
218
|
+
*/
|
|
219
|
+
admissionLimit() {
|
|
220
|
+
return this.maxSize * 2;
|
|
221
|
+
}
|
|
163
222
|
spawnOne() {
|
|
164
223
|
if (this.destroyed || this.workers.size >= this.maxSize)
|
|
165
224
|
return;
|
|
@@ -185,6 +244,8 @@ class QueryPool {
|
|
|
185
244
|
this.pendingWorkers.delete(w);
|
|
186
245
|
if (m.ok === false)
|
|
187
246
|
this.totalCrashes++; // hard open failure
|
|
247
|
+
else
|
|
248
|
+
this.everReady = true;
|
|
188
249
|
this.idle.push(w);
|
|
189
250
|
this.drain();
|
|
190
251
|
return;
|
|
@@ -257,19 +318,35 @@ class QueryPool {
|
|
|
257
318
|
clearTimeout(job.softTimer);
|
|
258
319
|
job.resolve(result);
|
|
259
320
|
}
|
|
321
|
+
settleBusyOrPartial(job, reason) {
|
|
322
|
+
if (job.settled)
|
|
323
|
+
return;
|
|
324
|
+
const partial = job.onSoftTimeout?.();
|
|
325
|
+
if (partial) {
|
|
326
|
+
this.settle(job, partial);
|
|
327
|
+
return;
|
|
328
|
+
}
|
|
329
|
+
this.settle(job, busyGuidance(Date.now() - job.enqueuedAt, reason));
|
|
330
|
+
}
|
|
260
331
|
/** Run a read tool on the pool. Always resolves (never rejects). */
|
|
261
|
-
run(toolName, args) {
|
|
332
|
+
run(toolName, args, opts) {
|
|
262
333
|
return new Promise((resolve) => {
|
|
263
334
|
const job = {
|
|
264
335
|
id: this.nextId++, toolName, args, resolve,
|
|
265
336
|
retries: 0, settled: false, enqueuedAt: Date.now(),
|
|
337
|
+
onSoftTimeout: opts?.onSoftTimeout,
|
|
266
338
|
};
|
|
339
|
+
// Hard admission: refuse to stack another wave that would sit until soft
|
|
340
|
+
// timeout / client hard timeout. Caller gets partial/busy NOW.
|
|
341
|
+
if (this.outstandingCount() >= this.admissionLimit()) {
|
|
342
|
+
this.settleBusyOrPartial(job, 'admission');
|
|
343
|
+
return;
|
|
344
|
+
}
|
|
267
345
|
// Don't let the caller wait past softTimeoutMs. The worker may still be
|
|
268
346
|
// busy (we can't cancel synchronous CPU), but the CLIENT gets a prompt,
|
|
269
|
-
// success-shaped "retry" instead of a hard timeout.
|
|
347
|
+
// success-shaped "retry"/partial instead of a hard timeout.
|
|
270
348
|
job.softTimer = setTimeout(() => {
|
|
271
|
-
|
|
272
|
-
this.settle(job, busyGuidance(Date.now() - job.enqueuedAt));
|
|
349
|
+
this.settleBusyOrPartial(job, 'timeout');
|
|
273
350
|
}, this.softTimeoutMs);
|
|
274
351
|
job.softTimer.unref?.();
|
|
275
352
|
this.queue.push(job);
|