grepmax 0.1.0 → 0.2.1

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.
Files changed (61) hide show
  1. package/LICENSE +1 -1
  2. package/NOTICE +2 -2
  3. package/README.md +72 -72
  4. package/dist/commands/claude-code.js +6 -6
  5. package/dist/commands/codex.js +17 -17
  6. package/dist/commands/doctor.js +6 -5
  7. package/dist/commands/droid.js +22 -22
  8. package/dist/commands/index.js +1 -1
  9. package/dist/commands/list.js +82 -19
  10. package/dist/commands/mcp.js +177 -158
  11. package/dist/commands/opencode.js +26 -26
  12. package/dist/commands/search.js +23 -13
  13. package/dist/commands/serve.js +30 -30
  14. package/dist/commands/setup.js +51 -40
  15. package/dist/commands/skeleton.js +19 -13
  16. package/dist/commands/symbols.js +40 -2
  17. package/dist/commands/verify.js +1 -1
  18. package/dist/commands/watch.js +206 -0
  19. package/dist/config.js +37 -7
  20. package/dist/eval.js +14 -14
  21. package/dist/index.js +11 -7
  22. package/dist/lib/core/languages.js +28 -0
  23. package/dist/lib/index/chunker.js +6 -3
  24. package/dist/lib/index/grammar-loader.js +2 -2
  25. package/dist/lib/index/ignore-patterns.js +1 -1
  26. package/dist/lib/index/index-config.js +50 -10
  27. package/dist/lib/index/sync-helpers.js +1 -1
  28. package/dist/lib/index/syncer.js +67 -45
  29. package/dist/lib/index/walker.js +3 -3
  30. package/dist/lib/index/watcher.js +4 -4
  31. package/dist/lib/output/formatter.js +1 -1
  32. package/dist/lib/search/searcher.js +9 -9
  33. package/dist/lib/setup/model-loader.js +3 -3
  34. package/dist/lib/setup/setup-helpers.js +2 -4
  35. package/dist/lib/skeleton/body-fields.js +20 -0
  36. package/dist/lib/skeleton/retriever.js +1 -1
  37. package/dist/lib/skeleton/skeletonizer.js +8 -2
  38. package/dist/lib/skeleton/summary-formatter.js +1 -4
  39. package/dist/lib/store/meta-cache.js +28 -3
  40. package/dist/lib/store/vector-db.js +17 -9
  41. package/dist/lib/utils/formatter.js +3 -3
  42. package/dist/lib/utils/lock.js +1 -1
  43. package/dist/lib/utils/project-registry.js +83 -0
  44. package/dist/lib/utils/project-root.js +32 -57
  45. package/dist/lib/utils/watcher-registry.js +100 -0
  46. package/dist/lib/workers/colbert-math.js +2 -2
  47. package/dist/lib/workers/download-worker.js +2 -2
  48. package/dist/lib/workers/embeddings/colbert.js +2 -2
  49. package/dist/lib/workers/embeddings/granite.js +4 -4
  50. package/dist/lib/workers/embeddings/mlx-client.js +1 -1
  51. package/dist/lib/workers/orchestrator.js +8 -8
  52. package/dist/lib/workers/pool.js +1 -1
  53. package/dist/lib/workers/worker.js +4 -1
  54. package/package.json +20 -21
  55. package/plugins/{osgrep → grepmax}/.claude-plugin/plugin.json +4 -4
  56. package/plugins/grepmax/hooks/start.js +63 -0
  57. package/plugins/grepmax/hooks/stop.js +3 -0
  58. package/plugins/{osgrep/skills/osgrep → grepmax/skills/gmax}/SKILL.md +11 -11
  59. package/plugins/osgrep/hooks/start.js +0 -90
  60. package/plugins/osgrep/hooks/stop.js +0 -3
  61. /package/plugins/{osgrep → grepmax}/hooks.json +0 -0
@@ -1,4 +1,37 @@
1
1
  "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
2
35
  var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
36
  function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
37
  return new (P || (P = Promise))(function (resolve, reject) {
@@ -10,6 +43,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
10
43
  };
11
44
  Object.defineProperty(exports, "__esModule", { value: true });
12
45
  exports.symbols = void 0;
46
+ const path = __importStar(require("node:path"));
13
47
  const commander_1 = require("commander");
14
48
  const vector_db_1 = require("../lib/store/vector-db");
15
49
  const exit_1 = require("../lib/utils/exit");
@@ -47,7 +81,11 @@ function collectSymbols(options) {
47
81
  // Fetch more rows to ensure we have enough after filtering/aggregation
48
82
  .limit(options.pattern ? 10000 : Math.max(options.limit * 50, 2000));
49
83
  if (options.pathPrefix) {
50
- query = query.where(`path LIKE '${(0, filter_builder_1.escapeSqlString)((0, filter_builder_1.normalizePath)(options.pathPrefix))}%'`);
84
+ // Resolve to absolute path for centralized index
85
+ const absPrefix = path.isAbsolute(options.pathPrefix)
86
+ ? options.pathPrefix
87
+ : path.resolve(options.projectRoot, options.pathPrefix);
88
+ query = query.where(`path LIKE '${(0, filter_builder_1.escapeSqlString)((0, filter_builder_1.normalizePath)(absPrefix))}%'`);
51
89
  }
52
90
  const rows = yield query.toArray();
53
91
  const map = new Map();
@@ -85,7 +123,7 @@ function collectSymbols(options) {
85
123
  }
86
124
  function formatTable(entries) {
87
125
  if (entries.length === 0) {
88
- return "No symbols found. Run `osgrep index` to build the index.";
126
+ return "No symbols found. Run `gmax index` to build the index.";
89
127
  }
90
128
  const rows = entries.map((e) => ({
91
129
  symbol: e.symbol,
@@ -47,7 +47,7 @@ const path = __importStar(require("node:path"));
47
47
  const transformers_1 = require("@huggingface/transformers");
48
48
  const ort = __importStar(require("onnxruntime-node"));
49
49
  // CONFIGURATION
50
- const MODEL_DIR = path.resolve("./osgrep-models/colbert"); // Adjust if your path differs
50
+ const MODEL_DIR = path.resolve("./gmax-models/colbert"); // Adjust if your path differs
51
51
  const MODEL_PATH = path.join(MODEL_DIR, "model.onnx");
52
52
  const SKIPLIST_PATH = path.join(MODEL_DIR, "skiplist.json");
53
53
  function main() {
@@ -0,0 +1,206 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
36
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
37
+ return new (P || (P = Promise))(function (resolve, reject) {
38
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
39
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
40
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
41
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
42
+ });
43
+ };
44
+ Object.defineProperty(exports, "__esModule", { value: true });
45
+ exports.watch = void 0;
46
+ const node_child_process_1 = require("node:child_process");
47
+ const fs = __importStar(require("node:fs"));
48
+ const path = __importStar(require("node:path"));
49
+ const commander_1 = require("commander");
50
+ const config_1 = require("../config");
51
+ const syncer_1 = require("../lib/index/syncer");
52
+ const watcher_1 = require("../lib/index/watcher");
53
+ const meta_cache_1 = require("../lib/store/meta-cache");
54
+ const vector_db_1 = require("../lib/store/vector-db");
55
+ const exit_1 = require("../lib/utils/exit");
56
+ const project_root_1 = require("../lib/utils/project-root");
57
+ const watcher_registry_1 = require("../lib/utils/watcher-registry");
58
+ const IDLE_TIMEOUT_MS = 30 * 60 * 1000; // 30 minutes
59
+ const IDLE_CHECK_INTERVAL_MS = 60 * 1000; // check every minute
60
+ exports.watch = new commander_1.Command("watch")
61
+ .description("Start background file watcher for live reindexing")
62
+ .option("-b, --background", "Run watcher in background and exit")
63
+ .option("--no-idle-timeout", "Disable the 30-minute idle shutdown")
64
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
65
+ var _a;
66
+ const projectRoot = (_a = (0, project_root_1.findProjectRoot)(process.cwd())) !== null && _a !== void 0 ? _a : process.cwd();
67
+ const projectName = path.basename(projectRoot);
68
+ // Check if watcher already running
69
+ const existing = (0, watcher_registry_1.getWatcherForProject)(projectRoot);
70
+ if (existing && (0, watcher_registry_1.isProcessRunning)(existing.pid)) {
71
+ console.log(`Watcher already running for ${projectName} (PID: ${existing.pid})`);
72
+ return;
73
+ }
74
+ // Background spawn
75
+ if (options.background) {
76
+ const args = process.argv
77
+ .slice(2)
78
+ .filter((arg) => arg !== "-b" && arg !== "--background");
79
+ const logDir = path.join(config_1.PATHS.globalRoot, "logs");
80
+ fs.mkdirSync(logDir, { recursive: true });
81
+ const safeName = projectName.replace(/[^a-zA-Z0-9._-]/g, "_");
82
+ const logFile = path.join(logDir, `watch-${safeName}.log`);
83
+ const out = fs.openSync(logFile, "a");
84
+ const child = (0, node_child_process_1.spawn)(process.argv[0], [process.argv[1], ...args], {
85
+ detached: true,
86
+ stdio: ["ignore", out, out],
87
+ cwd: process.cwd(),
88
+ env: Object.assign(Object.assign({}, process.env), { GMAX_BACKGROUND: "true" }),
89
+ });
90
+ child.unref();
91
+ console.log(`Watcher started for ${projectName} (PID: ${child.pid}, log: ${logFile})`);
92
+ process.exit(0);
93
+ }
94
+ // --- Foreground mode ---
95
+ const paths = (0, project_root_1.ensureProjectPaths)(projectRoot);
96
+ // Propagate project root to worker processes
97
+ process.env.GMAX_PROJECT_ROOT = paths.root;
98
+ console.log(`[watch:${projectName}] Starting...`);
99
+ // Initial sync if no index
100
+ const vectorDb = new vector_db_1.VectorDB(paths.lancedbDir);
101
+ if (!(yield vectorDb.hasAnyRows())) {
102
+ console.log(`[watch:${projectName}] No index found, running initial sync...`);
103
+ yield (0, syncer_1.initialSync)({ projectRoot });
104
+ console.log(`[watch:${projectName}] Initial sync complete.`);
105
+ }
106
+ // Open resources for watcher
107
+ const metaCache = new meta_cache_1.MetaCache(paths.lmdbPath);
108
+ // Register
109
+ (0, watcher_registry_1.registerWatcher)({
110
+ pid: process.pid,
111
+ projectRoot,
112
+ startTime: Date.now(),
113
+ });
114
+ // Start watching
115
+ const watcher = (0, watcher_1.startWatcher)({
116
+ projectRoot,
117
+ vectorDb,
118
+ metaCache,
119
+ dataDir: paths.dataDir,
120
+ onReindex: (files, ms) => {
121
+ console.log(`[watch:${projectName}] Reindexed ${files} file${files !== 1 ? "s" : ""} (${(ms / 1000).toFixed(1)}s)`);
122
+ lastActivity = Date.now();
123
+ },
124
+ });
125
+ console.log(`[watch:${projectName}] File watcher active`);
126
+ // Idle timeout
127
+ let lastActivity = Date.now();
128
+ if (options.idleTimeout !== false) {
129
+ setInterval(() => {
130
+ if (Date.now() - lastActivity > IDLE_TIMEOUT_MS) {
131
+ console.log(`[watch:${projectName}] Idle for 30 minutes, shutting down`);
132
+ shutdown();
133
+ }
134
+ }, IDLE_CHECK_INTERVAL_MS);
135
+ }
136
+ // Graceful shutdown
137
+ function shutdown() {
138
+ return __awaiter(this, void 0, void 0, function* () {
139
+ try {
140
+ yield watcher.close();
141
+ }
142
+ catch (_a) { }
143
+ metaCache.close();
144
+ yield vectorDb.close();
145
+ (0, watcher_registry_1.unregisterWatcher)(process.pid);
146
+ yield (0, exit_1.gracefulExit)();
147
+ });
148
+ }
149
+ process.on("SIGINT", shutdown);
150
+ process.on("SIGTERM", shutdown);
151
+ }));
152
+ // --- Subcommands ---
153
+ exports.watch
154
+ .command("status")
155
+ .description("Show running watchers")
156
+ .action(() => __awaiter(void 0, void 0, void 0, function* () {
157
+ const watchers = (0, watcher_registry_1.listWatchers)();
158
+ if (watchers.length === 0) {
159
+ console.log("No running watchers.");
160
+ yield (0, exit_1.gracefulExit)();
161
+ return;
162
+ }
163
+ console.log("Running watchers:");
164
+ for (const w of watchers) {
165
+ const age = Math.floor((Date.now() - w.startTime) / 60000);
166
+ console.log(`- PID: ${w.pid} | Root: ${w.projectRoot} | Running: ${age}m`);
167
+ }
168
+ yield (0, exit_1.gracefulExit)();
169
+ }));
170
+ exports.watch
171
+ .command("stop")
172
+ .description("Stop watcher for current project")
173
+ .option("--all", "Stop all running watchers")
174
+ .action((options) => __awaiter(void 0, void 0, void 0, function* () {
175
+ var _a;
176
+ if (options.all) {
177
+ const watchers = (0, watcher_registry_1.listWatchers)();
178
+ for (const w of watchers) {
179
+ try {
180
+ process.kill(w.pid, "SIGTERM");
181
+ (0, watcher_registry_1.unregisterWatcher)(w.pid);
182
+ }
183
+ catch (_b) { }
184
+ }
185
+ console.log(`Stopped ${watchers.length} watcher(s).`);
186
+ yield (0, exit_1.gracefulExit)();
187
+ return;
188
+ }
189
+ const projectRoot = (_a = (0, project_root_1.findProjectRoot)(process.cwd())) !== null && _a !== void 0 ? _a : process.cwd();
190
+ const watcher = (0, watcher_registry_1.getWatcherForProject)(projectRoot);
191
+ if (!watcher) {
192
+ console.log("No watcher running for this project.");
193
+ yield (0, exit_1.gracefulExit)();
194
+ return;
195
+ }
196
+ try {
197
+ process.kill(watcher.pid, "SIGTERM");
198
+ (0, watcher_registry_1.unregisterWatcher)(watcher.pid);
199
+ console.log(`Stopped watcher (PID: ${watcher.pid})`);
200
+ }
201
+ catch (_c) {
202
+ console.log("Watcher process not found.");
203
+ (0, watcher_registry_1.unregisterWatcher)(watcher.pid);
204
+ }
205
+ yield (0, exit_1.gracefulExit)();
206
+ }));
package/dist/config.js CHANGED
@@ -33,16 +33,35 @@ var __importStar = (this && this.__importStar) || (function () {
33
33
  };
34
34
  })();
35
35
  Object.defineProperty(exports, "__esModule", { value: true });
36
- exports.INDEXABLE_EXTENSIONS = exports.MAX_FILE_SIZE_BYTES = exports.PATHS = exports.MAX_WORKER_MEMORY_MB = exports.WORKER_BOOT_TIMEOUT_MS = exports.WORKER_TIMEOUT_MS = exports.CONFIG = exports.MODEL_IDS = void 0;
36
+ exports.INDEXABLE_EXTENSIONS = exports.MAX_FILE_SIZE_BYTES = exports.PATHS = exports.MAX_WORKER_MEMORY_MB = exports.WORKER_BOOT_TIMEOUT_MS = exports.WORKER_TIMEOUT_MS = exports.CONFIG = exports.MODEL_IDS = exports.DEFAULT_MODEL_TIER = exports.MODEL_TIERS = void 0;
37
37
  const os = __importStar(require("node:os"));
38
38
  const path = __importStar(require("node:path"));
39
+ exports.MODEL_TIERS = {
40
+ small: {
41
+ id: "small",
42
+ label: "granite-small (384d, 47M params, fast)",
43
+ onnxModel: "onnx-community/granite-embedding-small-english-r2-ONNX",
44
+ mlxModel: "ibm-granite/granite-embedding-small-english-r2",
45
+ vectorDim: 384,
46
+ params: "47M",
47
+ },
48
+ standard: {
49
+ id: "standard",
50
+ label: "granite-r2 (768d, 149M params, better quality)",
51
+ onnxModel: "onnx-community/granite-embedding-english-r2-ONNX",
52
+ mlxModel: "ibm-granite/granite-embedding-english-r2",
53
+ vectorDim: 768,
54
+ params: "149M",
55
+ },
56
+ };
57
+ exports.DEFAULT_MODEL_TIER = "small";
39
58
  exports.MODEL_IDS = {
40
- embed: "onnx-community/granite-embedding-small-english-r2-ONNX",
59
+ embed: exports.MODEL_TIERS[exports.DEFAULT_MODEL_TIER].onnxModel,
41
60
  colbert: "ryandono/mxbai-edge-colbert-v0-17m-onnx-int8",
42
61
  };
43
62
  const DEFAULT_WORKER_THREADS = (() => {
44
63
  var _a;
45
- const fromEnv = Number.parseInt((_a = process.env.OSGREP_WORKER_THREADS) !== null && _a !== void 0 ? _a : "", 10);
64
+ const fromEnv = Number.parseInt((_a = process.env.GMAX_WORKER_THREADS) !== null && _a !== void 0 ? _a : "", 10);
46
65
  if (Number.isFinite(fromEnv) && fromEnv > 0)
47
66
  return fromEnv;
48
67
  const cores = os.cpus().length || 1;
@@ -58,16 +77,22 @@ exports.CONFIG = {
58
77
  WORKER_THREADS: DEFAULT_WORKER_THREADS,
59
78
  QUERY_PREFIX: "",
60
79
  };
61
- exports.WORKER_TIMEOUT_MS = Number.parseInt(process.env.OSGREP_WORKER_TIMEOUT_MS || "60000", 10);
62
- exports.WORKER_BOOT_TIMEOUT_MS = Number.parseInt(process.env.OSGREP_WORKER_BOOT_TIMEOUT_MS || "300000", 10);
63
- exports.MAX_WORKER_MEMORY_MB = Number.parseInt(process.env.OSGREP_MAX_WORKER_MEMORY_MB ||
80
+ exports.WORKER_TIMEOUT_MS = Number.parseInt(process.env.GMAX_WORKER_TIMEOUT_MS || "60000", 10);
81
+ exports.WORKER_BOOT_TIMEOUT_MS = Number.parseInt(process.env.GMAX_WORKER_BOOT_TIMEOUT_MS || "300000", 10);
82
+ exports.MAX_WORKER_MEMORY_MB = Number.parseInt(process.env.GMAX_MAX_WORKER_MEMORY_MB ||
64
83
  String(Math.max(2048, Math.floor((os.totalmem() / 1024 / 1024) * 0.5))), 10);
65
84
  const HOME = os.homedir();
66
- const GLOBAL_ROOT = path.join(HOME, ".osgrep");
85
+ const GLOBAL_ROOT = path.join(HOME, ".gmax");
67
86
  exports.PATHS = {
68
87
  globalRoot: GLOBAL_ROOT,
69
88
  models: path.join(GLOBAL_ROOT, "models"),
70
89
  grammars: path.join(GLOBAL_ROOT, "grammars"),
90
+ // Centralized index storage — one database for all indexed directories
91
+ lancedbDir: path.join(GLOBAL_ROOT, "lancedb"),
92
+ cacheDir: path.join(GLOBAL_ROOT, "cache"),
93
+ lmdbPath: path.join(GLOBAL_ROOT, "cache", "meta.lmdb"),
94
+ configPath: path.join(GLOBAL_ROOT, "config.json"),
95
+ lockDir: GLOBAL_ROOT,
71
96
  };
72
97
  exports.MAX_FILE_SIZE_BYTES = 1024 * 1024 * 2; // 2MB limit for indexing
73
98
  // Extensions we consider for indexing to avoid binary noise and improve relevance.
@@ -76,12 +101,16 @@ exports.INDEXABLE_EXTENSIONS = new Set([
76
101
  ".tsx",
77
102
  ".js",
78
103
  ".jsx",
104
+ ".mjs",
105
+ ".cjs",
79
106
  ".py",
80
107
  ".go",
81
108
  ".rs",
82
109
  ".java",
83
110
  ".c",
84
111
  ".cpp",
112
+ ".cc",
113
+ ".cxx",
85
114
  ".h",
86
115
  ".hpp",
87
116
  ".rb",
@@ -91,6 +120,7 @@ exports.INDEXABLE_EXTENSIONS = new Set([
91
120
  ".kt",
92
121
  ".kts",
93
122
  ".scala",
123
+ ".sc",
94
124
  ".lua",
95
125
  ".sh",
96
126
  ".sql",
package/dist/eval.js CHANGED
@@ -14,7 +14,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
14
14
  exports.cases = void 0;
15
15
  exports.evaluateCase = evaluateCase;
16
16
  // Reduce worker pool fan-out during eval to avoid ONNX concurrency issues
17
- (_a = (_b = process.env).OSGREP_WORKER_COUNT) !== null && _a !== void 0 ? _a : (_b.OSGREP_WORKER_COUNT = "1");
17
+ (_a = (_b = process.env).GMAX_WORKER_COUNT) !== null && _a !== void 0 ? _a : (_b.GMAX_WORKER_COUNT = "1");
18
18
  const searcher_1 = require("./lib/search/searcher");
19
19
  const vector_db_1 = require("./lib/store/vector-db");
20
20
  const exit_1 = require("./lib/utils/exit");
@@ -231,7 +231,7 @@ exports.cases = [
231
231
  note: "Request body guard that 413s payloads over 1MB.",
232
232
  },
233
233
  {
234
- query: "How does serve --background redirect logs to ~/.osgrep/logs/server.log?",
234
+ query: "How does serve --background redirect logs to ~/.gmax/logs/server.log?",
235
235
  expectedPath: "src/commands/serve.ts",
236
236
  note: "Background flag redirecting stdio to server.log.",
237
237
  },
@@ -252,19 +252,19 @@ exports.cases = [
252
252
  },
253
253
  // --- Paths, Config, Environment ---
254
254
  {
255
- query: "How do we create .osgrep directories and add them to .gitignore?",
255
+ query: "How do we create .gmax directories and add them to .gitignore?",
256
256
  expectedPath: "src/lib/utils/project-root.ts",
257
257
  note: "ensureProjectPaths scaffolds directories and gitignore entry.",
258
258
  },
259
259
  {
260
- query: "How is the project root detected via .git or existing .osgrep?",
260
+ query: "How is the project root detected via .git or existing .gmax?",
261
261
  expectedPath: "src/lib/utils/project-root.ts",
262
262
  note: "findProjectRoot walking parents and honoring repo roots.",
263
263
  },
264
264
  {
265
265
  query: "Where are PATHS.globalRoot, models, and grammars defined?",
266
266
  expectedPath: "src/config.ts",
267
- note: "PATHS pointing to ~/.osgrep directories.",
267
+ note: "PATHS pointing to ~/.gmax directories.",
268
268
  },
269
269
  {
270
270
  query: "How do workers prefer a local ./models directory when present?",
@@ -278,17 +278,17 @@ exports.cases = [
278
278
  },
279
279
  // --- Extended Coverage ---
280
280
  {
281
- query: "Where do we read WORKER_TIMEOUT_MS from OSGREP_WORKER_TIMEOUT_MS?",
281
+ query: "Where do we read WORKER_TIMEOUT_MS from GMAX_WORKER_TIMEOUT_MS?",
282
282
  expectedPath: "src/config.ts",
283
283
  note: "WORKER_TIMEOUT_MS env override.",
284
284
  },
285
285
  {
286
286
  query: "Where is TASK_TIMEOUT_MS set for worker tasks?",
287
287
  expectedPath: "src/lib/workers/pool.ts",
288
- note: "OSGREP_WORKER_TASK_TIMEOUT_MS guarded timeout.",
288
+ note: "GMAX_WORKER_TASK_TIMEOUT_MS guarded timeout.",
289
289
  },
290
290
  {
291
- query: "How do we cap worker threads from OSGREP_WORKER_THREADS with a HARD_CAP of 4?",
291
+ query: "How do we cap worker threads from GMAX_WORKER_THREADS with a HARD_CAP of 4?",
292
292
  expectedPath: "src/config.ts",
293
293
  note: "DEFAULT_WORKER_THREADS calculation.",
294
294
  },
@@ -343,7 +343,7 @@ exports.cases = [
343
343
  note: "splitIfTooBig uses OVERLAP_LINES and OVERLAP_CHARS.",
344
344
  },
345
345
  {
346
- query: "Where is GRAMMARS_DIR set to ~/.osgrep/grammars?",
346
+ query: "Where is GRAMMARS_DIR set to ~/.gmax/grammars?",
347
347
  expectedPath: "src/lib/index/grammar-loader.ts",
348
348
  note: "GRAMMARS_DIR constant.",
349
349
  },
@@ -428,7 +428,7 @@ exports.cases = [
428
428
  note: "createIndexingSpinner onProgress formatting.",
429
429
  },
430
430
  {
431
- query: "Where does ensureSetup create ~/.osgrep directories with ora spinner?",
431
+ query: "Where does ensureSetup create ~/.gmax directories with ora spinner?",
432
432
  expectedPath: "src/lib/setup/setup-helpers.ts",
433
433
  note: "ensureSetup directory creation feedback.",
434
434
  },
@@ -465,7 +465,7 @@ exports.cases = [
465
465
  {
466
466
  query: "Where does serve register running servers to servers.json?",
467
467
  expectedPath: "src/lib/utils/server-registry.ts",
468
- note: "registerServer writes to ~/.osgrep/servers.json.",
468
+ note: "registerServer writes to ~/.gmax/servers.json.",
469
469
  },
470
470
  {
471
471
  query: "How does serve status enumerate active servers?",
@@ -555,7 +555,7 @@ function run() {
555
555
  const hasRows = yield vectorDb.hasAnyRows();
556
556
  if (!hasRows) {
557
557
  console.error(`❌ Store appears to be empty!`);
558
- console.error(` Run "osgrep index" to populate the store with data.`);
558
+ console.error(` Run "gmax index" to populate the store with data.`);
559
559
  process.exit(1);
560
560
  }
561
561
  // 2. Check if store has data (redundant but good for sanity)
@@ -563,7 +563,7 @@ function run() {
563
563
  const testResult = yield searcher.search("test", 1, { rerank: true });
564
564
  if (testResult.data.length === 0) {
565
565
  console.error(`⚠️ Store appears to be empty (search returned 0 results)!`);
566
- console.error(` Run "osgrep index" to populate the store with data.`);
566
+ console.error(` Run "gmax index" to populate the store with data.`);
567
567
  process.exit(1);
568
568
  }
569
569
  }
@@ -610,7 +610,7 @@ function run() {
610
610
  if (
611
611
  // Only auto-run when executed directly (not when imported for experiments/tests)
612
612
  require.main === module &&
613
- process.env.OSGREP_EVAL_AUTORUN !== "0") {
613
+ process.env.GMAX_EVAL_AUTORUN !== "0") {
614
614
  run().catch((err) => {
615
615
  console.error("Eval failed:", err);
616
616
  (0, exit_1.gracefulExit)(1);
package/dist/index.js CHANGED
@@ -51,17 +51,20 @@ const setup_1 = require("./commands/setup");
51
51
  const skeleton_1 = require("./commands/skeleton");
52
52
  const symbols_1 = require("./commands/symbols");
53
53
  const trace_1 = require("./commands/trace");
54
+ const watch_1 = require("./commands/watch");
54
55
  commander_1.program
55
56
  .version(JSON.parse(fs.readFileSync(path.join(__dirname, "../package.json"), {
56
57
  encoding: "utf-8",
57
58
  })).version)
58
- .option("--store <string>", "The store to use (auto-detected if not specified)", process.env.OSGREP_STORE || undefined);
59
- const legacyDataPath = path.join(require("node:os").homedir(), ".osgrep", "data");
60
- const isIndexCommand = process.argv.some((arg) => arg === "index");
61
- if (isIndexCommand && fs.existsSync(legacyDataPath)) {
62
- console.log("⚠️ Legacy global database detected at ~/.osgrep/data.");
63
- console.log(" osgrep now uses per-project .osgrep/ directories.");
64
- console.log(" Run 'osgrep index' in your project root to create a new index.");
59
+ .option("--store <string>", "The store to use (auto-detected if not specified)", process.env.GMAX_STORE || undefined);
60
+ // Detect legacy per-project .gmax/ or .osgrep/ directories
61
+ const legacyProjectData = [".gmax", ".osgrep"]
62
+ .map((d) => path.join(process.cwd(), d))
63
+ .find((d) => fs.existsSync(path.join(d, "lancedb")));
64
+ if (legacyProjectData) {
65
+ console.log(`⚠️ Legacy per-project index detected at ${legacyProjectData}`);
66
+ console.log(" gmax now uses a centralized index at ~/.gmax/lancedb/.");
67
+ console.log(" Run 'gmax index' to re-index into the centralized store.");
65
68
  }
66
69
  commander_1.program.addCommand(search_1.search, { isDefault: true });
67
70
  commander_1.program.addCommand(index_1.index);
@@ -71,6 +74,7 @@ commander_1.program.addCommand(symbols_1.symbols);
71
74
  commander_1.program.addCommand(trace_1.trace);
72
75
  commander_1.program.addCommand(setup_1.setup);
73
76
  commander_1.program.addCommand(serve_1.serve);
77
+ commander_1.program.addCommand(watch_1.watch);
74
78
  commander_1.program.addCommand(mcp_1.mcp);
75
79
  commander_1.program.addCommand(claude_code_1.installClaudeCode);
76
80
  commander_1.program.addCommand(codex_1.installCodex);
@@ -196,6 +196,29 @@ exports.LANGUAGES = [
196
196
  "object_declaration", // object singletons, companion objects
197
197
  ],
198
198
  },
199
+ {
200
+ id: "scala",
201
+ extensions: [".scala", ".sc"],
202
+ grammar: {
203
+ name: "scala",
204
+ url: "https://github.com/tree-sitter/tree-sitter-scala/releases/download/v0.25.0/tree-sitter-scala.wasm",
205
+ },
206
+ definitionTypes: [
207
+ "function_definition",
208
+ "class_definition",
209
+ "object_definition",
210
+ "trait_definition",
211
+ ],
212
+ },
213
+ {
214
+ id: "lua",
215
+ extensions: [".lua"],
216
+ grammar: {
217
+ name: "lua",
218
+ url: "https://github.com/tree-sitter-grammars/tree-sitter-lua/releases/download/v0.5.0/tree-sitter-lua.wasm",
219
+ },
220
+ definitionTypes: ["function_declaration"],
221
+ },
199
222
  {
200
223
  id: "json",
201
224
  extensions: [".json"],
@@ -224,6 +247,11 @@ exports.LANGUAGES = [
224
247
  {
225
248
  id: "bash",
226
249
  extensions: [".sh"],
250
+ grammar: {
251
+ name: "bash",
252
+ url: "https://github.com/tree-sitter/tree-sitter-bash/releases/download/v0.25.1/tree-sitter-bash.wasm",
253
+ },
254
+ definitionTypes: ["function_definition"],
227
255
  },
228
256
  ];
229
257
  function getLanguageByExtension(ext) {
@@ -190,7 +190,7 @@ class TreeSitterChunker {
190
190
  return cached;
191
191
  const wasmPath = path.join(grammar_loader_1.GRAMMARS_DIR, `tree-sitter-${lang}.wasm`);
192
192
  if (!fs.existsSync(wasmPath)) {
193
- console.warn(`⚠️ Missing grammar for ${lang}. Run 'osgrep setup' to download it. Using fallback chunking.`);
193
+ console.warn(`⚠️ Missing grammar for ${lang}. Run 'gmax setup' to download it. Using fallback chunking.`);
194
194
  this.languages.set(lang, null);
195
195
  return null;
196
196
  }
@@ -352,6 +352,7 @@ class TreeSitterChunker {
352
352
  "type_identifier",
353
353
  "field_identifier",
354
354
  "simple_identifier", // Swift, Kotlin
355
+ "word", // Bash
355
356
  ].includes(c.type));
356
357
  if (identifierChild === null || identifierChild === void 0 ? void 0 : identifierChild.text)
357
358
  return String(identifierChild.text);
@@ -483,8 +484,10 @@ class TreeSitterChunker {
483
484
  const referencedSymbols = [];
484
485
  const extractRefs = (n) => {
485
486
  var _a, _b, _c, _d;
486
- // Handle JS/TS (call_expression) and Python (call)
487
- if (n.type === "call_expression" || n.type === "call") {
487
+ // Handle JS/TS (call_expression), Python (call), Lua (function_call)
488
+ if (n.type === "call_expression" ||
489
+ n.type === "call" ||
490
+ n.type === "function_call") {
488
491
  const func = n.childForFieldName
489
492
  ? n.childForFieldName("function")
490
493
  : null;
@@ -48,7 +48,7 @@ const fs = __importStar(require("node:fs"));
48
48
  const os = __importStar(require("node:os"));
49
49
  const path = __importStar(require("node:path"));
50
50
  const languages_1 = require("../core/languages");
51
- exports.GRAMMARS_DIR = path.join(os.homedir(), ".osgrep", "grammars");
51
+ exports.GRAMMARS_DIR = path.join(os.homedir(), ".gmax", "grammars");
52
52
  const GRAMMAR_URLS = {};
53
53
  for (const lang of languages_1.LANGUAGES) {
54
54
  if (lang.grammar) {
@@ -58,7 +58,7 @@ for (const lang of languages_1.LANGUAGES) {
58
58
  const downloadFile = (url, dest) => __awaiter(void 0, void 0, void 0, function* () {
59
59
  const response = yield fetch(url, {
60
60
  headers: {
61
- "User-Agent": "osgrep",
61
+ "User-Agent": "gmax",
62
62
  },
63
63
  });
64
64
  if (!response.ok)
@@ -9,7 +9,7 @@ exports.DEFAULT_IGNORE_PATTERNS = [
9
9
  "*.ipynb",
10
10
  "*.pyc",
11
11
  "*.onnx",
12
- // Non-code text files (osgrep is for CODE search)
12
+ // Non-code text files (gmax is for CODE search)
13
13
  "*.txt",
14
14
  "*.log",
15
15
  "*.csv",