grepmax 0.26.30 → 0.26.33
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/.claude-plugin/marketplace.json +1 -1
- package/README.md +4 -2
- package/dist/commands/context.js +12 -8
- package/dist/commands/doctor.js +7 -9
- package/dist/commands/droid.js +2 -1
- package/dist/commands/extract.js +8 -11
- package/dist/commands/impact.js +5 -8
- package/dist/commands/mcp.js +38 -41
- package/dist/commands/peek.js +6 -9
- package/dist/commands/search-output.js +10 -11
- package/dist/commands/search-run.js +5 -4
- package/dist/commands/search-skeletons.js +2 -1
- package/dist/commands/search.js +5 -4
- package/dist/commands/serve.js +2 -1
- package/dist/commands/similar.js +7 -6
- package/dist/commands/skeleton.js +17 -22
- package/dist/commands/test-find.js +5 -8
- package/dist/config.js +6 -5
- package/dist/eval-oss.js +4 -3
- package/dist/eval-tokens.js +4 -4
- package/dist/eval.js +2 -5
- package/dist/index.js +4 -3
- package/dist/lib/daemon/daemon.js +36 -29
- package/dist/lib/daemon/graph-handler.js +2 -1
- package/dist/lib/daemon/mlx-server-manager.js +10 -9
- package/dist/lib/daemon/rows-handler.js +11 -13
- package/dist/lib/daemon/search-handler.js +6 -5
- package/dist/lib/daemon/vector-handler.js +2 -1
- package/dist/lib/daemon/watcher-manager.js +4 -2
- package/dist/lib/graph/graph-builder.js +4 -10
- package/dist/lib/graph/graph-traversal.js +0 -0
- package/dist/lib/index/batch-processor.js +13 -12
- package/dist/lib/index/chunker.js +22 -23
- package/dist/lib/index/syncer.js +2 -2
- package/dist/lib/llm/investigate.js +5 -4
- package/dist/lib/llm/review.js +2 -1
- package/dist/lib/llm/tools.js +6 -5
- package/dist/lib/output/agent-search-formatter.js +3 -2
- package/dist/lib/output/compact-results.js +16 -12
- package/dist/lib/search/searcher.js +11 -13
- package/dist/lib/setup/model-loader.js +1 -1
- package/dist/lib/skeleton/body-fields.js +2 -1
- package/dist/lib/skeleton/skeletonizer.js +8 -7
- package/dist/lib/store/vector-db.js +6 -5
- package/dist/lib/utils/formatter.js +5 -4
- package/dist/lib/utils/stale-hint.js +4 -3
- package/dist/lib/utils/store-access.js +2 -1
- package/dist/lib/workers/embeddings/granite.js +2 -1
- package/dist/lib/workers/pool.js +14 -10
- package/package.json +13 -15
- package/plugins/grepmax/.claude-plugin/plugin.json +1 -1
|
@@ -10,7 +10,7 @@
|
|
|
10
10
|
"name": "grepmax",
|
|
11
11
|
"source": "./plugins/grepmax",
|
|
12
12
|
"description": "Semantic code search for Claude Code. Automatically indexes your project and provides intelligent search capabilities.",
|
|
13
|
-
"version": "0.26.
|
|
13
|
+
"version": "0.26.33",
|
|
14
14
|
"author": {
|
|
15
15
|
"name": "Robert Owens",
|
|
16
16
|
"email": "robowens@me.com"
|
package/README.md
CHANGED
|
@@ -207,7 +207,9 @@ The CLI and MCP output include score, max similarity, pair count, representative
|
|
|
207
207
|
|
|
208
208
|
## Background Daemon
|
|
209
209
|
|
|
210
|
-
A single daemon watches
|
|
210
|
+
A single daemon watches your projects via native OS file events (FSEvents/inotify). Changes are detected in sub-second and incrementally reindexed. All writes to LanceDB are routed through the daemon via IPC, eliminating lock contention.
|
|
211
|
+
|
|
212
|
+
The daemon watches only projects that are in use: each Claude Code session (its MCP server and session hooks) holds a lease on its project, and `gmax add` / `gmax index` take a short one. When the last lease ends the project is unwatched; its index stays searchable, and the next session's catch-up scan picks up whatever changed in between. Set `GMAX_WATCH_ALL=1` to watch every registered project instead.
|
|
211
213
|
|
|
212
214
|
```bash
|
|
213
215
|
gmax watch --daemon -b # Start daemon manually
|
|
@@ -215,7 +217,7 @@ gmax watch stop # Stop daemon
|
|
|
215
217
|
gmax status # See all projects + watcher status
|
|
216
218
|
```
|
|
217
219
|
|
|
218
|
-
The daemon auto-starts when you run `gmax add`, `gmax index`, `gmax remove`, `gmax summarize`, or `gmax mcp`. It shuts down after
|
|
220
|
+
The daemon auto-starts when you run `gmax add`, `gmax index`, `gmax remove`, `gmax summarize`, or `gmax mcp`. It shuts down after 4 hours of inactivity, and hands off to a fresh daemon after 24 hours or once its memory footprint passes 2.5 GB. File-change batches are processed on at most four worker processes, added only when work backs up, with one kept free for searches; LanceDB compaction runs after writes rather than on every maintenance tick.
|
|
219
221
|
|
|
220
222
|
## Running under the Claude Code sandbox
|
|
221
223
|
|
package/dist/commands/context.js
CHANGED
|
@@ -77,13 +77,15 @@ function chunkPath(chunk) {
|
|
|
77
77
|
return String(chunk.path || (metadata === null || metadata === void 0 ? void 0 : metadata.path) || "");
|
|
78
78
|
}
|
|
79
79
|
function chunkStartLine(chunk) {
|
|
80
|
-
var _a
|
|
81
|
-
|
|
80
|
+
var _a;
|
|
81
|
+
var _b, _c, _d;
|
|
82
|
+
return Number((_d = (_c = (_b = chunk.start_line) !== null && _b !== void 0 ? _b : chunk.startLine) !== null && _c !== void 0 ? _c : (_a = chunk.generated_metadata) === null || _a === void 0 ? void 0 : _a.start_line) !== null && _d !== void 0 ? _d : 0);
|
|
82
83
|
}
|
|
83
84
|
function chunkEndLine(chunk) {
|
|
84
|
-
var _a
|
|
85
|
+
var _a;
|
|
86
|
+
var _b, _c, _d;
|
|
85
87
|
const start = chunkStartLine(chunk);
|
|
86
|
-
return Number((_d = (
|
|
88
|
+
return Number((_d = (_c = (_b = chunk.end_line) !== null && _b !== void 0 ? _b : chunk.endLine) !== null && _c !== void 0 ? _c : (_a = chunk.generated_metadata) === null || _a === void 0 ? void 0 : _a.end_line) !== null && _d !== void 0 ? _d : start);
|
|
87
89
|
}
|
|
88
90
|
/**
|
|
89
91
|
* The definition line of `parentSymbol` nearest above `startLine` — used to
|
|
@@ -167,14 +169,15 @@ exports.context = new commander_1.Command("context")
|
|
|
167
169
|
.option("--root <dir>", "Project root directory")
|
|
168
170
|
.option("--agent", "Compact output for AI agents", false)
|
|
169
171
|
.action((topic, opts) => __awaiter(void 0, void 0, void 0, function* () {
|
|
170
|
-
var _a
|
|
172
|
+
var _a;
|
|
173
|
+
var _b, _c;
|
|
171
174
|
const budget = Number.parseInt(opts.budget || "4000", 10) || 4000;
|
|
172
175
|
const maxResults = Number.parseInt(opts.maxResults || "10", 10) || 10;
|
|
173
176
|
try {
|
|
174
177
|
const root = (0, project_registry_1.resolveRootOrExit)(opts.root);
|
|
175
178
|
if (root === null)
|
|
176
179
|
return;
|
|
177
|
-
const projectRoot = (
|
|
180
|
+
const projectRoot = (_b = (0, project_root_1.findProjectRoot)(root)) !== null && _b !== void 0 ? _b : root;
|
|
178
181
|
const paths = (0, project_root_1.ensureProjectPaths)(projectRoot);
|
|
179
182
|
const pathTarget = (0, path_containment_1.resolveContainedExistingPath)(projectRoot, topic, {
|
|
180
183
|
cwd: root,
|
|
@@ -224,7 +227,7 @@ exports.context = new commander_1.Command("context")
|
|
|
224
227
|
const p = chunkPath(r);
|
|
225
228
|
const line = chunkStartLine(r);
|
|
226
229
|
const parentSym = String(r.parent_symbol || "");
|
|
227
|
-
const sym = (_c = (
|
|
230
|
+
const sym = (_c = (_a = (0, arrow_1.toArr)(r.defined_symbols)) === null || _a === void 0 ? void 0 : _a[0]) !== null && _c !== void 0 ? _c : (parentSym ? `(in ${parentSym})` : "");
|
|
228
231
|
const role = String(r.role || "IMPLEMENTATION");
|
|
229
232
|
epSection.push(`${relPath(projectRoot, p)}:${line + 1} ${sym} [${role}]`);
|
|
230
233
|
}
|
|
@@ -238,7 +241,8 @@ exports.context = new commander_1.Command("context")
|
|
|
238
241
|
// relevant one can fill the remaining budget instead of aborting the rest.
|
|
239
242
|
const topChunks = entryPoints.slice(0, 3);
|
|
240
243
|
const bodyBlobs = topChunks.map((r) => {
|
|
241
|
-
var _a
|
|
244
|
+
var _a;
|
|
245
|
+
var _b;
|
|
242
246
|
let absP;
|
|
243
247
|
try {
|
|
244
248
|
absP = (0, path_containment_1.resolveContainedPath)(projectRoot, chunkPath(r), {
|
package/dist/commands/doctor.js
CHANGED
|
@@ -342,7 +342,8 @@ exports.doctor = new commander_1.Command("doctor")
|
|
|
342
342
|
.option("--fix", "Auto-fix detected issues (compact, prune, remove stale locks)", false)
|
|
343
343
|
.option("--agent", "Compact output for AI agents", false)
|
|
344
344
|
.action((opts) => __awaiter(void 0, void 0, void 0, function* () {
|
|
345
|
-
var _a, _b
|
|
345
|
+
var _a, _b;
|
|
346
|
+
var _c, _d, _e, _f, _g, _h, _j, _k, _l, _m, _o, _p;
|
|
346
347
|
if (!opts.agent)
|
|
347
348
|
console.log("gmax Doctor\n");
|
|
348
349
|
const root = config_1.PATHS.globalRoot;
|
|
@@ -359,12 +360,12 @@ exports.doctor = new commander_1.Command("doctor")
|
|
|
359
360
|
checkDir("Grammars", grammars);
|
|
360
361
|
}
|
|
361
362
|
const globalConfig = (0, index_config_1.readGlobalConfig)();
|
|
362
|
-
const tier = (
|
|
363
|
+
const tier = (_c = config_1.MODEL_TIERS[globalConfig.modelTier]) !== null && _c !== void 0 ? _c : config_1.MODEL_TIERS.small;
|
|
363
364
|
if (!config_1.MODEL_TIERS[globalConfig.modelTier]) {
|
|
364
365
|
console.log(`WARN Unknown model tier '${globalConfig.modelTier}', falling back to 'small'`);
|
|
365
366
|
}
|
|
366
367
|
const embedModel = globalConfig.embedMode === "gpu"
|
|
367
|
-
? ((
|
|
368
|
+
? ((_d = globalConfig.mlxModel) !== null && _d !== void 0 ? _d : tier.mlxModel)
|
|
368
369
|
: tier.onnxModel;
|
|
369
370
|
if (!opts.agent) {
|
|
370
371
|
console.log(`\nEmbed mode: ${globalConfig.embedMode} | Model tier: ${globalConfig.modelTier} (${tier.vectorDim}d)`);
|
|
@@ -425,7 +426,7 @@ exports.doctor = new commander_1.Command("doctor")
|
|
|
425
426
|
body: JSON.stringify({ texts: ["gmax health check"] }),
|
|
426
427
|
});
|
|
427
428
|
const embedData = yield embedRes.json();
|
|
428
|
-
const dim = (_e = (
|
|
429
|
+
const dim = (_e = (_b = (_a = embedData === null || embedData === void 0 ? void 0 : embedData.vectors) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.length) !== null && _e !== void 0 ? _e : 0;
|
|
429
430
|
const ms = Date.now() - start;
|
|
430
431
|
const expectedDim = tier.vectorDim || 384;
|
|
431
432
|
if (dim === expectedDim) {
|
|
@@ -572,11 +573,8 @@ exports.doctor = new commander_1.Command("doctor")
|
|
|
572
573
|
: "ok";
|
|
573
574
|
}
|
|
574
575
|
catch (_q) { }
|
|
575
|
-
const staleChunkerProjects = projects.filter((p) => {
|
|
576
|
-
|
|
577
|
-
return p.status === "indexed" &&
|
|
578
|
-
((_a = p.chunkerVersion) !== null && _a !== void 0 ? _a : 1) < config_1.CONFIG.CHUNKER_VERSION;
|
|
579
|
-
});
|
|
576
|
+
const staleChunkerProjects = projects.filter((p) => { var _a; return p.status === "indexed" &&
|
|
577
|
+
((_a = p.chunkerVersion) !== null && _a !== void 0 ? _a : 1) < config_1.CONFIG.CHUNKER_VERSION; });
|
|
580
578
|
const staleEmbeddingProjects = projects.filter((p) => p.status === "indexed" &&
|
|
581
579
|
(0, embedding_status_1.projectEmbeddingStatus)(p, globalConfig).state === "stale");
|
|
582
580
|
const legacyEmbeddingCount = (0, embedding_status_1.countLegacyEmbeddingProjects)(projects, globalConfig);
|
package/dist/commands/droid.js
CHANGED
|
@@ -92,7 +92,8 @@ function loadSettings(settingsPath) {
|
|
|
92
92
|
/** True when a hook entry was installed by gmax — its command points at our
|
|
93
93
|
* hooks dir. Used to remove only gmax entries on uninstall. */
|
|
94
94
|
function isGmaxHookEntry(entry, hooksDir) {
|
|
95
|
-
var _a
|
|
95
|
+
var _a;
|
|
96
|
+
var _b;
|
|
96
97
|
return (_b = (_a = entry.hooks) === null || _a === void 0 ? void 0 : _a.some((h) => { var _a; return (_a = h.command) === null || _a === void 0 ? void 0 : _a.includes(hooksDir); })) !== null && _b !== void 0 ? _b : false;
|
|
97
98
|
}
|
|
98
99
|
/** Strip gmax hook entries from settings.hooks in place, preserving unrelated
|
package/dist/commands/extract.js
CHANGED
|
@@ -154,17 +154,14 @@ exports.extract = new commander_1.Command("extract")
|
|
|
154
154
|
matches: [{ kind: "definedSymbol", symbol }],
|
|
155
155
|
limit: 10,
|
|
156
156
|
});
|
|
157
|
-
const indexedChunks = (indexedRows !== null && indexedRows !== void 0 ? indexedRows : []).map((row) => {
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
definedSymbols: (_a = row.defined_symbols) !== null && _a !== void 0 ? _a : [],
|
|
166
|
-
});
|
|
167
|
-
});
|
|
157
|
+
const indexedChunks = (indexedRows !== null && indexedRows !== void 0 ? indexedRows : []).map((row) => { var _a; return ({
|
|
158
|
+
path: String(row.path || ""),
|
|
159
|
+
startLine: Number(row.start_line || 0),
|
|
160
|
+
endLine: Number(row.end_line || 0),
|
|
161
|
+
role: String(row.role || "IMPLEMENTATION"),
|
|
162
|
+
exported: Boolean(row.is_exported),
|
|
163
|
+
definedSymbols: (_a = row.defined_symbols) !== null && _a !== void 0 ? _a : [],
|
|
164
|
+
}); });
|
|
168
165
|
const chunks = indexedChunks.flatMap((chunk) => {
|
|
169
166
|
try {
|
|
170
167
|
return [
|
package/dist/commands/impact.js
CHANGED
|
@@ -98,14 +98,11 @@ exports.impact = new commander_1.Command("impact")
|
|
|
98
98
|
projectRoot,
|
|
99
99
|
scope,
|
|
100
100
|
payload: { target },
|
|
101
|
-
render: (resp) => {
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
symbolFamilies: (_b = resp.symbolFamilies) !== null && _b !== void 0 ? _b : null,
|
|
107
|
-
});
|
|
108
|
-
},
|
|
101
|
+
render: (resp) => { var _a, _b; return ({
|
|
102
|
+
symbols: (_a = resp.symbols) !== null && _a !== void 0 ? _a : [],
|
|
103
|
+
resolvedAsFile: resp.resolvedAsFile === true,
|
|
104
|
+
symbolFamilies: (_b = resp.symbolFamilies) !== null && _b !== void 0 ? _b : null,
|
|
105
|
+
}); },
|
|
109
106
|
inProcess: () => (0, graph_handler_1.runGraphResolve)(localDb(), { target, projectRoot }),
|
|
110
107
|
});
|
|
111
108
|
if (symbols.length === 0) {
|
package/dist/commands/mcp.js
CHANGED
|
@@ -232,16 +232,19 @@ function chunkSymbols(chunk) {
|
|
|
232
232
|
// r.start_line directly yields undefined (and crashed build_context's rel()).
|
|
233
233
|
// Use nullish (not ||) so a legitimate line 0 isn't skipped.
|
|
234
234
|
function searchResultPath(r) {
|
|
235
|
-
var _a
|
|
236
|
-
|
|
235
|
+
var _a;
|
|
236
|
+
var _b, _c;
|
|
237
|
+
return String((_c = (_b = r === null || r === void 0 ? void 0 : r.path) !== null && _b !== void 0 ? _b : (_a = r === null || r === void 0 ? void 0 : r.metadata) === null || _a === void 0 ? void 0 : _a.path) !== null && _c !== void 0 ? _c : "");
|
|
237
238
|
}
|
|
238
239
|
function searchResultStartLine(r) {
|
|
239
|
-
var _a
|
|
240
|
-
|
|
240
|
+
var _a;
|
|
241
|
+
var _b, _c;
|
|
242
|
+
return Number((_c = (_b = r === null || r === void 0 ? void 0 : r.start_line) !== null && _b !== void 0 ? _b : (_a = r === null || r === void 0 ? void 0 : r.generated_metadata) === null || _a === void 0 ? void 0 : _a.start_line) !== null && _c !== void 0 ? _c : 0);
|
|
241
243
|
}
|
|
242
244
|
function searchResultEndLine(r, fallbackStart = 0) {
|
|
243
|
-
var _a
|
|
244
|
-
|
|
245
|
+
var _a;
|
|
246
|
+
var _b, _c;
|
|
247
|
+
return Number((_c = (_b = r === null || r === void 0 ? void 0 : r.end_line) !== null && _b !== void 0 ? _b : (_a = r === null || r === void 0 ? void 0 : r.generated_metadata) === null || _a === void 0 ? void 0 : _a.end_line) !== null && _c !== void 0 ? _c : fallbackStart);
|
|
245
248
|
}
|
|
246
249
|
function filterMcpSearchResults(data, options = {}) {
|
|
247
250
|
var _a, _b;
|
|
@@ -420,10 +423,7 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
420
423
|
*/
|
|
421
424
|
function searchStore(args) {
|
|
422
425
|
return readStore("search", {
|
|
423
|
-
daemon: () => {
|
|
424
|
-
var _a;
|
|
425
|
-
return (0, daemon_client_1.sendDaemonCommand)(Object.assign({ cmd: ((_a = args.filters) === null || _a === void 0 ? void 0 : _a.projectRoots) ? "search-v2" : "search" }, args), { timeoutMs: 60000 });
|
|
426
|
-
},
|
|
426
|
+
daemon: () => { var _a; return (0, daemon_client_1.sendDaemonCommand)(Object.assign({ cmd: ((_a = args.filters) === null || _a === void 0 ? void 0 : _a.projectRoots) ? "search-v2" : "search" }, args), { timeoutMs: 60000 }); },
|
|
427
427
|
render: (resp) => ({
|
|
428
428
|
data: Array.isArray(resp.data) ? resp.data : [],
|
|
429
429
|
warnings: Array.isArray(resp.warnings)
|
|
@@ -470,14 +470,11 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
470
470
|
projectRoot: root,
|
|
471
471
|
scope,
|
|
472
472
|
payload: { target },
|
|
473
|
-
render: (resp) => {
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
symbolFamilies: (_b = resp.symbolFamilies) !== null && _b !== void 0 ? _b : null,
|
|
479
|
-
});
|
|
480
|
-
},
|
|
473
|
+
render: (resp) => { var _a, _b; return ({
|
|
474
|
+
symbols: (_a = resp.symbols) !== null && _a !== void 0 ? _a : [],
|
|
475
|
+
resolvedAsFile: resp.resolvedAsFile === true,
|
|
476
|
+
symbolFamilies: (_b = resp.symbolFamilies) !== null && _b !== void 0 ? _b : null,
|
|
477
|
+
}); },
|
|
481
478
|
inProcess: () => localStore((deps) => (0, graph_handler_1.runGraphResolve)(deps.vectorDb, { target, projectRoot: root })),
|
|
482
479
|
});
|
|
483
480
|
}
|
|
@@ -547,13 +544,10 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
547
544
|
function lookupSkeleton(root, req) {
|
|
548
545
|
return readStore("skeleton", {
|
|
549
546
|
daemon: () => (0, daemon_client_1.sendDaemonCommand)(Object.assign({ cmd: "rows.skeleton", projectRoot: root }, req), { timeoutMs: 30000 }),
|
|
550
|
-
render: (resp) => {
|
|
551
|
-
|
|
552
|
-
|
|
553
|
-
|
|
554
|
-
skeleton: ((_b = resp.skeleton) !== null && _b !== void 0 ? _b : null),
|
|
555
|
-
});
|
|
556
|
-
},
|
|
547
|
+
render: (resp) => { var _a, _b; return ({
|
|
548
|
+
path: ((_a = resp.path) !== null && _a !== void 0 ? _a : null),
|
|
549
|
+
skeleton: ((_b = resp.skeleton) !== null && _b !== void 0 ? _b : null),
|
|
550
|
+
}); },
|
|
557
551
|
inProcess: () => localStore((deps) => (0, rows_handler_1.runSkeleton)(deps, Object.assign({ projectRoot: root }, req))),
|
|
558
552
|
});
|
|
559
553
|
}
|
|
@@ -779,13 +773,14 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
779
773
|
return ok(prefixNotes(output));
|
|
780
774
|
}
|
|
781
775
|
let results = result.data.map((r) => {
|
|
782
|
-
var _a, _b, _c
|
|
783
|
-
|
|
776
|
+
var _a, _b, _c;
|
|
777
|
+
var _d, _e, _f, _g, _h, _j, _k, _l, _m;
|
|
778
|
+
const absPath = (_e = (_d = r.path) !== null && _d !== void 0 ? _d : (_a = r.metadata) === null || _a === void 0 ? void 0 : _a.path) !== null && _e !== void 0 ? _e : "";
|
|
784
779
|
const relPath = absPath.startsWith(displayRoot)
|
|
785
780
|
? absPath.slice(displayRoot.length + 1)
|
|
786
781
|
: absPath;
|
|
787
|
-
const startLine = (
|
|
788
|
-
const endLine = (_j = (
|
|
782
|
+
const startLine = (_g = (_f = r.startLine) !== null && _f !== void 0 ? _f : (_b = r.generated_metadata) === null || _b === void 0 ? void 0 : _b.start_line) !== null && _g !== void 0 ? _g : 0;
|
|
783
|
+
const endLine = (_j = (_h = r.endLine) !== null && _h !== void 0 ? _h : (_c = r.generated_metadata) === null || _c === void 0 ? void 0 : _c.end_line) !== null && _j !== void 0 ? _j : 0;
|
|
789
784
|
const defs = toStringArray((_k = r.definedSymbols) !== null && _k !== void 0 ? _k : r.defined_symbols);
|
|
790
785
|
const refs = toStringArray((_l = r.referenced_symbols) !== null && _l !== void 0 ? _l : r.referencedSymbols);
|
|
791
786
|
const symbol = defs[0] || "(anonymous)";
|
|
@@ -1230,7 +1225,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
1230
1225
|
}
|
|
1231
1226
|
function handlePeekSymbol(args) {
|
|
1232
1227
|
return __awaiter(this, void 0, void 0, function* () {
|
|
1233
|
-
var _a, _b, _c
|
|
1228
|
+
var _a, _b, _c;
|
|
1229
|
+
var _d, _e, _f, _g;
|
|
1234
1230
|
ensureWatcher();
|
|
1235
1231
|
const symbol = String(args.symbol || "");
|
|
1236
1232
|
if (!symbol)
|
|
@@ -1252,9 +1248,9 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
1252
1248
|
const rel = (p) => p.startsWith(root) ? p.slice(root.length + 1) : p;
|
|
1253
1249
|
// Chunk metadata for is_exported and end_line; null when the symbol has
|
|
1254
1250
|
// no defining chunk, in which case the center's own line stands in.
|
|
1255
|
-
const exported = (
|
|
1256
|
-
const startLine = (
|
|
1257
|
-
const endLine = (_f = (
|
|
1251
|
+
const exported = (_d = (_a = peek.meta) === null || _a === void 0 ? void 0 : _a.isExported) !== null && _d !== void 0 ? _d : false;
|
|
1252
|
+
const startLine = (_e = (_b = peek.meta) === null || _b === void 0 ? void 0 : _b.startLine) !== null && _e !== void 0 ? _e : center.line;
|
|
1253
|
+
const endLine = (_f = (_c = peek.meta) === null || _c === void 0 ? void 0 : _c.endLine) !== null && _f !== void 0 ? _f : center.line;
|
|
1258
1254
|
// Get signature from source
|
|
1259
1255
|
const fs = yield Promise.resolve().then(() => __importStar(require("node:fs")));
|
|
1260
1256
|
let sigText = "(source not available)";
|
|
@@ -2073,7 +2069,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
2073
2069
|
if (filtered.length === 0)
|
|
2074
2070
|
return ok("No indexed results found in changed files for that query.");
|
|
2075
2071
|
const lines = filtered.slice(0, limit).map((r) => {
|
|
2076
|
-
var _a
|
|
2072
|
+
var _a;
|
|
2073
|
+
var _b;
|
|
2077
2074
|
const sym = (_b = (_a = toStringArray(r.defined_symbols)) === null || _a === void 0 ? void 0 : _a[0]) !== null && _b !== void 0 ? _b : "";
|
|
2078
2075
|
return `${rel(searchResultPath(r))}:${searchResultStartLine(r) + 1} ${sym} [${r.role || "IMPL"}]`;
|
|
2079
2076
|
});
|
|
@@ -2178,10 +2175,7 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
2178
2175
|
limit,
|
|
2179
2176
|
families: symbolFamilies,
|
|
2180
2177
|
},
|
|
2181
|
-
render: (resp) => {
|
|
2182
|
-
var _a;
|
|
2183
|
-
return (_a = resp.dependents) !== null && _a !== void 0 ? _a : [];
|
|
2184
|
-
},
|
|
2178
|
+
render: (resp) => { var _a; return (_a = resp.dependents) !== null && _a !== void 0 ? _a : []; },
|
|
2185
2179
|
inProcess: () => localStore((deps) => (0, graph_handler_1.runGraphDependents)(deps.vectorDb, {
|
|
2186
2180
|
symbols,
|
|
2187
2181
|
queryRoot: root,
|
|
@@ -2304,7 +2298,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
2304
2298
|
}
|
|
2305
2299
|
function handleBuildContext(args) {
|
|
2306
2300
|
return __awaiter(this, void 0, void 0, function* () {
|
|
2307
|
-
var _a
|
|
2301
|
+
var _a;
|
|
2302
|
+
var _b;
|
|
2308
2303
|
ensureWatcher();
|
|
2309
2304
|
const topic = String(args.topic || "");
|
|
2310
2305
|
if (!topic)
|
|
@@ -2327,7 +2322,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
2327
2322
|
// Entry points. searcher.search() returns mapped chunks, so the path and
|
|
2328
2323
|
// line live under metadata/generated_metadata — read via the helpers.
|
|
2329
2324
|
const epLines = response.data.slice(0, 5).map((r) => {
|
|
2330
|
-
var _a
|
|
2325
|
+
var _a;
|
|
2326
|
+
var _b;
|
|
2331
2327
|
const sym = (_b = (_a = toStringArray(r.defined_symbols)) === null || _a === void 0 ? void 0 : _a[0]) !== null && _b !== void 0 ? _b : "";
|
|
2332
2328
|
return `${rel(searchResultPath(r))}:${searchResultStartLine(r) + 1} ${sym} [${r.role || "IMPL"}]`;
|
|
2333
2329
|
});
|
|
@@ -2522,7 +2518,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
2522
2518
|
// Best-effort query logging, applied uniformly to every tool exactly as the
|
|
2523
2519
|
// old single CallToolRequestSchema dispatch did before each return.
|
|
2524
2520
|
const logToolCall = (name, toolArgs, startMs, result) => __awaiter(void 0, void 0, void 0, function* () {
|
|
2525
|
-
var _a, _b
|
|
2521
|
+
var _a, _b;
|
|
2522
|
+
var _c;
|
|
2526
2523
|
try {
|
|
2527
2524
|
const { logQuery } = yield Promise.resolve().then(() => __importStar(require("../lib/utils/query-log")));
|
|
2528
2525
|
const text = (_c = (_b = (_a = result.content) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.text) !== null && _c !== void 0 ? _c : "";
|
package/dist/commands/peek.js
CHANGED
|
@@ -258,15 +258,12 @@ exports.peek = new commander_1.Command("peek")
|
|
|
258
258
|
return [];
|
|
259
259
|
}
|
|
260
260
|
});
|
|
261
|
-
const resolvedCallers = (0, callsites_1.resolveCallSites)(readableCallers, symbol).map((c) => {
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
edgeKind: edgeKindBySym.get(c.symbol),
|
|
268
|
-
});
|
|
269
|
-
});
|
|
261
|
+
const resolvedCallers = (0, callsites_1.resolveCallSites)(readableCallers, symbol).map((c) => { var _a; return ({
|
|
262
|
+
symbol: c.symbol,
|
|
263
|
+
file: c.file,
|
|
264
|
+
line: (_a = c.snippetLine) !== null && _a !== void 0 ? _a : c.line,
|
|
265
|
+
edgeKind: edgeKindBySym.get(c.symbol),
|
|
266
|
+
}); });
|
|
270
267
|
// Builtins listed as "(not indexed)" callees (trunc, now, filter, …)
|
|
271
268
|
// are noise; project symbols always resolve so they're unaffected.
|
|
272
269
|
// Dedupe by symbol — repeated references arrive once per chunk.
|
|
@@ -194,7 +194,8 @@ function executeServerSearch(params) {
|
|
|
194
194
|
*/
|
|
195
195
|
function renderSearchOutput(params) {
|
|
196
196
|
return __awaiter(this, void 0, void 0, function* () {
|
|
197
|
-
var _a, _b, _c
|
|
197
|
+
var _a, _b, _c;
|
|
198
|
+
var _d, _e, _f, _g;
|
|
198
199
|
const { searchResult, options, minScore, crossProject, pattern, effectiveRoot, projectRoot, vectorDb, precomputedSkeletons, precomputedGraph, indexState, } = params;
|
|
199
200
|
if (!options.agent && ((_a = searchResult.warnings) === null || _a === void 0 ? void 0 : _a.length)) {
|
|
200
201
|
for (const w of searchResult.warnings) {
|
|
@@ -266,10 +267,7 @@ function renderSearchOutput(params) {
|
|
|
266
267
|
emitFooter();
|
|
267
268
|
return { resultCount };
|
|
268
269
|
}
|
|
269
|
-
const getPath = (r) => {
|
|
270
|
-
var _a, _b, _c;
|
|
271
|
-
return String((_c = (_a = r.path) !== null && _a !== void 0 ? _a : (_b = r.metadata) === null || _b === void 0 ? void 0 : _b.path) !== null && _c !== void 0 ? _c : "");
|
|
272
|
-
};
|
|
270
|
+
const getPath = (r) => { var _a; var _b, _c; return String((_c = (_b = r.path) !== null && _b !== void 0 ? _b : (_a = r.metadata) === null || _a === void 0 ? void 0 : _a.path) !== null && _c !== void 0 ? _c : ""); };
|
|
273
271
|
const groups = (0, cross_project_1.groupResultsByProject)(filteredData, crossProject.roots, getPath);
|
|
274
272
|
const isTTY = process.stdout.isTTY;
|
|
275
273
|
const shouldBePlain = options.plain || !isTTY;
|
|
@@ -397,10 +395,11 @@ function renderSearchOutput(params) {
|
|
|
397
395
|
// chunk and keeps filling with smaller, still-relevant ones rather than
|
|
398
396
|
// aborting the loop — recovering budget the old greedy `break` wasted.
|
|
399
397
|
const candidates = filteredData.map((r, idx) => {
|
|
400
|
-
var _a, _b, _c
|
|
401
|
-
|
|
402
|
-
const
|
|
403
|
-
const
|
|
398
|
+
var _a, _b, _c;
|
|
399
|
+
var _d, _e, _f, _g, _h, _j, _k, _l;
|
|
400
|
+
const indexedPath = (_e = (_d = r.path) !== null && _d !== void 0 ? _d : (_a = r.metadata) === null || _a === void 0 ? void 0 : _a.path) !== null && _e !== void 0 ? _e : "";
|
|
401
|
+
const startLine = (_h = (_g = (_f = r.startLine) !== null && _f !== void 0 ? _f : r.start_line) !== null && _g !== void 0 ? _g : (_b = r.generated_metadata) === null || _b === void 0 ? void 0 : _b.start_line) !== null && _h !== void 0 ? _h : 0;
|
|
402
|
+
const endLine = (_l = (_k = (_j = r.endLine) !== null && _j !== void 0 ? _j : r.end_line) !== null && _k !== void 0 ? _k : (_c = r.generated_metadata) === null || _c === void 0 ? void 0 : _c.end_line) !== null && _l !== void 0 ? _l : startLine;
|
|
404
403
|
let relPath = "(invalid indexed path)";
|
|
405
404
|
const role = r.role || "IMPLEMENTATION";
|
|
406
405
|
const symbol = Array.isArray(r.defined_symbols) &&
|
|
@@ -454,7 +453,7 @@ function renderSearchOutput(params) {
|
|
|
454
453
|
if (options.imports) {
|
|
455
454
|
const seenFiles = new Set();
|
|
456
455
|
for (const r of filteredData) {
|
|
457
|
-
const absP = (
|
|
456
|
+
const absP = (_e = (_d = r.path) !== null && _d !== void 0 ? _d : (_b = r.metadata) === null || _b === void 0 ? void 0 : _b.path) !== null && _e !== void 0 ? _e : "";
|
|
458
457
|
if (absP && !seenFiles.has(absP)) {
|
|
459
458
|
seenFiles.add(absP);
|
|
460
459
|
const imports = getImportsForFile(absP);
|
|
@@ -481,7 +480,7 @@ function renderSearchOutput(params) {
|
|
|
481
480
|
for (const r of filteredData) {
|
|
482
481
|
const b = r.scoreBreakdown;
|
|
483
482
|
if (b) {
|
|
484
|
-
const absP = (_g = (
|
|
483
|
+
const absP = (_g = (_f = r.path) !== null && _f !== void 0 ? _f : (_c = r.metadata) === null || _c === void 0 ? void 0 : _c.path) !== null && _g !== void 0 ? _g : "";
|
|
485
484
|
const relPath = absP.startsWith(projectRoot)
|
|
486
485
|
? absP.slice(projectRoot.length + 1)
|
|
487
486
|
: absP;
|
|
@@ -73,7 +73,8 @@ exports.shouldFallbackFromDaemonError = store_access_1.shouldFallbackFromDaemonE
|
|
|
73
73
|
*/
|
|
74
74
|
function runSearch(params) {
|
|
75
75
|
return __awaiter(this, void 0, void 0, function* () {
|
|
76
|
-
var _a, _b
|
|
76
|
+
var _a, _b;
|
|
77
|
+
var _c;
|
|
77
78
|
const { pattern, options, projectRoot, effectiveRoot, paths, projectStatus, searchFilters, pathFilter, seeds, } = params;
|
|
78
79
|
// Tracks a DB opened by the in-process path so it can be (a) returned to the
|
|
79
80
|
// caller for closing after render, or (b) closed here if indexing throws.
|
|
@@ -133,7 +134,7 @@ function runSearch(params) {
|
|
|
133
134
|
throw new Error(`Daemon search failed${detail}`);
|
|
134
135
|
}
|
|
135
136
|
else if (process.env.GMAX_DEBUG === "1") {
|
|
136
|
-
console.error(`[search] daemon path unavailable: ${(
|
|
137
|
+
console.error(`[search] daemon path unavailable: ${(_c = resp.error) !== null && _c !== void 0 ? _c : "unknown"}`);
|
|
137
138
|
}
|
|
138
139
|
}
|
|
139
140
|
catch (err) {
|
|
@@ -214,7 +215,7 @@ function runSearch(params) {
|
|
|
214
215
|
return { kind: "dry-run", vectorDb: openedDb };
|
|
215
216
|
}
|
|
216
217
|
yield vectorDb.createFTSIndex();
|
|
217
|
-
yield (
|
|
218
|
+
yield (_a = vectorDb.createVectorIndex) === null || _a === void 0 ? void 0 : _a.call(vectorDb);
|
|
218
219
|
if (result.degraded) {
|
|
219
220
|
spinner.warn(`Indexing incomplete (${result.processed}/${result.total}) • ${result.scanErrors} scan errors • ${result.failedFiles} failed. Results may be partial.`);
|
|
220
221
|
}
|
|
@@ -242,7 +243,7 @@ function runSearch(params) {
|
|
|
242
243
|
}
|
|
243
244
|
}
|
|
244
245
|
// Ensure a watcher is running for live reindexing
|
|
245
|
-
if (!process.env.VITEST && !((
|
|
246
|
+
if (!process.env.VITEST && !((_b = process.env.NODE_ENV) === null || _b === void 0 ? void 0 : _b.includes("test"))) {
|
|
246
247
|
const { launchWatcher } = yield Promise.resolve().then(() => __importStar(require("../lib/utils/watcher-launcher")));
|
|
247
248
|
const launched = yield launchWatcher(projectRoot);
|
|
248
249
|
if (!launched.ok && launched.reason === "spawn-failed") {
|
|
@@ -51,7 +51,8 @@ const path_containment_1 = require("../lib/utils/path-containment");
|
|
|
51
51
|
let globalSkeletonizer = null;
|
|
52
52
|
function outputSkeletons(results, projectRoot, limit, db, precomputed) {
|
|
53
53
|
return __awaiter(this, void 0, void 0, function* () {
|
|
54
|
-
var _a
|
|
54
|
+
var _a;
|
|
55
|
+
var _b;
|
|
55
56
|
const seenPaths = new Set();
|
|
56
57
|
const filesToProcess = [];
|
|
57
58
|
for (const result of results) {
|
package/dist/commands/search.js
CHANGED
|
@@ -102,7 +102,8 @@ Examples:
|
|
|
102
102
|
gmax "auth middleware" --projects api,gateway --plain
|
|
103
103
|
`)
|
|
104
104
|
.action((pattern, exec_path, _options, cmd) => __awaiter(void 0, void 0, void 0, function* () {
|
|
105
|
-
var _a, _b, _c
|
|
105
|
+
var _a, _b, _c;
|
|
106
|
+
var _d, _e, _f, _g;
|
|
106
107
|
const options = cmd.optsWithGlobals();
|
|
107
108
|
const root = process.cwd();
|
|
108
109
|
const minScore = Number.isFinite(Number.parseFloat(options.minScore))
|
|
@@ -160,9 +161,9 @@ Examples:
|
|
|
160
161
|
const resolved = (0, project_registry_1.resolveRootOrExit)(options.root);
|
|
161
162
|
if (resolved === null)
|
|
162
163
|
return;
|
|
163
|
-
resolvedOptionRoot = (
|
|
164
|
+
resolvedOptionRoot = (_d = (0, project_root_1.findProjectRoot)(resolved)) !== null && _d !== void 0 ? _d : resolved;
|
|
164
165
|
}
|
|
165
|
-
const cwdProjectRoot = (
|
|
166
|
+
const cwdProjectRoot = (_e = (0, project_root_1.findProjectRoot)(root)) !== null && _e !== void 0 ? _e : root;
|
|
166
167
|
const projectRootForServer = resolvedOptionRoot !== null && resolvedOptionRoot !== void 0 ? resolvedOptionRoot : cwdProjectRoot;
|
|
167
168
|
// A cwd inside a nested git repo covered by a registered umbrella project
|
|
168
169
|
// resolves to the umbrella (findProjectRoot). Scope the search to the
|
|
@@ -201,7 +202,7 @@ Examples:
|
|
|
201
202
|
}
|
|
202
203
|
// Only announce the scope when it was implied by the cwd; an explicit
|
|
203
204
|
// --in/[path] already states what the caller scoped to.
|
|
204
|
-
if (nestedScopeRoot && !((
|
|
205
|
+
if (nestedScopeRoot && !((_c = options.in) === null || _c === void 0 ? void 0 : _c.length) && !exec_path) {
|
|
205
206
|
const subName = path.relative(cwdProjectRoot, nestedScopeRoot);
|
|
206
207
|
const projName = path.basename(cwdProjectRoot);
|
|
207
208
|
console.error(`Scoped to ${subName}/ within ${projName}; pass --root ${projName} to search the whole project.`);
|
package/dist/commands/serve.js
CHANGED
|
@@ -190,7 +190,8 @@ function optionalStringArray(body, key) {
|
|
|
190
190
|
function createServeHttpServer(projectRoot, deps) {
|
|
191
191
|
const active = new Set();
|
|
192
192
|
const server = http.createServer((req, res) => __awaiter(this, void 0, void 0, function* () {
|
|
193
|
-
var _a
|
|
193
|
+
var _a;
|
|
194
|
+
var _b, _c, _d;
|
|
194
195
|
(_a = deps.onActivity) === null || _a === void 0 ? void 0 : _a.call(deps);
|
|
195
196
|
if (req.method === "GET" && req.url === "/health") {
|
|
196
197
|
writeJson(res, 200, { status: "ok" });
|
package/dist/commands/similar.js
CHANGED
|
@@ -64,14 +64,15 @@ exports.similar = new commander_1.Command("similar")
|
|
|
64
64
|
.option("--exclude <subpath>", "Exclude a sub-path of the project (repeatable)", (value, prev) => prev ? [...prev, value] : [value])
|
|
65
65
|
.option("--agent", "Compact output for AI agents", false)
|
|
66
66
|
.action((target, opts) => __awaiter(void 0, void 0, void 0, function* () {
|
|
67
|
-
var _a, _b
|
|
67
|
+
var _a, _b;
|
|
68
|
+
var _c, _d, _e, _f, _g, _h, _j;
|
|
68
69
|
const limit = Math.min(Math.max(Number.parseInt(opts.maxCount || "5", 10), 1), 25);
|
|
69
70
|
const threshold = Number.parseFloat(opts.threshold || "0") || 0;
|
|
70
71
|
try {
|
|
71
72
|
const root = (0, project_registry_1.resolveRootOrExit)(opts.root);
|
|
72
73
|
if (root === null)
|
|
73
74
|
return;
|
|
74
|
-
const projectRoot = (
|
|
75
|
+
const projectRoot = (_c = (0, project_root_1.findProjectRoot)(root)) !== null && _c !== void 0 ? _c : root;
|
|
75
76
|
(0, stale_hint_1.maybeWarnStaleChunker)(projectRoot, { agent: opts.agent });
|
|
76
77
|
(0, stale_hint_1.maybeWarnStaleEmbedding)(projectRoot, { agent: opts.agent });
|
|
77
78
|
const paths = (0, project_root_1.ensureProjectPaths)(projectRoot);
|
|
@@ -133,17 +134,17 @@ exports.similar = new commander_1.Command("similar")
|
|
|
133
134
|
const rel = (p) => p.startsWith(`${projectRoot}/`) ? p.slice(projectRoot.length + 1) : p;
|
|
134
135
|
if (opts.agent) {
|
|
135
136
|
for (const r of filtered.slice(0, limit)) {
|
|
136
|
-
const sym = (
|
|
137
|
-
const line = ((
|
|
137
|
+
const sym = (_d = (_a = r.defined_symbols) === null || _a === void 0 ? void 0 : _a[0]) !== null && _d !== void 0 ? _d : "";
|
|
138
|
+
const line = ((_e = r.start_line) !== null && _e !== void 0 ? _e : 0) + 1;
|
|
138
139
|
const role = (r.role || "IMPL").slice(0, 4);
|
|
139
|
-
const dist = ((
|
|
140
|
+
const dist = ((_f = r._distance) !== null && _f !== void 0 ? _f : 0).toFixed(3);
|
|
140
141
|
console.log(`${rel(r.path)}:${line}\t${sym}\t[${role}]\td=${dist}`);
|
|
141
142
|
}
|
|
142
143
|
}
|
|
143
144
|
else {
|
|
144
145
|
console.log(`Code similar to ${target}:\n`);
|
|
145
146
|
for (const r of filtered.slice(0, limit)) {
|
|
146
|
-
const sym = (_g = (
|
|
147
|
+
const sym = (_g = (_b = r.defined_symbols) === null || _b === void 0 ? void 0 : _b[0]) !== null && _g !== void 0 ? _g : "";
|
|
147
148
|
const line = ((_h = r.start_line) !== null && _h !== void 0 ? _h : 0) + 1;
|
|
148
149
|
const role = r.role || "IMPLEMENTATION";
|
|
149
150
|
const dist = ((_j = r._distance) !== null && _j !== void 0 ? _j : 0).toFixed(3);
|