kirograph 0.17.0 → 0.19.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +1 -1
- package/README.md +103 -1822
- package/dist/architecture/layers/dart.js +112 -0
- package/dist/architecture/layers/dart.js.map +7 -0
- package/dist/architecture/layers/index.js +3 -1
- package/dist/architecture/layers/index.js.map +2 -2
- package/dist/bin/banner.js +74 -6
- package/dist/bin/banner.js.map +2 -2
- package/dist/bin/commands/attack-surface.js +157 -0
- package/dist/bin/commands/attack-surface.js.map +7 -0
- package/dist/bin/commands/benchmark.js +206 -0
- package/dist/bin/commands/benchmark.js.map +7 -0
- package/dist/bin/commands/budget.js +70 -0
- package/dist/bin/commands/budget.js.map +7 -0
- package/dist/bin/commands/communities.js +77 -0
- package/dist/bin/commands/communities.js.map +7 -0
- package/dist/bin/commands/dep-confusion.js +119 -0
- package/dist/bin/commands/dep-confusion.js.map +7 -0
- package/dist/bin/commands/export.js +304 -10
- package/dist/bin/commands/export.js.map +2 -2
- package/dist/bin/commands/flows.js +97 -0
- package/dist/bin/commands/flows.js.map +7 -0
- package/dist/bin/commands/help.js +382 -101
- package/dist/bin/commands/help.js.map +2 -2
- package/dist/bin/commands/install.js +90 -8
- package/dist/bin/commands/install.js.map +2 -2
- package/dist/bin/commands/licenses.js +201 -0
- package/dist/bin/commands/licenses.js.map +7 -0
- package/dist/bin/commands/reachability.js +160 -0
- package/dist/bin/commands/reachability.js.map +7 -0
- package/dist/bin/commands/read.js +100 -0
- package/dist/bin/commands/read.js.map +7 -0
- package/dist/bin/commands/refactor.js +116 -0
- package/dist/bin/commands/refactor.js.map +7 -0
- package/dist/bin/commands/remediation.js +133 -0
- package/dist/bin/commands/remediation.js.map +7 -0
- package/dist/bin/commands/sbom.js +76 -0
- package/dist/bin/commands/sbom.js.map +7 -0
- package/dist/bin/commands/security-ci-report.js +267 -0
- package/dist/bin/commands/security-ci-report.js.map +7 -0
- package/dist/bin/commands/security-export.js +1349 -0
- package/dist/bin/commands/security-export.js.map +7 -0
- package/dist/bin/commands/security-flows.js +126 -0
- package/dist/bin/commands/security-flows.js.map +7 -0
- package/dist/bin/commands/security-secrets.js +170 -0
- package/dist/bin/commands/security-secrets.js.map +7 -0
- package/dist/bin/commands/security.js +193 -0
- package/dist/bin/commands/security.js.map +7 -0
- package/dist/bin/commands/staleness.js +144 -0
- package/dist/bin/commands/staleness.js.map +7 -0
- package/dist/bin/commands/status.js +102 -2
- package/dist/bin/commands/status.js.map +2 -2
- package/dist/bin/commands/supply-chain.js +138 -0
- package/dist/bin/commands/supply-chain.js.map +7 -0
- package/dist/bin/commands/uninit.js +109 -60
- package/dist/bin/commands/uninit.js.map +2 -2
- package/dist/bin/commands/vex.js +76 -0
- package/dist/bin/commands/vex.js.map +7 -0
- package/dist/bin/commands/vuln-suppress.js +95 -0
- package/dist/bin/commands/vuln-suppress.js.map +7 -0
- package/dist/bin/commands/vulns.js +382 -0
- package/dist/bin/commands/vulns.js.map +7 -0
- package/dist/bin/installer/auto-detect.js +125 -0
- package/dist/bin/installer/auto-detect.js.map +7 -0
- package/dist/bin/installer/cli-agent.js +28 -5
- package/dist/bin/installer/cli-agent.js.map +2 -2
- package/dist/bin/installer/common.js +47 -0
- package/dist/bin/installer/common.js.map +2 -2
- package/dist/bin/installer/config-prompt.js +12 -1
- package/dist/bin/installer/config-prompt.js.map +2 -2
- package/dist/bin/installer/detect.js +309 -0
- package/dist/bin/installer/detect.js.map +7 -0
- package/dist/bin/installer/index.js +9 -1
- package/dist/bin/installer/index.js.map +2 -2
- package/dist/bin/installer/instructions.js +195 -3
- package/dist/bin/installer/instructions.js.map +2 -2
- package/dist/bin/installer/steering.js +407 -0
- package/dist/bin/installer/steering.js.map +2 -2
- package/dist/bin/installer/targets/aider.js +3 -3
- package/dist/bin/installer/targets/aider.js.map +2 -2
- package/dist/bin/installer/targets/amp.js +3 -3
- package/dist/bin/installer/targets/amp.js.map +2 -2
- package/dist/bin/installer/targets/antigravity.js +35 -6
- package/dist/bin/installer/targets/antigravity.js.map +2 -2
- package/dist/bin/installer/targets/augment.js +3 -3
- package/dist/bin/installer/targets/augment.js.map +2 -2
- package/dist/bin/installer/targets/claude.js +49 -5
- package/dist/bin/installer/targets/claude.js.map +2 -2
- package/dist/bin/installer/targets/cline.js +32 -6
- package/dist/bin/installer/targets/cline.js.map +2 -2
- package/dist/bin/installer/targets/codex.js +64 -12
- package/dist/bin/installer/targets/codex.js.map +2 -2
- package/dist/bin/installer/targets/continue.js +2 -2
- package/dist/bin/installer/targets/continue.js.map +2 -2
- package/dist/bin/installer/targets/copilot-cli.js +101 -0
- package/dist/bin/installer/targets/copilot-cli.js.map +7 -0
- package/dist/bin/installer/targets/copilot.js +31 -5
- package/dist/bin/installer/targets/copilot.js.map +2 -2
- package/dist/bin/installer/targets/cursor.js +4 -4
- package/dist/bin/installer/targets/cursor.js.map +2 -2
- package/dist/bin/installer/targets/devin.js +2 -2
- package/dist/bin/installer/targets/devin.js.map +2 -2
- package/dist/bin/installer/targets/gemini-cli.js +2 -2
- package/dist/bin/installer/targets/gemini-cli.js.map +2 -2
- package/dist/bin/installer/targets/generic.js +2 -14
- package/dist/bin/installer/targets/generic.js.map +2 -2
- package/dist/bin/installer/targets/goose.js +3 -3
- package/dist/bin/installer/targets/goose.js.map +2 -2
- package/dist/bin/installer/targets/index.js +250 -0
- package/dist/bin/installer/targets/index.js.map +2 -2
- package/dist/bin/installer/targets/junie.js +2 -2
- package/dist/bin/installer/targets/junie.js.map +2 -2
- package/dist/bin/installer/targets/kilo.js +2 -2
- package/dist/bin/installer/targets/kilo.js.map +2 -2
- package/dist/bin/installer/targets/kiro.js +3 -3
- package/dist/bin/installer/targets/kiro.js.map +2 -2
- package/dist/bin/installer/targets/opencode.js +2 -2
- package/dist/bin/installer/targets/opencode.js.map +2 -2
- package/dist/bin/installer/targets/openhands.js +3 -3
- package/dist/bin/installer/targets/openhands.js.map +2 -2
- package/dist/bin/installer/targets/qoder.js +91 -0
- package/dist/bin/installer/targets/qoder.js.map +7 -0
- package/dist/bin/installer/targets/qwen.js +96 -0
- package/dist/bin/installer/targets/qwen.js.map +7 -0
- package/dist/bin/installer/targets/replit.js +3 -3
- package/dist/bin/installer/targets/replit.js.map +2 -2
- package/dist/bin/installer/targets/roo.js +2 -2
- package/dist/bin/installer/targets/roo.js.map +2 -2
- package/dist/bin/installer/targets/tabnine.js +3 -3
- package/dist/bin/installer/targets/tabnine.js.map +2 -2
- package/dist/bin/installer/targets/trae.js +5 -5
- package/dist/bin/installer/targets/trae.js.map +2 -2
- package/dist/bin/installer/targets/warp.js +2 -2
- package/dist/bin/installer/targets/warp.js.map +2 -2
- package/dist/bin/installer/targets/windsurf.js +35 -6
- package/dist/bin/installer/targets/windsurf.js.map +2 -2
- package/dist/bin/kirograph.js +72 -6
- package/dist/bin/kirograph.js.map +3 -3
- package/dist/compression/tracker.js +80 -0
- package/dist/compression/tracker.js.map +2 -2
- package/dist/config.js +90 -3
- package/dist/config.js.map +2 -2
- package/dist/core/pipeline.js +36 -2
- package/dist/core/pipeline.js.map +2 -2
- package/dist/db/database.js +56 -5
- package/dist/db/database.js.map +2 -2
- package/dist/db/memory-schema.sql +5 -1
- package/dist/db/schema.sql +3 -1
- package/dist/db/security-schema.sql +72 -0
- package/dist/extraction/extractor.js +81 -0
- package/dist/extraction/extractor.js.map +2 -2
- package/dist/extraction/grammars.js +32 -8
- package/dist/extraction/grammars.js.map +2 -2
- package/dist/extraction/languages.js +43 -1
- package/dist/extraction/languages.js.map +2 -2
- package/dist/extraction/notebook.js +300 -0
- package/dist/extraction/notebook.js.map +7 -0
- package/dist/extraction/wasm/tree-sitter-astro.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-gdscript.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-julia.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-nix.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-perl.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-powershell.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-r.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-sql.wasm +0 -0
- package/dist/extraction/wasm/tree-sitter-verilog.wasm +0 -0
- package/dist/frameworks/flutter.js +130 -0
- package/dist/frameworks/flutter.js.map +7 -0
- package/dist/frameworks/index.js +7 -1
- package/dist/frameworks/index.js.map +3 -3
- package/dist/graph/communities.js +317 -0
- package/dist/graph/communities.js.map +7 -0
- package/dist/graph/flows.js +138 -0
- package/dist/graph/flows.js.map +7 -0
- package/dist/graph/refactor.js +155 -0
- package/dist/graph/refactor.js.map +7 -0
- package/dist/index.js +1 -1
- package/dist/index.js.map +2 -2
- package/dist/mcp/cache.js +172 -0
- package/dist/mcp/cache.js.map +7 -0
- package/dist/mcp/read-modes.js +295 -0
- package/dist/mcp/read-modes.js.map +7 -0
- package/dist/mcp/server.js +2 -1
- package/dist/mcp/server.js.map +2 -2
- package/dist/mcp/tool-names.js +21 -1
- package/dist/mcp/tool-names.js.map +2 -2
- package/dist/mcp/tools.js +1160 -1
- package/dist/mcp/tools.js.map +3 -3
- package/dist/memory/database.js +32 -2
- package/dist/memory/database.js.map +2 -2
- package/dist/memory/types.js.map +1 -1
- package/dist/resolution/bridges/android-rn.js +298 -0
- package/dist/resolution/bridges/android-rn.js.map +7 -0
- package/dist/resolution/bridges/expo-modules.js +155 -0
- package/dist/resolution/bridges/expo-modules.js.map +7 -0
- package/dist/resolution/bridges/flutter-channel.js +385 -0
- package/dist/resolution/bridges/flutter-channel.js.map +7 -0
- package/dist/resolution/bridges/index.js +80 -0
- package/dist/resolution/bridges/index.js.map +7 -0
- package/dist/resolution/bridges/native-events.js +188 -0
- package/dist/resolution/bridges/native-events.js.map +7 -0
- package/dist/resolution/bridges/native-views.js +244 -0
- package/dist/resolution/bridges/native-views.js.map +7 -0
- package/dist/resolution/bridges/react-native.js +161 -0
- package/dist/resolution/bridges/react-native.js.map +7 -0
- package/dist/resolution/bridges/swift-objc.js +227 -0
- package/dist/resolution/bridges/swift-objc.js.map +7 -0
- package/dist/resolution/bridges/turbomodules.js +216 -0
- package/dist/resolution/bridges/turbomodules.js.map +7 -0
- package/dist/resolution/index.js +61 -2
- package/dist/resolution/index.js.map +2 -2
- package/dist/security/attack-surface.js +164 -0
- package/dist/security/attack-surface.js.map +7 -0
- package/dist/security/context-warnings.js +123 -0
- package/dist/security/context-warnings.js.map +7 -0
- package/dist/security/context-warnings.test.js +300 -0
- package/dist/security/context-warnings.test.js.map +7 -0
- package/dist/security/data-flows.js +228 -0
- package/dist/security/data-flows.js.map +7 -0
- package/dist/security/dep-confusion.js +255 -0
- package/dist/security/dep-confusion.js.map +7 -0
- package/dist/security/errors.js +51 -0
- package/dist/security/errors.js.map +7 -0
- package/dist/security/export/fix-suggestions.js +58 -0
- package/dist/security/export/fix-suggestions.js.map +7 -0
- package/dist/security/export/fix-suggestions.test.js +74 -0
- package/dist/security/export/fix-suggestions.test.js.map +7 -0
- package/dist/security/export/sbom.js +230 -0
- package/dist/security/export/sbom.js.map +7 -0
- package/dist/security/export/sbom.test.js +288 -0
- package/dist/security/export/sbom.test.js.map +7 -0
- package/dist/security/export/serialization.js +142 -0
- package/dist/security/export/serialization.js.map +7 -0
- package/dist/security/export/serialization.test.js +310 -0
- package/dist/security/export/serialization.test.js.map +7 -0
- package/dist/security/export/vex.js +220 -0
- package/dist/security/export/vex.js.map +7 -0
- package/dist/security/export/vex.test.js +278 -0
- package/dist/security/export/vex.test.js.map +7 -0
- package/dist/security/index.js +67 -0
- package/dist/security/index.js.map +7 -0
- package/dist/security/integrator-transitives.test.js +359 -0
- package/dist/security/integrator-transitives.test.js.map +7 -0
- package/dist/security/integrator.js +491 -0
- package/dist/security/integrator.js.map +7 -0
- package/dist/security/integrator.test.js +237 -0
- package/dist/security/integrator.test.js.map +7 -0
- package/dist/security/license.js +70 -0
- package/dist/security/license.js.map +7 -0
- package/dist/security/manifest/adapter.js +243 -0
- package/dist/security/manifest/adapter.js.map +7 -0
- package/dist/security/manifest/adapter.test.js +272 -0
- package/dist/security/manifest/adapter.test.js.map +7 -0
- package/dist/security/manifest/parser.js +376 -0
- package/dist/security/manifest/parser.js.map +7 -0
- package/dist/security/manifest/parser.test.js +110 -0
- package/dist/security/manifest/parser.test.js.map +7 -0
- package/dist/security/manifest/plugins/cargo.js +233 -0
- package/dist/security/manifest/plugins/cargo.js.map +7 -0
- package/dist/security/manifest/plugins/cargo.test.js +304 -0
- package/dist/security/manifest/plugins/cargo.test.js.map +7 -0
- package/dist/security/manifest/plugins/composer.js +152 -0
- package/dist/security/manifest/plugins/composer.js.map +7 -0
- package/dist/security/manifest/plugins/go.js +146 -0
- package/dist/security/manifest/plugins/go.js.map +7 -0
- package/dist/security/manifest/plugins/go.test.js +341 -0
- package/dist/security/manifest/plugins/go.test.js.map +7 -0
- package/dist/security/manifest/plugins/gradle.js +159 -0
- package/dist/security/manifest/plugins/gradle.js.map +7 -0
- package/dist/security/manifest/plugins/hex.js +159 -0
- package/dist/security/manifest/plugins/hex.js.map +7 -0
- package/dist/security/manifest/plugins/maven.js +128 -0
- package/dist/security/manifest/plugins/maven.js.map +7 -0
- package/dist/security/manifest/plugins/maven.test.js +389 -0
- package/dist/security/manifest/plugins/maven.test.js.map +7 -0
- package/dist/security/manifest/plugins/npm.js +284 -0
- package/dist/security/manifest/plugins/npm.js.map +7 -0
- package/dist/security/manifest/plugins/npm.test.js +298 -0
- package/dist/security/manifest/plugins/npm.test.js.map +7 -0
- package/dist/security/manifest/plugins/nuget.js +186 -0
- package/dist/security/manifest/plugins/nuget.js.map +7 -0
- package/dist/security/manifest/plugins/pip.js +123 -0
- package/dist/security/manifest/plugins/pip.js.map +7 -0
- package/dist/security/manifest/plugins/pip.test.js +208 -0
- package/dist/security/manifest/plugins/pip.test.js.map +7 -0
- package/dist/security/manifest/plugins/pubspec.js +212 -0
- package/dist/security/manifest/plugins/pubspec.js.map +7 -0
- package/dist/security/manifest/plugins/pyproject.js +261 -0
- package/dist/security/manifest/plugins/pyproject.js.map +7 -0
- package/dist/security/manifest/plugins/rubygems.js +185 -0
- package/dist/security/manifest/plugins/rubygems.js.map +7 -0
- package/dist/security/manifest/plugins/swift.js +200 -0
- package/dist/security/manifest/plugins/swift.js.map +7 -0
- package/dist/security/owasp.js +104 -0
- package/dist/security/owasp.js.map +7 -0
- package/dist/security/pipeline.js +125 -0
- package/dist/security/pipeline.js.map +7 -0
- package/dist/security/reachability.js +276 -0
- package/dist/security/reachability.js.map +7 -0
- package/dist/security/reachability.test.js +394 -0
- package/dist/security/reachability.test.js.map +7 -0
- package/dist/security/remediation.js +126 -0
- package/dist/security/remediation.js.map +7 -0
- package/dist/security/secrets.js +176 -0
- package/dist/security/secrets.js.map +7 -0
- package/dist/security/staleness.js +231 -0
- package/dist/security/staleness.js.map +7 -0
- package/dist/security/supply-chain.js +301 -0
- package/dist/security/supply-chain.js.map +7 -0
- package/dist/security/suppressions.js +106 -0
- package/dist/security/suppressions.js.map +7 -0
- package/dist/security/types.js +17 -0
- package/dist/security/types.js.map +7 -0
- package/dist/security/vuln/client.js +355 -0
- package/dist/security/vuln/client.js.map +7 -0
- package/dist/security/vuln/client.test.js +288 -0
- package/dist/security/vuln/client.test.js.map +7 -0
- package/dist/security/vuln/epss-client.js +95 -0
- package/dist/security/vuln/epss-client.js.map +7 -0
- package/dist/security/vuln/index.js +29 -0
- package/dist/security/vuln/index.js.map +7 -0
- package/dist/security/vuln/osv-adapter.js +321 -0
- package/dist/security/vuln/osv-adapter.js.map +7 -0
- package/dist/security/vuln/osv-adapter.test.js +391 -0
- package/dist/security/vuln/osv-adapter.test.js.map +7 -0
- package/dist/security/vuln/types.js +17 -0
- package/dist/security/vuln/types.js.map +7 -0
- package/dist/types.js.map +2 -2
- package/package.json +2 -1
package/dist/bin/kirograph.js
CHANGED
|
@@ -34,6 +34,28 @@ var import_exec = require("./commands/exec");
|
|
|
34
34
|
var import_memory = require("./commands/memory");
|
|
35
35
|
var import_docs = require("./commands/docs");
|
|
36
36
|
var import_data = require("./commands/data");
|
|
37
|
+
var import_benchmark = require("./commands/benchmark");
|
|
38
|
+
var import_flows = require("./commands/flows");
|
|
39
|
+
var import_communities = require("./commands/communities");
|
|
40
|
+
var import_refactor = require("./commands/refactor");
|
|
41
|
+
var import_read = require("./commands/read");
|
|
42
|
+
var import_budget = require("./commands/budget");
|
|
43
|
+
var import_security = require("./commands/security");
|
|
44
|
+
var import_sbom = require("./commands/sbom");
|
|
45
|
+
var import_vex = require("./commands/vex");
|
|
46
|
+
var import_vulns = require("./commands/vulns");
|
|
47
|
+
var import_reachability = require("./commands/reachability");
|
|
48
|
+
var import_staleness = require("./commands/staleness");
|
|
49
|
+
var import_licenses = require("./commands/licenses");
|
|
50
|
+
var import_security_export = require("./commands/security-export");
|
|
51
|
+
var import_vuln_suppress = require("./commands/vuln-suppress");
|
|
52
|
+
var import_attack_surface = require("./commands/attack-surface");
|
|
53
|
+
var import_security_secrets = require("./commands/security-secrets");
|
|
54
|
+
var import_security_flows = require("./commands/security-flows");
|
|
55
|
+
var import_security_ci_report = require("./commands/security-ci-report");
|
|
56
|
+
var import_supply_chain = require("./commands/supply-chain");
|
|
57
|
+
var import_dep_confusion = require("./commands/dep-confusion");
|
|
58
|
+
var import_remediation = require("./commands/remediation");
|
|
37
59
|
process.on("uncaughtException", (err) => {
|
|
38
60
|
const msg = err?.message ?? String(err);
|
|
39
61
|
const isWasmAbort = msg.includes("Aborted(") || msg.includes("RuntimeError") || err?.constructor?.name === "RuntimeError";
|
|
@@ -62,7 +84,7 @@ process.on("uncaughtException", (err) => {
|
|
|
62
84
|
process.exit(1);
|
|
63
85
|
});
|
|
64
86
|
const program = new import_commander.Command();
|
|
65
|
-
program.name("kirograph").description("Semantic code knowledge graph for Kiro").version("0.
|
|
87
|
+
program.name("kirograph").description("Semantic code knowledge graph for Kiro").version("0.19.0").addHelpCommand(true).hook("preAction", (thisCommand) => {
|
|
66
88
|
const name = thisCommand.name();
|
|
67
89
|
if (name === "init") (0, import_banner.printBanner)();
|
|
68
90
|
});
|
|
@@ -97,11 +119,55 @@ program.name("kirograph").description("Semantic code knowledge graph for Kiro").
|
|
|
97
119
|
(0, import_memory.register)(program);
|
|
98
120
|
(0, import_docs.register)(program);
|
|
99
121
|
(0, import_data.register)(program);
|
|
122
|
+
(0, import_benchmark.register)(program);
|
|
123
|
+
(0, import_flows.register)(program);
|
|
124
|
+
(0, import_communities.register)(program);
|
|
125
|
+
(0, import_refactor.register)(program);
|
|
126
|
+
(0, import_read.register)(program);
|
|
127
|
+
(0, import_budget.register)(program);
|
|
128
|
+
const securityCmd = (0, import_security.register)(program);
|
|
129
|
+
(0, import_sbom.register)(program);
|
|
130
|
+
(0, import_vex.register)(program);
|
|
131
|
+
(0, import_vulns.register)(program);
|
|
132
|
+
(0, import_reachability.register)(program);
|
|
133
|
+
(0, import_staleness.register)(program);
|
|
134
|
+
(0, import_licenses.register)(program);
|
|
135
|
+
(0, import_security_export.register)(securityCmd);
|
|
136
|
+
(0, import_security_secrets.register)(securityCmd);
|
|
137
|
+
(0, import_security_flows.register)(securityCmd);
|
|
138
|
+
(0, import_security_ci_report.register)(securityCmd);
|
|
139
|
+
(0, import_vuln_suppress.register)(program);
|
|
140
|
+
(0, import_attack_surface.register)(program);
|
|
141
|
+
(0, import_supply_chain.register)(program);
|
|
142
|
+
(0, import_dep_confusion.register)(program);
|
|
143
|
+
(0, import_remediation.register)(program);
|
|
144
|
+
program.command("help").description("Show interactive help").action(() => {
|
|
145
|
+
if (process.stdout.isTTY) {
|
|
146
|
+
(0, import_help.printInteractiveHelp)();
|
|
147
|
+
} else {
|
|
148
|
+
(0, import_banner.printBanner)();
|
|
149
|
+
(0, import_help.printColoredHelp)();
|
|
150
|
+
process.exit(0);
|
|
151
|
+
}
|
|
152
|
+
});
|
|
153
|
+
(0, import_help.register)(program);
|
|
100
154
|
if (process.argv.length === 2) {
|
|
101
|
-
(
|
|
102
|
-
|
|
103
|
-
|
|
155
|
+
if (process.stdout.isTTY) {
|
|
156
|
+
(0, import_help.printInteractiveHelp)();
|
|
157
|
+
} else {
|
|
158
|
+
(0, import_banner.printBanner)();
|
|
159
|
+
(0, import_help.printColoredHelp)();
|
|
160
|
+
process.exit(0);
|
|
161
|
+
}
|
|
162
|
+
} else if (process.argv.includes("--help") || process.argv.includes("-h")) {
|
|
163
|
+
if (process.stdout.isTTY) {
|
|
164
|
+
(0, import_help.printInteractiveHelp)();
|
|
165
|
+
} else {
|
|
166
|
+
(0, import_banner.printBanner)();
|
|
167
|
+
(0, import_help.printColoredHelp)();
|
|
168
|
+
process.exit(0);
|
|
169
|
+
}
|
|
170
|
+
} else {
|
|
171
|
+
program.parse(process.argv);
|
|
104
172
|
}
|
|
105
|
-
(0, import_help.register)(program);
|
|
106
|
-
program.parse(process.argv);
|
|
107
173
|
//# sourceMappingURL=kirograph.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../src/bin/kirograph.ts"],
|
|
4
|
-
"sourcesContent": ["#!/usr/bin/env node\n/**\n * KiroGraph CLI\n */\n\nimport { Command } from 'commander';\nimport { printBanner } from './banner';\nimport { printColoredHelp, register as registerHelp } from './commands/help';\nimport { register as registerInit } from './commands/init';\nimport { register as registerUninit } from './commands/uninit';\nimport { register as registerIndex } from './commands/index';\nimport { register as registerSync } from './commands/sync';\nimport { register as registerStatus } from './commands/status';\nimport { register as registerQuery } from './commands/query';\nimport { register as registerFiles } from './commands/files';\nimport { register as registerContext } from './commands/context';\nimport { register as registerAffected } from './commands/affected';\nimport { register as registerMarkDirty } from './commands/mark-dirty';\nimport { register as registerSyncIfDirty } from './commands/sync-if-dirty';\nimport { register as registerUnlock } from './commands/unlock';\nimport { register as registerInstall } from './commands/install';\nimport { register as registerServe } from './commands/serve';\nimport { register as registerDashboard } from './commands/dashboard';\nimport { register as registerArchitecture } from './commands/architecture';\nimport { register as registerCoupling } from './commands/coupling';\nimport { register as registerPackage } from './commands/package';\nimport { register as registerCaveman } from './commands/caveman';\nimport { register as registerDeadCode } from './commands/dead-code';\nimport { register as registerHotspots } from './commands/hotspots';\nimport { register as registerSurprising } from './commands/surprising';\nimport { register as registerSnapshot } from './commands/snapshot';\nimport { register as registerPath } from './commands/path';\nimport { register as registerExport } from './commands/export';\nimport { register as registerGain } from './commands/gain';\nimport { register as registerCompression } from './commands/compression';\nimport { register as registerExec } from './commands/exec';\nimport { register as registerMemory } from './commands/memory';\nimport { register as registerDocs } from './commands/docs';\nimport { register as registerData } from './commands/data';\n\n// \u2500\u2500 Global error handler for WASM runtime crashes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n//\n// node-sqlite3-wasm calls process.abort() when it hits a fatal error (e.g.\n// database is locked by another process). This produces a raw \"Aborted()\"\n// message with no context. We intercept it here to print a clear explanation\n// before the process exits.\nprocess.on('uncaughtException', (err: Error) => {\n const msg = err?.message ?? String(err);\n const isWasmAbort = msg.includes('Aborted(') || msg.includes('RuntimeError') || (err as any)?.constructor?.name === 'RuntimeError';\n\n if (isWasmAbort) {\n process.stderr.write([\n '',\n ' \u2716 KiroGraph crashed: SQLite WASM runtime aborted.',\n '',\n ' Most likely cause: another process (e.g. the Kiro MCP server) is',\n ' holding the database open while indexing is running.',\n '',\n ' How to fix:',\n ' 1. Close Kiro IDE (or disable the kirograph MCP server) before indexing',\n ' 2. Run: kirograph unlock',\n ' 3. Then retry: kirograph index',\n '',\n ' If the problem persists, delete the lock manually:',\n ' del .kirograph\\\\kirograph.db.lock (Windows)',\n ' rm -rf .kirograph/kirograph.db.lock (macOS/Linux)',\n '',\n ].join('\\n'));\n process.exit(1);\n }\n\n // Not a WASM crash \u2014 re-throw as normal\n process.stderr.write(`Uncaught error: ${msg}\\n`);\n process.exit(1);\n});\n\ndeclare const __CLI_VERSION__: string;\n\nconst program = new Command();\n\nprogram\n .name('kirograph')\n .description('Semantic code knowledge graph for Kiro')\n .version(__CLI_VERSION__)\n .addHelpCommand(true)\n .hook('preAction', (thisCommand) => {\n const name = thisCommand.name();\n if (name === 'init') printBanner();\n });\n\nregisterInstall(program);\nregisterInit(program);\nregisterUninit(program);\nregisterIndex(program);\nregisterSync(program);\nregisterSyncIfDirty(program);\nregisterMarkDirty(program);\nregisterStatus(program);\nregisterQuery(program);\nregisterContext(program);\nregisterFiles(program);\nregisterAffected(program);\nregisterUnlock(program);\nregisterServe(program);\nregisterDashboard(program);\nregisterArchitecture(program);\nregisterCoupling(program);\nregisterPackage(program);\nregisterCaveman(program);\nregisterDeadCode(program);\nregisterHotspots(program);\nregisterSurprising(program);\nregisterSnapshot(program);\nregisterPath(program);\nregisterExport(program);\nregisterGain(program);\nregisterCompression(program);\nregisterExec(program);\nregisterMemory(program);\nregisterDocs(program);\nregisterData(program);\n\n// Show
|
|
5
|
-
"mappings": ";;AAKA,uBAAwB;AACxB,oBAA4B;AAC5B,
|
|
6
|
-
"names": ["registerInstall", "registerInit", "registerUninit", "registerIndex", "registerSync", "registerSyncIfDirty", "registerMarkDirty", "registerStatus", "registerQuery", "registerContext", "registerFiles", "registerAffected", "registerUnlock", "registerServe", "registerDashboard", "registerArchitecture", "registerCoupling", "registerPackage", "registerCaveman", "registerDeadCode", "registerHotspots", "registerSurprising", "registerSnapshot", "registerPath", "registerExport", "registerGain", "registerCompression", "registerExec", "registerMemory", "registerDocs", "registerData", "registerHelp"]
|
|
4
|
+
"sourcesContent": ["#!/usr/bin/env node\n/**\n * KiroGraph CLI\n */\n\nimport { Command } from 'commander';\nimport { printBanner } from './banner';\nimport { printColoredHelp, printInteractiveHelp, register as registerHelp } from './commands/help';\nimport { register as registerInit } from './commands/init';\nimport { register as registerUninit } from './commands/uninit';\nimport { register as registerIndex } from './commands/index';\nimport { register as registerSync } from './commands/sync';\nimport { register as registerStatus } from './commands/status';\nimport { register as registerQuery } from './commands/query';\nimport { register as registerFiles } from './commands/files';\nimport { register as registerContext } from './commands/context';\nimport { register as registerAffected } from './commands/affected';\nimport { register as registerMarkDirty } from './commands/mark-dirty';\nimport { register as registerSyncIfDirty } from './commands/sync-if-dirty';\nimport { register as registerUnlock } from './commands/unlock';\nimport { register as registerInstall } from './commands/install';\nimport { register as registerServe } from './commands/serve';\nimport { register as registerDashboard } from './commands/dashboard';\nimport { register as registerArchitecture } from './commands/architecture';\nimport { register as registerCoupling } from './commands/coupling';\nimport { register as registerPackage } from './commands/package';\nimport { register as registerCaveman } from './commands/caveman';\nimport { register as registerDeadCode } from './commands/dead-code';\nimport { register as registerHotspots } from './commands/hotspots';\nimport { register as registerSurprising } from './commands/surprising';\nimport { register as registerSnapshot } from './commands/snapshot';\nimport { register as registerPath } from './commands/path';\nimport { register as registerExport } from './commands/export';\nimport { register as registerGain } from './commands/gain';\nimport { register as registerCompression } from './commands/compression';\nimport { register as registerExec } from './commands/exec';\nimport { register as registerMemory } from './commands/memory';\nimport { register as registerDocs } from './commands/docs';\nimport { register as registerData } from './commands/data';\nimport { register as registerBenchmark } from './commands/benchmark';\nimport { register as registerFlows } from './commands/flows';\nimport { register as registerCommunities } from './commands/communities';\nimport { register as registerRefactor } from './commands/refactor';\nimport { register as registerRead } from './commands/read';\nimport { register as registerBudget } from './commands/budget';\nimport { register as registerSecurity } from './commands/security';\nimport { register as registerSbom } from './commands/sbom';\nimport { register as registerVex } from './commands/vex';\nimport { register as registerVulns } from './commands/vulns';\nimport { register as registerReachability } from './commands/reachability';\nimport { register as registerStaleness } from './commands/staleness';\nimport { register as registerLicenses } from './commands/licenses';\nimport { register as registerSecurityExport } from './commands/security-export';\nimport { register as registerVulnSuppress } from './commands/vuln-suppress';\nimport { register as registerAttackSurface } from './commands/attack-surface';\nimport { register as registerSecuritySecrets } from './commands/security-secrets';\nimport { register as registerSecurityFlows } from './commands/security-flows';\nimport { register as registerSecurityCiReport } from './commands/security-ci-report';\nimport { register as registerSupplyChain } from './commands/supply-chain';\nimport { register as registerDepConfusion } from './commands/dep-confusion';\nimport { register as registerRemediation } from './commands/remediation';\n\n// \u2500\u2500 Global error handler for WASM runtime crashes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n//\n// node-sqlite3-wasm calls process.abort() when it hits a fatal error (e.g.\n// database is locked by another process). This produces a raw \"Aborted()\"\n// message with no context. We intercept it here to print a clear explanation\n// before the process exits.\nprocess.on('uncaughtException', (err: Error) => {\n const msg = err?.message ?? String(err);\n const isWasmAbort = msg.includes('Aborted(') || msg.includes('RuntimeError') || (err as any)?.constructor?.name === 'RuntimeError';\n\n if (isWasmAbort) {\n process.stderr.write([\n '',\n ' \u2716 KiroGraph crashed: SQLite WASM runtime aborted.',\n '',\n ' Most likely cause: another process (e.g. the Kiro MCP server) is',\n ' holding the database open while indexing is running.',\n '',\n ' How to fix:',\n ' 1. Close Kiro IDE (or disable the kirograph MCP server) before indexing',\n ' 2. Run: kirograph unlock',\n ' 3. Then retry: kirograph index',\n '',\n ' If the problem persists, delete the lock manually:',\n ' del .kirograph\\\\kirograph.db.lock (Windows)',\n ' rm -rf .kirograph/kirograph.db.lock (macOS/Linux)',\n '',\n ].join('\\n'));\n process.exit(1);\n }\n\n // Not a WASM crash \u2014 re-throw as normal\n process.stderr.write(`Uncaught error: ${msg}\\n`);\n process.exit(1);\n});\n\ndeclare const __CLI_VERSION__: string;\n\nconst program = new Command();\n\nprogram\n .name('kirograph')\n .description('Semantic code knowledge graph for Kiro')\n .version(__CLI_VERSION__)\n .addHelpCommand(true)\n .hook('preAction', (thisCommand) => {\n const name = thisCommand.name();\n if (name === 'init') printBanner();\n });\n\nregisterInstall(program);\nregisterInit(program);\nregisterUninit(program);\nregisterIndex(program);\nregisterSync(program);\nregisterSyncIfDirty(program);\nregisterMarkDirty(program);\nregisterStatus(program);\nregisterQuery(program);\nregisterContext(program);\nregisterFiles(program);\nregisterAffected(program);\nregisterUnlock(program);\nregisterServe(program);\nregisterDashboard(program);\nregisterArchitecture(program);\nregisterCoupling(program);\nregisterPackage(program);\nregisterCaveman(program);\nregisterDeadCode(program);\nregisterHotspots(program);\nregisterSurprising(program);\nregisterSnapshot(program);\nregisterPath(program);\nregisterExport(program);\nregisterGain(program);\nregisterCompression(program);\nregisterExec(program);\nregisterMemory(program);\nregisterDocs(program);\nregisterData(program);\nregisterBenchmark(program);\nregisterFlows(program);\nregisterCommunities(program);\nregisterRefactor(program);\nregisterRead(program);\nregisterBudget(program);\nconst securityCmd = registerSecurity(program);\nregisterSbom(program);\nregisterVex(program);\nregisterVulns(program);\nregisterReachability(program);\nregisterStaleness(program);\nregisterLicenses(program);\nregisterSecurityExport(securityCmd);\nregisterSecuritySecrets(securityCmd);\nregisterSecurityFlows(securityCmd);\nregisterSecurityCiReport(securityCmd);\nregisterVulnSuppress(program);\nregisterAttackSurface(program);\nregisterSupplyChain(program);\nregisterDepConfusion(program);\nregisterRemediation(program);\n\n// Register the help command for `kirograph help`\nprogram\n .command('help')\n .description('Show interactive help')\n .action(() => {\n if (process.stdout.isTTY) {\n printInteractiveHelp();\n } else {\n printBanner();\n printColoredHelp();\n process.exit(0);\n }\n });\n\nregisterHelp(program);\n\n// Show interactive help when called with no arguments\nif (process.argv.length === 2) {\n if (process.stdout.isTTY) {\n printInteractiveHelp();\n } else {\n printBanner();\n printColoredHelp();\n process.exit(0);\n }\n} else if (process.argv.includes('--help') || process.argv.includes('-h')) {\n // Intercept --help before Commander to avoid process.exit\n if (process.stdout.isTTY) {\n printInteractiveHelp();\n } else {\n printBanner();\n printColoredHelp();\n process.exit(0);\n }\n} else {\n program.parse(process.argv);\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["registerInstall", "registerInit", "registerUninit", "registerIndex", "registerSync", "registerSyncIfDirty", "registerMarkDirty", "registerStatus", "registerQuery", "registerContext", "registerFiles", "registerAffected", "registerUnlock", "registerServe", "registerDashboard", "registerArchitecture", "registerCoupling", "registerPackage", "registerCaveman", "registerDeadCode", "registerHotspots", "registerSurprising", "registerSnapshot", "registerPath", "registerExport", "registerGain", "registerCompression", "registerExec", "registerMemory", "registerDocs", "registerData", "registerBenchmark", "registerFlows", "registerCommunities", "registerRefactor", "registerRead", "registerBudget", "registerSecurity", "registerSbom", "registerVex", "registerVulns", "registerReachability", "registerStaleness", "registerLicenses", "registerSecurityExport", "registerSecuritySecrets", "registerSecurityFlows", "registerSecurityCiReport", "registerVulnSuppress", "registerAttackSurface", "registerSupplyChain", "registerDepConfusion", "registerRemediation", "registerHelp"]
|
|
7
7
|
}
|
|
@@ -28,6 +28,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
28
28
|
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
29
29
|
var tracker_exports = {};
|
|
30
30
|
__export(tracker_exports, {
|
|
31
|
+
BudgetTracker: () => BudgetTracker,
|
|
31
32
|
TokenTracker: () => TokenTracker
|
|
32
33
|
});
|
|
33
34
|
module.exports = __toCommonJS(tracker_exports);
|
|
@@ -253,8 +254,87 @@ class TokenTracker {
|
|
|
253
254
|
}
|
|
254
255
|
}
|
|
255
256
|
}
|
|
257
|
+
const DEFAULT_BUDGET = {
|
|
258
|
+
maxTokensPerSession: 1e5,
|
|
259
|
+
warnAt: 8e4,
|
|
260
|
+
throttleAt: 95e3
|
|
261
|
+
};
|
|
262
|
+
class BudgetTracker {
|
|
263
|
+
constructor(projectRoot, config) {
|
|
264
|
+
this.consumed = 0;
|
|
265
|
+
this.projectRoot = projectRoot;
|
|
266
|
+
this.config = { ...DEFAULT_BUDGET, ...config };
|
|
267
|
+
}
|
|
268
|
+
static {
|
|
269
|
+
this.instances = /* @__PURE__ */ new Map();
|
|
270
|
+
}
|
|
271
|
+
static getInstance(projectRoot, config) {
|
|
272
|
+
const key = projectRoot;
|
|
273
|
+
if (!BudgetTracker.instances.has(key)) {
|
|
274
|
+
BudgetTracker.instances.set(key, new BudgetTracker(projectRoot, config));
|
|
275
|
+
}
|
|
276
|
+
const instance = BudgetTracker.instances.get(key);
|
|
277
|
+
if (config) {
|
|
278
|
+
instance.config = { ...DEFAULT_BUDGET, ...config };
|
|
279
|
+
}
|
|
280
|
+
return instance;
|
|
281
|
+
}
|
|
282
|
+
/**
|
|
283
|
+
* Record tokens consumed by a tool response.
|
|
284
|
+
*/
|
|
285
|
+
recordConsumption(tokens) {
|
|
286
|
+
this.consumed += tokens;
|
|
287
|
+
}
|
|
288
|
+
/**
|
|
289
|
+
* Get current budget status.
|
|
290
|
+
*/
|
|
291
|
+
getStatus() {
|
|
292
|
+
const limit = this.config.maxTokensPerSession;
|
|
293
|
+
const remaining = Math.max(0, limit - this.consumed);
|
|
294
|
+
const utilization = limit > 0 ? Math.round(this.consumed / limit * 100) : 0;
|
|
295
|
+
let warning = null;
|
|
296
|
+
if (limit > 0 && this.consumed >= this.config.throttleAt) {
|
|
297
|
+
warning = `Budget nearly exhausted (${utilization}%). Responses will be truncated.`;
|
|
298
|
+
} else if (limit > 0 && this.consumed >= this.config.warnAt) {
|
|
299
|
+
warning = `Approaching budget limit (${utilization}%). Consider using compact read modes.`;
|
|
300
|
+
}
|
|
301
|
+
return {
|
|
302
|
+
consumed: this.consumed,
|
|
303
|
+
limit,
|
|
304
|
+
remaining,
|
|
305
|
+
utilization,
|
|
306
|
+
warning,
|
|
307
|
+
throttled: limit > 0 && this.consumed >= this.config.throttleAt
|
|
308
|
+
};
|
|
309
|
+
}
|
|
310
|
+
/**
|
|
311
|
+
* Check if the budget is throttled (responses should be truncated).
|
|
312
|
+
*/
|
|
313
|
+
isThrottled() {
|
|
314
|
+
return this.config.maxTokensPerSession > 0 && this.consumed >= this.config.throttleAt;
|
|
315
|
+
}
|
|
316
|
+
/**
|
|
317
|
+
* Check if a warning should be appended to responses.
|
|
318
|
+
*/
|
|
319
|
+
shouldWarn() {
|
|
320
|
+
return this.config.maxTokensPerSession > 0 && this.consumed >= this.config.warnAt;
|
|
321
|
+
}
|
|
322
|
+
/**
|
|
323
|
+
* Reset the budget counters.
|
|
324
|
+
*/
|
|
325
|
+
reset() {
|
|
326
|
+
this.consumed = 0;
|
|
327
|
+
}
|
|
328
|
+
/**
|
|
329
|
+
* Update budget configuration.
|
|
330
|
+
*/
|
|
331
|
+
updateConfig(config) {
|
|
332
|
+
this.config = { ...this.config, ...config };
|
|
333
|
+
}
|
|
334
|
+
}
|
|
256
335
|
// Annotate the CommonJS export names for ESM import in node:
|
|
257
336
|
0 && (module.exports = {
|
|
337
|
+
BudgetTracker,
|
|
258
338
|
TokenTracker
|
|
259
339
|
});
|
|
260
340
|
//# sourceMappingURL=tracker.js.map
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
3
|
"sources": ["../../src/compression/tracker.ts"],
|
|
4
|
-
"sourcesContent": ["/**\n * KiroGraph Token Savings Tracker\n *\n * Records compression results to a local JSON file for analytics.\n * Uses a simple append-only JSON lines file to avoid SQLite dependency\n * in the compression module (keeps it lightweight and independent).\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport * as crypto from 'crypto';\nimport type { TokenSavingsRecord } from './types';\n\nconst TRACKER_DIR = '.kirograph';\nconst TRACKER_FILE = 'token-savings.jsonl';\nconst MAX_RECORDS = 5000; // Rotate after this many records\n\nexport interface GainStats {\n totalCommands: number;\n totalOriginal: number;\n totalCompressed: number;\n totalSaved: number;\n savingsPercent: number;\n byFamily: Record<string, { count: number; savings: number }>;\n recentCommands: Array<{ command: string; savings: number; timestamp: number; source?: string }>;\n /** Breakdown by source type */\n bySource: {\n exec: { count: number; saved: number };\n graph: { count: number; saved: number };\n memory: { count: number; saved: number };\n docs: { count: number; saved: number };\n data: { count: number; saved: number };\n };\n}\n\nexport class TokenTracker {\n private filePath: string;\n private sessionId: string;\n\n constructor(projectRoot: string) {\n const dir = path.join(projectRoot, TRACKER_DIR);\n fs.mkdirSync(dir, { recursive: true });\n this.filePath = path.join(dir, TRACKER_FILE);\n this.sessionId = this.getOrCreateSessionId(dir);\n }\n\n private getOrCreateSessionId(dir: string): string {\n const sessionFile = path.join(dir, '.session-id');\n try {\n const existing = fs.readFileSync(sessionFile, 'utf8').trim();\n if (existing) return existing;\n } catch { /* file doesn't exist */ }\n\n const id = crypto.randomBytes(8).toString('hex');\n try {\n fs.writeFileSync(sessionFile, id, 'utf8');\n } catch { /* ignore write errors */ }\n return id;\n }\n\n /**\n * Record a compression result.\n */\n record(command: string, originalTokens: number, compressedTokens: number, strategy: string, source: 'exec' | 'graph' | 'memory' | 'docs' | 'data' = 'exec'): void {\n const record: TokenSavingsRecord = {\n timestamp: Date.now(),\n command: command.slice(0, 200), // Truncate long commands\n originalTokens,\n compressedTokens,\n strategy,\n sessionId: this.sessionId,\n source,\n };\n\n try {\n fs.appendFileSync(this.filePath, JSON.stringify(record) + '\\n', 'utf8');\n this.maybeRotate();\n } catch {\n // Non-critical \u2014 don't crash on tracking failure\n }\n }\n\n /**\n * Record a graph tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without the tool\n */\n recordGraphSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `graph:${toolName}`, 'graph');\n }\n\n /**\n * Record a memory tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without memory\n */\n recordMemorySaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `memory:${toolName}`, 'memory');\n }\n\n /**\n * Record a docs tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without docs indexing\n */\n recordDocsSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `docs:${toolName}`, 'docs');\n }\n\n /**\n * Record a data tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without data indexing\n */\n recordDataSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `data:${toolName}`, 'data');\n }\n\n /**\n * Get aggregated statistics for a time period.\n */\n getStats(period: 'session' | 'today' | 'week' | 'all'): GainStats {\n const records = this.loadRecords(period);\n\n if (records.length === 0) {\n return {\n totalCommands: 0,\n totalOriginal: 0,\n totalCompressed: 0,\n totalSaved: 0,\n savingsPercent: 0,\n byFamily: {},\n recentCommands: [],\n bySource: { exec: { count: 0, saved: 0 }, graph: { count: 0, saved: 0 }, memory: { count: 0, saved: 0 }, docs: { count: 0, saved: 0 }, data: { count: 0, saved: 0 } },\n };\n }\n\n let totalOriginal = 0;\n let totalCompressed = 0;\n const byFamily = new Map<string, { count: number; totalOriginal: number; totalCompressed: number }>();\n const bySource = { exec: { count: 0, saved: 0 }, graph: { count: 0, saved: 0 }, memory: { count: 0, saved: 0 }, docs: { count: 0, saved: 0 }, data: { count: 0, saved: 0 } };\n\n for (const r of records) {\n totalOriginal += r.originalTokens;\n totalCompressed += r.compressedTokens;\n\n const family = this.extractFamily(r.strategy);\n const existing = byFamily.get(family) || { count: 0, totalOriginal: 0, totalCompressed: 0 };\n existing.count++;\n existing.totalOriginal += r.originalTokens;\n existing.totalCompressed += r.compressedTokens;\n byFamily.set(family, existing);\n\n const source = (r.source || 'exec') as 'exec' | 'graph' | 'memory' | 'docs' | 'data';\n if (bySource[source]) {\n bySource[source].count++;\n bySource[source].saved += r.originalTokens - r.compressedTokens;\n } else {\n bySource.exec.count++;\n bySource.exec.saved += r.originalTokens - r.compressedTokens;\n }\n }\n\n const totalSaved = totalOriginal - totalCompressed;\n const savingsPercent = totalOriginal > 0 ? Math.round((totalSaved / totalOriginal) * 100) : 0;\n\n // Convert byFamily map to sorted object\n const byFamilyObj: Record<string, { count: number; savings: number }> = {};\n const sortedFamilies = [...byFamily.entries()].sort((a, b) => b[1].count - a[1].count);\n for (const [family, data] of sortedFamilies) {\n const familySaved = data.totalOriginal - data.totalCompressed;\n const familyPercent = data.totalOriginal > 0 ? Math.round((familySaved / data.totalOriginal) * 100) : 0;\n byFamilyObj[family] = { count: data.count, savings: familyPercent };\n }\n\n // Recent commands (last 10)\n const recentCommands = records.slice(-10).reverse().map(r => ({\n command: r.command,\n savings: r.originalTokens > 0\n ? Math.round(((r.originalTokens - r.compressedTokens) / r.originalTokens) * 100)\n : 0,\n timestamp: r.timestamp,\n source: r.source,\n }));\n\n return {\n totalCommands: records.length,\n totalOriginal,\n totalCompressed,\n totalSaved,\n savingsPercent,\n byFamily: byFamilyObj,\n recentCommands,\n bySource,\n };\n }\n\n /**\n * Get raw history for CLI display.\n */\n getHistory(limit: number = 20): TokenSavingsRecord[] {\n const records = this.loadRecords('all');\n return records.slice(-limit).reverse();\n }\n\n /**\n * Get daily breakdown for graph display.\n */\n getDailyBreakdown(days: number = 30): Array<{ date: string; commands: number; saved: number }> {\n const records = this.loadRecords('all');\n const now = Date.now();\n const cutoff = now - days * 24 * 60 * 60 * 1000;\n\n const byDay = new Map<string, { commands: number; saved: number }>();\n\n for (const r of records) {\n if (r.timestamp < cutoff) continue;\n const date = new Date(r.timestamp).toISOString().slice(0, 10);\n const existing = byDay.get(date) || { commands: 0, saved: 0 };\n existing.commands++;\n existing.saved += r.originalTokens - r.compressedTokens;\n byDay.set(date, existing);\n }\n\n return [...byDay.entries()]\n .sort((a, b) => a[0].localeCompare(b[0]))\n .map(([date, data]) => ({ date, ...data }));\n }\n\n // \u2500\u2500 Private \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n private loadRecords(period: 'session' | 'today' | 'week' | 'all'): TokenSavingsRecord[] {\n if (!fs.existsSync(this.filePath)) return [];\n\n let lines: string[];\n try {\n lines = fs.readFileSync(this.filePath, 'utf8').split('\\n').filter(l => l.trim());\n } catch {\n return [];\n }\n\n const records: TokenSavingsRecord[] = [];\n for (const line of lines) {\n try {\n records.push(JSON.parse(line));\n } catch {\n // Skip malformed lines\n }\n }\n\n // Filter by period\n const now = Date.now();\n switch (period) {\n case 'session':\n return records.filter(r => r.sessionId === this.sessionId);\n case 'today': {\n const startOfDay = new Date();\n startOfDay.setHours(0, 0, 0, 0);\n return records.filter(r => r.timestamp >= startOfDay.getTime());\n }\n case 'week':\n return records.filter(r => r.timestamp >= now - 7 * 24 * 60 * 60 * 1000);\n case 'all':\n return records;\n }\n }\n\n private extractFamily(strategy: string): string {\n // \"git:status:ultra\" \u2192 \"git\"\n // \"jest:failures\" \u2192 \"jest\"\n const colon = strategy.indexOf(':');\n return colon > 0 ? strategy.slice(0, colon) : strategy;\n }\n\n private maybeRotate(): void {\n try {\n const stat = fs.statSync(this.filePath);\n // Rotate if file exceeds ~500KB\n if (stat.size > 500 * 1024) {\n const lines = fs.readFileSync(this.filePath, 'utf8').split('\\n').filter(l => l.trim());\n if (lines.length > MAX_RECORDS) {\n // Keep last half\n const keep = lines.slice(-Math.floor(MAX_RECORDS / 2));\n fs.writeFileSync(this.filePath, keep.join('\\n') + '\\n', 'utf8');\n }\n }\n } catch {\n // Non-critical\n }\n }\n}\n"],
|
|
5
|
-
"mappings": "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",
|
|
4
|
+
"sourcesContent": ["/**\n * KiroGraph Token Savings Tracker\n *\n * Records compression results to a local JSON file for analytics.\n * Uses a simple append-only JSON lines file to avoid SQLite dependency\n * in the compression module (keeps it lightweight and independent).\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport * as crypto from 'crypto';\nimport type { TokenSavingsRecord } from './types';\n\nconst TRACKER_DIR = '.kirograph';\nconst TRACKER_FILE = 'token-savings.jsonl';\nconst MAX_RECORDS = 5000; // Rotate after this many records\n\nexport interface GainStats {\n totalCommands: number;\n totalOriginal: number;\n totalCompressed: number;\n totalSaved: number;\n savingsPercent: number;\n byFamily: Record<string, { count: number; savings: number }>;\n recentCommands: Array<{ command: string; savings: number; timestamp: number; source?: string }>;\n /** Breakdown by source type */\n bySource: {\n exec: { count: number; saved: number };\n graph: { count: number; saved: number };\n memory: { count: number; saved: number };\n docs: { count: number; saved: number };\n data: { count: number; saved: number };\n };\n}\n\nexport class TokenTracker {\n private filePath: string;\n private sessionId: string;\n\n constructor(projectRoot: string) {\n const dir = path.join(projectRoot, TRACKER_DIR);\n fs.mkdirSync(dir, { recursive: true });\n this.filePath = path.join(dir, TRACKER_FILE);\n this.sessionId = this.getOrCreateSessionId(dir);\n }\n\n private getOrCreateSessionId(dir: string): string {\n const sessionFile = path.join(dir, '.session-id');\n try {\n const existing = fs.readFileSync(sessionFile, 'utf8').trim();\n if (existing) return existing;\n } catch { /* file doesn't exist */ }\n\n const id = crypto.randomBytes(8).toString('hex');\n try {\n fs.writeFileSync(sessionFile, id, 'utf8');\n } catch { /* ignore write errors */ }\n return id;\n }\n\n /**\n * Record a compression result.\n */\n record(command: string, originalTokens: number, compressedTokens: number, strategy: string, source: 'exec' | 'graph' | 'memory' | 'docs' | 'data' = 'exec'): void {\n const record: TokenSavingsRecord = {\n timestamp: Date.now(),\n command: command.slice(0, 200), // Truncate long commands\n originalTokens,\n compressedTokens,\n strategy,\n sessionId: this.sessionId,\n source,\n };\n\n try {\n fs.appendFileSync(this.filePath, JSON.stringify(record) + '\\n', 'utf8');\n this.maybeRotate();\n } catch {\n // Non-critical \u2014 don't crash on tracking failure\n }\n }\n\n /**\n * Record a graph tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without the tool\n */\n recordGraphSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `graph:${toolName}`, 'graph');\n }\n\n /**\n * Record a memory tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without memory\n */\n recordMemorySaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `memory:${toolName}`, 'memory');\n }\n\n /**\n * Record a docs tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without docs indexing\n */\n recordDocsSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `docs:${toolName}`, 'docs');\n }\n\n /**\n * Record a data tool saving.\n * @param toolName - The MCP tool that was called\n * @param outputTokens - Actual tokens returned by the tool\n * @param naiveCost - Estimated tokens the agent would have used without data indexing\n */\n recordDataSaving(toolName: string, outputTokens: number, naiveCost: number): void {\n this.record(toolName, naiveCost, outputTokens, `data:${toolName}`, 'data');\n }\n\n /**\n * Get aggregated statistics for a time period.\n */\n getStats(period: 'session' | 'today' | 'week' | 'all'): GainStats {\n const records = this.loadRecords(period);\n\n if (records.length === 0) {\n return {\n totalCommands: 0,\n totalOriginal: 0,\n totalCompressed: 0,\n totalSaved: 0,\n savingsPercent: 0,\n byFamily: {},\n recentCommands: [],\n bySource: { exec: { count: 0, saved: 0 }, graph: { count: 0, saved: 0 }, memory: { count: 0, saved: 0 }, docs: { count: 0, saved: 0 }, data: { count: 0, saved: 0 } },\n };\n }\n\n let totalOriginal = 0;\n let totalCompressed = 0;\n const byFamily = new Map<string, { count: number; totalOriginal: number; totalCompressed: number }>();\n const bySource = { exec: { count: 0, saved: 0 }, graph: { count: 0, saved: 0 }, memory: { count: 0, saved: 0 }, docs: { count: 0, saved: 0 }, data: { count: 0, saved: 0 } };\n\n for (const r of records) {\n totalOriginal += r.originalTokens;\n totalCompressed += r.compressedTokens;\n\n const family = this.extractFamily(r.strategy);\n const existing = byFamily.get(family) || { count: 0, totalOriginal: 0, totalCompressed: 0 };\n existing.count++;\n existing.totalOriginal += r.originalTokens;\n existing.totalCompressed += r.compressedTokens;\n byFamily.set(family, existing);\n\n const source = (r.source || 'exec') as 'exec' | 'graph' | 'memory' | 'docs' | 'data';\n if (bySource[source]) {\n bySource[source].count++;\n bySource[source].saved += r.originalTokens - r.compressedTokens;\n } else {\n bySource.exec.count++;\n bySource.exec.saved += r.originalTokens - r.compressedTokens;\n }\n }\n\n const totalSaved = totalOriginal - totalCompressed;\n const savingsPercent = totalOriginal > 0 ? Math.round((totalSaved / totalOriginal) * 100) : 0;\n\n // Convert byFamily map to sorted object\n const byFamilyObj: Record<string, { count: number; savings: number }> = {};\n const sortedFamilies = [...byFamily.entries()].sort((a, b) => b[1].count - a[1].count);\n for (const [family, data] of sortedFamilies) {\n const familySaved = data.totalOriginal - data.totalCompressed;\n const familyPercent = data.totalOriginal > 0 ? Math.round((familySaved / data.totalOriginal) * 100) : 0;\n byFamilyObj[family] = { count: data.count, savings: familyPercent };\n }\n\n // Recent commands (last 10)\n const recentCommands = records.slice(-10).reverse().map(r => ({\n command: r.command,\n savings: r.originalTokens > 0\n ? Math.round(((r.originalTokens - r.compressedTokens) / r.originalTokens) * 100)\n : 0,\n timestamp: r.timestamp,\n source: r.source,\n }));\n\n return {\n totalCommands: records.length,\n totalOriginal,\n totalCompressed,\n totalSaved,\n savingsPercent,\n byFamily: byFamilyObj,\n recentCommands,\n bySource,\n };\n }\n\n /**\n * Get raw history for CLI display.\n */\n getHistory(limit: number = 20): TokenSavingsRecord[] {\n const records = this.loadRecords('all');\n return records.slice(-limit).reverse();\n }\n\n /**\n * Get daily breakdown for graph display.\n */\n getDailyBreakdown(days: number = 30): Array<{ date: string; commands: number; saved: number }> {\n const records = this.loadRecords('all');\n const now = Date.now();\n const cutoff = now - days * 24 * 60 * 60 * 1000;\n\n const byDay = new Map<string, { commands: number; saved: number }>();\n\n for (const r of records) {\n if (r.timestamp < cutoff) continue;\n const date = new Date(r.timestamp).toISOString().slice(0, 10);\n const existing = byDay.get(date) || { commands: 0, saved: 0 };\n existing.commands++;\n existing.saved += r.originalTokens - r.compressedTokens;\n byDay.set(date, existing);\n }\n\n return [...byDay.entries()]\n .sort((a, b) => a[0].localeCompare(b[0]))\n .map(([date, data]) => ({ date, ...data }));\n }\n\n // \u2500\u2500 Private \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\n private loadRecords(period: 'session' | 'today' | 'week' | 'all'): TokenSavingsRecord[] {\n if (!fs.existsSync(this.filePath)) return [];\n\n let lines: string[];\n try {\n lines = fs.readFileSync(this.filePath, 'utf8').split('\\n').filter(l => l.trim());\n } catch {\n return [];\n }\n\n const records: TokenSavingsRecord[] = [];\n for (const line of lines) {\n try {\n records.push(JSON.parse(line));\n } catch {\n // Skip malformed lines\n }\n }\n\n // Filter by period\n const now = Date.now();\n switch (period) {\n case 'session':\n return records.filter(r => r.sessionId === this.sessionId);\n case 'today': {\n const startOfDay = new Date();\n startOfDay.setHours(0, 0, 0, 0);\n return records.filter(r => r.timestamp >= startOfDay.getTime());\n }\n case 'week':\n return records.filter(r => r.timestamp >= now - 7 * 24 * 60 * 60 * 1000);\n case 'all':\n return records;\n }\n }\n\n private extractFamily(strategy: string): string {\n // \"git:status:ultra\" \u2192 \"git\"\n // \"jest:failures\" \u2192 \"jest\"\n const colon = strategy.indexOf(':');\n return colon > 0 ? strategy.slice(0, colon) : strategy;\n }\n\n private maybeRotate(): void {\n try {\n const stat = fs.statSync(this.filePath);\n // Rotate if file exceeds ~500KB\n if (stat.size > 500 * 1024) {\n const lines = fs.readFileSync(this.filePath, 'utf8').split('\\n').filter(l => l.trim());\n if (lines.length > MAX_RECORDS) {\n // Keep last half\n const keep = lines.slice(-Math.floor(MAX_RECORDS / 2));\n fs.writeFileSync(this.filePath, keep.join('\\n') + '\\n', 'utf8');\n }\n }\n } catch {\n // Non-critical\n }\n }\n}\n\n\n// \u2500\u2500 Context Budget Governance \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport interface BudgetConfig {\n maxTokensPerSession: number;\n warnAt: number;\n throttleAt: number;\n}\n\nexport interface BudgetStatus {\n consumed: number;\n limit: number;\n remaining: number;\n utilization: number;\n warning: string | null;\n throttled: boolean;\n}\n\nconst DEFAULT_BUDGET: BudgetConfig = {\n maxTokensPerSession: 100_000,\n warnAt: 80_000,\n throttleAt: 95_000,\n};\n\n/**\n * Session-scoped context budget tracker.\n * Tracks cumulative token consumption and enforces budget limits.\n */\nexport class BudgetTracker {\n private static instances = new Map<string, BudgetTracker>();\n\n private consumed = 0;\n private config: BudgetConfig;\n private projectRoot: string;\n\n private constructor(projectRoot: string, config?: Partial<BudgetConfig>) {\n this.projectRoot = projectRoot;\n this.config = { ...DEFAULT_BUDGET, ...config };\n }\n\n static getInstance(projectRoot: string, config?: Partial<BudgetConfig>): BudgetTracker {\n const key = projectRoot;\n if (!BudgetTracker.instances.has(key)) {\n BudgetTracker.instances.set(key, new BudgetTracker(projectRoot, config));\n }\n const instance = BudgetTracker.instances.get(key)!;\n if (config) {\n instance.config = { ...DEFAULT_BUDGET, ...config };\n }\n return instance;\n }\n\n /**\n * Record tokens consumed by a tool response.\n */\n recordConsumption(tokens: number): void {\n this.consumed += tokens;\n }\n\n /**\n * Get current budget status.\n */\n getStatus(): BudgetStatus {\n const limit = this.config.maxTokensPerSession;\n const remaining = Math.max(0, limit - this.consumed);\n const utilization = limit > 0 ? Math.round((this.consumed / limit) * 100) : 0;\n\n let warning: string | null = null;\n if (limit > 0 && this.consumed >= this.config.throttleAt) {\n warning = `Budget nearly exhausted (${utilization}%). Responses will be truncated.`;\n } else if (limit > 0 && this.consumed >= this.config.warnAt) {\n warning = `Approaching budget limit (${utilization}%). Consider using compact read modes.`;\n }\n\n return {\n consumed: this.consumed,\n limit,\n remaining,\n utilization,\n warning,\n throttled: limit > 0 && this.consumed >= this.config.throttleAt,\n };\n }\n\n /**\n * Check if the budget is throttled (responses should be truncated).\n */\n isThrottled(): boolean {\n return this.config.maxTokensPerSession > 0 && this.consumed >= this.config.throttleAt;\n }\n\n /**\n * Check if a warning should be appended to responses.\n */\n shouldWarn(): boolean {\n return this.config.maxTokensPerSession > 0 && this.consumed >= this.config.warnAt;\n }\n\n /**\n * Reset the budget counters.\n */\n reset(): void {\n this.consumed = 0;\n }\n\n /**\n * Update budget configuration.\n */\n updateConfig(config: Partial<BudgetConfig>): void {\n this.config = { ...this.config, ...config };\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
6
|
"names": []
|
|
7
7
|
}
|
package/dist/config.js
CHANGED
|
@@ -93,6 +93,12 @@ const KNOWN_FIELDS = /* @__PURE__ */ new Set([
|
|
|
93
93
|
"dataMaxRows",
|
|
94
94
|
"dataQueryLimit",
|
|
95
95
|
"dataMaxResponseTokens",
|
|
96
|
+
"enableSecurity",
|
|
97
|
+
"securityDatabases",
|
|
98
|
+
"securityAutoEnrich",
|
|
99
|
+
"securityEnrichMaxAgeDays",
|
|
100
|
+
"securityLicensePolicy",
|
|
101
|
+
"contextBudget",
|
|
96
102
|
// Legacy aliases (still accepted, mapped during validation)
|
|
97
103
|
"enableCompression",
|
|
98
104
|
"compressionLevel"
|
|
@@ -151,7 +157,12 @@ function createDefaultConfig(_projectRoot) {
|
|
|
151
157
|
dataMaxFileSize: 52428800,
|
|
152
158
|
dataMaxRows: 1e6,
|
|
153
159
|
dataQueryLimit: 500,
|
|
154
|
-
dataMaxResponseTokens: 8e3
|
|
160
|
+
dataMaxResponseTokens: 8e3,
|
|
161
|
+
enableSecurity: false,
|
|
162
|
+
securityDatabases: ["OSV"],
|
|
163
|
+
securityAutoEnrich: true,
|
|
164
|
+
securityEnrichMaxAgeDays: 7,
|
|
165
|
+
securityLicensePolicy: { deny: [], warn: [] }
|
|
155
166
|
};
|
|
156
167
|
}
|
|
157
168
|
function validateConfig(config) {
|
|
@@ -223,6 +234,76 @@ function validateConfig(config) {
|
|
|
223
234
|
const dataMaxRows = typeof raw.dataMaxRows === "number" && raw.dataMaxRows > 0 ? Math.round(raw.dataMaxRows) : defaults.dataMaxRows;
|
|
224
235
|
const dataQueryLimit = typeof raw.dataQueryLimit === "number" && raw.dataQueryLimit > 0 ? Math.min(Math.round(raw.dataQueryLimit), 500) : defaults.dataQueryLimit;
|
|
225
236
|
const dataMaxResponseTokens = typeof raw.dataMaxResponseTokens === "number" && raw.dataMaxResponseTokens > 0 ? Math.round(raw.dataMaxResponseTokens) : defaults.dataMaxResponseTokens;
|
|
237
|
+
let enableSecurity;
|
|
238
|
+
if (typeof raw.enableSecurity === "boolean") {
|
|
239
|
+
enableSecurity = raw.enableSecurity;
|
|
240
|
+
} else {
|
|
241
|
+
if (raw.enableSecurity !== void 0) {
|
|
242
|
+
(0, import_errors.logWarn)("Invalid config field enableSecurity: expected boolean, applying default (false)");
|
|
243
|
+
}
|
|
244
|
+
enableSecurity = defaults.enableSecurity;
|
|
245
|
+
}
|
|
246
|
+
let securityAutoEnrich;
|
|
247
|
+
if (typeof raw.securityAutoEnrich === "boolean") {
|
|
248
|
+
securityAutoEnrich = raw.securityAutoEnrich;
|
|
249
|
+
} else {
|
|
250
|
+
if (raw.securityAutoEnrich !== void 0) {
|
|
251
|
+
(0, import_errors.logWarn)("Invalid config field securityAutoEnrich: expected boolean, applying default (true)");
|
|
252
|
+
}
|
|
253
|
+
securityAutoEnrich = defaults.securityAutoEnrich;
|
|
254
|
+
}
|
|
255
|
+
let securityEnrichMaxAgeDays;
|
|
256
|
+
if (typeof raw.securityEnrichMaxAgeDays === "number" && raw.securityEnrichMaxAgeDays > 0) {
|
|
257
|
+
securityEnrichMaxAgeDays = raw.securityEnrichMaxAgeDays;
|
|
258
|
+
} else {
|
|
259
|
+
if (raw.securityEnrichMaxAgeDays !== void 0) {
|
|
260
|
+
(0, import_errors.logWarn)("Invalid config field securityEnrichMaxAgeDays: expected positive number, applying default (7)");
|
|
261
|
+
}
|
|
262
|
+
securityEnrichMaxAgeDays = defaults.securityEnrichMaxAgeDays;
|
|
263
|
+
}
|
|
264
|
+
const SUPPORTED_SECURITY_DATABASES = /* @__PURE__ */ new Set(["OSV"]);
|
|
265
|
+
let securityDatabases;
|
|
266
|
+
if (Array.isArray(raw.securityDatabases) && raw.securityDatabases.every((d) => typeof d === "string")) {
|
|
267
|
+
const valid = raw.securityDatabases.filter((d) => {
|
|
268
|
+
if (!SUPPORTED_SECURITY_DATABASES.has(d)) {
|
|
269
|
+
(0, import_errors.logWarn)(`Unsupported security database "${d}" in securityDatabases, ignoring`);
|
|
270
|
+
return false;
|
|
271
|
+
}
|
|
272
|
+
return true;
|
|
273
|
+
});
|
|
274
|
+
securityDatabases = valid.length > 0 ? valid : defaults.securityDatabases;
|
|
275
|
+
} else {
|
|
276
|
+
if (raw.securityDatabases !== void 0) {
|
|
277
|
+
(0, import_errors.logWarn)('Invalid config field securityDatabases: expected array of strings, applying default (["OSV"])');
|
|
278
|
+
}
|
|
279
|
+
securityDatabases = defaults.securityDatabases;
|
|
280
|
+
}
|
|
281
|
+
let securityLicensePolicy;
|
|
282
|
+
if (raw.securityLicensePolicy && typeof raw.securityLicensePolicy === "object" && !Array.isArray(raw.securityLicensePolicy)) {
|
|
283
|
+
const rawPolicy = raw.securityLicensePolicy;
|
|
284
|
+
const deny = Array.isArray(rawPolicy.deny) && rawPolicy.deny.every((p) => typeof p === "string") ? rawPolicy.deny : defaults.securityLicensePolicy.deny;
|
|
285
|
+
const warn = Array.isArray(rawPolicy.warn) && rawPolicy.warn.every((p) => typeof p === "string") ? rawPolicy.warn : defaults.securityLicensePolicy.warn;
|
|
286
|
+
securityLicensePolicy = { deny, warn };
|
|
287
|
+
} else {
|
|
288
|
+
if (raw.securityLicensePolicy !== void 0) {
|
|
289
|
+
(0, import_errors.logWarn)("Invalid config field securityLicensePolicy: expected object with deny/warn arrays, applying default");
|
|
290
|
+
}
|
|
291
|
+
securityLicensePolicy = defaults.securityLicensePolicy;
|
|
292
|
+
}
|
|
293
|
+
let finalEnableArchitecture = enableArchitecture;
|
|
294
|
+
if (enableSecurity && !enableArchitecture) {
|
|
295
|
+
(0, import_errors.logWarn)("enableSecurity requires enableArchitecture \u2014 auto-enabling architecture analysis");
|
|
296
|
+
finalEnableArchitecture = true;
|
|
297
|
+
}
|
|
298
|
+
let contextBudget;
|
|
299
|
+
if (raw.contextBudget && typeof raw.contextBudget === "object" && !Array.isArray(raw.contextBudget)) {
|
|
300
|
+
const cb = raw.contextBudget;
|
|
301
|
+
contextBudget = {
|
|
302
|
+
maxTokensPerSession: typeof cb.maxTokensPerSession === "number" && cb.maxTokensPerSession > 0 ? Math.round(cb.maxTokensPerSession) : 1e5,
|
|
303
|
+
warnAt: typeof cb.warnAt === "number" && cb.warnAt > 0 ? Math.round(cb.warnAt) : 8e4,
|
|
304
|
+
throttleAt: typeof cb.throttleAt === "number" && cb.throttleAt > 0 ? Math.round(cb.throttleAt) : 95e3
|
|
305
|
+
};
|
|
306
|
+
}
|
|
226
307
|
const include = _validatePatterns(raw.include, defaults.include);
|
|
227
308
|
const exclude = _validatePatterns(raw.exclude, defaults.exclude);
|
|
228
309
|
return {
|
|
@@ -243,7 +324,7 @@ function validateConfig(config) {
|
|
|
243
324
|
minLogLevel,
|
|
244
325
|
frameworkHints,
|
|
245
326
|
fuzzyResolutionThreshold,
|
|
246
|
-
enableArchitecture,
|
|
327
|
+
enableArchitecture: finalEnableArchitecture,
|
|
247
328
|
cavemanMode,
|
|
248
329
|
shellCompressionLevel,
|
|
249
330
|
syncWarningThreshold,
|
|
@@ -272,7 +353,13 @@ function validateConfig(config) {
|
|
|
272
353
|
dataMaxRows,
|
|
273
354
|
dataQueryLimit,
|
|
274
355
|
dataMaxResponseTokens,
|
|
275
|
-
|
|
356
|
+
enableSecurity,
|
|
357
|
+
securityDatabases,
|
|
358
|
+
securityAutoEnrich,
|
|
359
|
+
securityEnrichMaxAgeDays,
|
|
360
|
+
securityLicensePolicy,
|
|
361
|
+
...architectureLayers !== void 0 ? { architectureLayers } : {},
|
|
362
|
+
...contextBudget !== void 0 ? { contextBudget } : {}
|
|
276
363
|
};
|
|
277
364
|
}
|
|
278
365
|
function _validateArchitectureLayers(raw) {
|