grepmax 0.7.10 → 0.7.11
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/dist/commands/mcp.js
CHANGED
|
@@ -268,6 +268,19 @@ const TOOLS = [
|
|
|
268
268
|
},
|
|
269
269
|
},
|
|
270
270
|
},
|
|
271
|
+
{
|
|
272
|
+
name: "summarize_project",
|
|
273
|
+
description: "High-level overview of an indexed project — languages, directory structure, role distribution, key symbols, and entry points. Use when first exploring a codebase.",
|
|
274
|
+
inputSchema: {
|
|
275
|
+
type: "object",
|
|
276
|
+
properties: {
|
|
277
|
+
root: {
|
|
278
|
+
type: "string",
|
|
279
|
+
description: "Project root (absolute path). Defaults to current project.",
|
|
280
|
+
},
|
|
281
|
+
},
|
|
282
|
+
},
|
|
283
|
+
},
|
|
271
284
|
];
|
|
272
285
|
// ---------------------------------------------------------------------------
|
|
273
286
|
// Helpers
|
|
@@ -998,6 +1011,130 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
998
1011
|
}
|
|
999
1012
|
});
|
|
1000
1013
|
}
|
|
1014
|
+
function handleSummarizeProject(args) {
|
|
1015
|
+
return __awaiter(this, void 0, void 0, function* () {
|
|
1016
|
+
var _a;
|
|
1017
|
+
const root = typeof args.root === "string"
|
|
1018
|
+
? path.resolve(args.root)
|
|
1019
|
+
: projectRoot;
|
|
1020
|
+
const prefix = root.endsWith("/") ? root : `${root}/`;
|
|
1021
|
+
const projectName = path.basename(root);
|
|
1022
|
+
try {
|
|
1023
|
+
const db = getVectorDb();
|
|
1024
|
+
const table = yield db.ensureTable();
|
|
1025
|
+
const rows = yield table
|
|
1026
|
+
.query()
|
|
1027
|
+
.select([
|
|
1028
|
+
"path",
|
|
1029
|
+
"role",
|
|
1030
|
+
"is_exported",
|
|
1031
|
+
"complexity",
|
|
1032
|
+
"defined_symbols",
|
|
1033
|
+
"referenced_symbols",
|
|
1034
|
+
])
|
|
1035
|
+
.where(`path LIKE '${(0, filter_builder_1.escapeSqlString)(prefix)}%'`)
|
|
1036
|
+
.limit(200000)
|
|
1037
|
+
.toArray();
|
|
1038
|
+
if (rows.length === 0) {
|
|
1039
|
+
return ok(`No indexed data found for ${root}. Run: gmax index --path ${root}`);
|
|
1040
|
+
}
|
|
1041
|
+
const files = new Set();
|
|
1042
|
+
const extCounts = new Map();
|
|
1043
|
+
const dirCounts = new Map();
|
|
1044
|
+
const roleCounts = new Map();
|
|
1045
|
+
const symbolRefs = new Map();
|
|
1046
|
+
const entryPoints = [];
|
|
1047
|
+
for (const row of rows) {
|
|
1048
|
+
const p = String(row.path || "");
|
|
1049
|
+
const role = String(row.role || "IMPLEMENTATION");
|
|
1050
|
+
const exported = Boolean(row.is_exported);
|
|
1051
|
+
const complexity = Number(row.complexity || 0);
|
|
1052
|
+
const defs = toStringArray(row.defined_symbols);
|
|
1053
|
+
const refs = toStringArray(row.referenced_symbols);
|
|
1054
|
+
files.add(p);
|
|
1055
|
+
const ext = path.extname(p).toLowerCase() || path.basename(p);
|
|
1056
|
+
extCounts.set(ext, (extCounts.get(ext) || 0) + 1);
|
|
1057
|
+
const rel = p.startsWith(prefix)
|
|
1058
|
+
? p.slice(prefix.length)
|
|
1059
|
+
: p;
|
|
1060
|
+
const parts = rel.split("/");
|
|
1061
|
+
const dir = parts.length > 2
|
|
1062
|
+
? `${parts.slice(0, 2).join("/")}/`
|
|
1063
|
+
: parts.length > 1
|
|
1064
|
+
? `${parts[0]}/`
|
|
1065
|
+
: "(root)";
|
|
1066
|
+
if (!dirCounts.has(dir)) {
|
|
1067
|
+
dirCounts.set(dir, { files: new Set(), chunks: 0 });
|
|
1068
|
+
}
|
|
1069
|
+
const dc = dirCounts.get(dir);
|
|
1070
|
+
dc.files.add(p);
|
|
1071
|
+
dc.chunks++;
|
|
1072
|
+
roleCounts.set(role, (roleCounts.get(role) || 0) + 1);
|
|
1073
|
+
for (const ref of refs) {
|
|
1074
|
+
symbolRefs.set(ref, (symbolRefs.get(ref) || 0) + 1);
|
|
1075
|
+
}
|
|
1076
|
+
if (exported &&
|
|
1077
|
+
role === "ORCHESTRATION" &&
|
|
1078
|
+
complexity >= 5 &&
|
|
1079
|
+
defs.length > 0) {
|
|
1080
|
+
const relPath = p.startsWith(prefix)
|
|
1081
|
+
? p.slice(prefix.length)
|
|
1082
|
+
: p;
|
|
1083
|
+
entryPoints.push({ symbol: defs[0], path: relPath });
|
|
1084
|
+
}
|
|
1085
|
+
}
|
|
1086
|
+
const lines = [];
|
|
1087
|
+
const projects = (0, project_registry_1.listProjects)();
|
|
1088
|
+
const proj = projects.find((p) => p.root === root);
|
|
1089
|
+
lines.push(`Project: ${projectName} (${root})`);
|
|
1090
|
+
lines.push(`Last indexed: ${(_a = proj === null || proj === void 0 ? void 0 : proj.lastIndexed) !== null && _a !== void 0 ? _a : "unknown"} • ${rows.length} chunks • ${files.size} files`);
|
|
1091
|
+
lines.push("");
|
|
1092
|
+
const extEntries = Array.from(extCounts.entries())
|
|
1093
|
+
.sort((a, b) => b[1] - a[1])
|
|
1094
|
+
.slice(0, 8);
|
|
1095
|
+
const langLine = extEntries
|
|
1096
|
+
.map(([ext, count]) => `${ext} (${Math.round((count / rows.length) * 100)}%)`)
|
|
1097
|
+
.join(", ");
|
|
1098
|
+
lines.push(`Languages: ${langLine}`);
|
|
1099
|
+
lines.push("");
|
|
1100
|
+
lines.push("Directory structure:");
|
|
1101
|
+
const dirEntries = Array.from(dirCounts.entries())
|
|
1102
|
+
.sort((a, b) => b[1].chunks - a[1].chunks)
|
|
1103
|
+
.slice(0, 12);
|
|
1104
|
+
for (const [dir, data] of dirEntries) {
|
|
1105
|
+
lines.push(` ${dir.padEnd(25)} (${data.files.size} files, ${data.chunks} chunks)`);
|
|
1106
|
+
}
|
|
1107
|
+
lines.push("");
|
|
1108
|
+
const roleEntries = Array.from(roleCounts.entries()).sort((a, b) => b[1] - a[1]);
|
|
1109
|
+
const roleLine = roleEntries
|
|
1110
|
+
.map(([role, count]) => `${Math.round((count / rows.length) * 100)}% ${role}`)
|
|
1111
|
+
.join(", ");
|
|
1112
|
+
lines.push(`Roles: ${roleLine}`);
|
|
1113
|
+
lines.push("");
|
|
1114
|
+
const topSymbols = Array.from(symbolRefs.entries())
|
|
1115
|
+
.sort((a, b) => b[1] - a[1])
|
|
1116
|
+
.slice(0, 8);
|
|
1117
|
+
if (topSymbols.length > 0) {
|
|
1118
|
+
lines.push("Key symbols (by reference count):");
|
|
1119
|
+
for (const [sym, count] of topSymbols) {
|
|
1120
|
+
lines.push(` ${sym.padEnd(25)} (referenced ${count}x)`);
|
|
1121
|
+
}
|
|
1122
|
+
lines.push("");
|
|
1123
|
+
}
|
|
1124
|
+
if (entryPoints.length > 0) {
|
|
1125
|
+
lines.push("Entry points (exported orchestration):");
|
|
1126
|
+
for (const ep of entryPoints.slice(0, 10)) {
|
|
1127
|
+
lines.push(` ${ep.symbol.padEnd(25)} ${ep.path}`);
|
|
1128
|
+
}
|
|
1129
|
+
}
|
|
1130
|
+
return ok(lines.join("\n"));
|
|
1131
|
+
}
|
|
1132
|
+
catch (e) {
|
|
1133
|
+
const msg = e instanceof Error ? e.message : String(e);
|
|
1134
|
+
return err(`Project summary failed: ${msg}`);
|
|
1135
|
+
}
|
|
1136
|
+
});
|
|
1137
|
+
}
|
|
1001
1138
|
// --- MCP server setup ---
|
|
1002
1139
|
const transport = new stdio_js_1.StdioServerTransport();
|
|
1003
1140
|
const server = new index_js_1.Server({
|
|
@@ -1031,6 +1168,8 @@ exports.mcp = new commander_1.Command("mcp")
|
|
|
1031
1168
|
return handleIndexStatus();
|
|
1032
1169
|
case "summarize_directory":
|
|
1033
1170
|
return handleSummarizeDirectory(toolArgs);
|
|
1171
|
+
case "summarize_project":
|
|
1172
|
+
return handleSummarizeProject(toolArgs);
|
|
1034
1173
|
default:
|
|
1035
1174
|
return err(`Unknown tool: ${name}`);
|
|
1036
1175
|
}
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: grepmax
|
|
3
3
|
description: Semantic code search. Use alongside grep - grep for exact strings, gmax for concepts.
|
|
4
|
-
allowed-tools: "mcp__grepmax__semantic_search, mcp__grepmax__search_all, mcp__grepmax__code_skeleton, mcp__grepmax__trace_calls, mcp__grepmax__list_symbols, mcp__grepmax__index_status, mcp__grepmax__summarize_directory, Bash(gmax:*), Read"
|
|
4
|
+
allowed-tools: "mcp__grepmax__semantic_search, mcp__grepmax__search_all, mcp__grepmax__code_skeleton, mcp__grepmax__trace_calls, mcp__grepmax__list_symbols, mcp__grepmax__index_status, mcp__grepmax__summarize_directory, mcp__grepmax__summarize_project, Bash(gmax:*), Read"
|
|
5
5
|
---
|
|
6
6
|
|
|
7
7
|
## What gmax does
|
|
@@ -79,6 +79,10 @@ List indexed symbols with definition locations, role, and export status.
|
|
|
79
79
|
|
|
80
80
|
Output: `symbolName [ORCH] exported src/path/file.ts:42`
|
|
81
81
|
|
|
82
|
+
### summarize_project
|
|
83
|
+
High-level project overview — languages, directory structure, role distribution, key symbols, entry points. Use when first exploring a new codebase.
|
|
84
|
+
- `root` (optional): Project root path. Defaults to current project.
|
|
85
|
+
|
|
82
86
|
### index_status
|
|
83
87
|
Check centralized index health — chunks, files, indexed directories, model info, watcher status.
|
|
84
88
|
|