@wb200/mgrep 0.1.10

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 (46) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +288 -0
  3. package/dist/commands/login.js +28 -0
  4. package/dist/commands/login.js.map +1 -0
  5. package/dist/commands/search.js +191 -0
  6. package/dist/commands/search.js.map +1 -0
  7. package/dist/commands/watch.js +134 -0
  8. package/dist/commands/watch.js.map +1 -0
  9. package/dist/commands/watch_mcp.js +77 -0
  10. package/dist/commands/watch_mcp.js.map +1 -0
  11. package/dist/index.js +36 -0
  12. package/dist/index.js.map +1 -0
  13. package/dist/install/claude-code.js +71 -0
  14. package/dist/install/claude-code.js.map +1 -0
  15. package/dist/install/codex.js +116 -0
  16. package/dist/install/codex.js.map +1 -0
  17. package/dist/install/droid.js +191 -0
  18. package/dist/install/droid.js.map +1 -0
  19. package/dist/install/opencode.js +161 -0
  20. package/dist/install/opencode.js.map +1 -0
  21. package/dist/lib/config.js +216 -0
  22. package/dist/lib/config.js.map +1 -0
  23. package/dist/lib/context.js +35 -0
  24. package/dist/lib/context.js.map +1 -0
  25. package/dist/lib/file.js +154 -0
  26. package/dist/lib/file.js.map +1 -0
  27. package/dist/lib/git.js +167 -0
  28. package/dist/lib/git.js.map +1 -0
  29. package/dist/lib/logger.js +80 -0
  30. package/dist/lib/logger.js.map +1 -0
  31. package/dist/lib/model-studio.js +205 -0
  32. package/dist/lib/model-studio.js.map +1 -0
  33. package/dist/lib/store.js +639 -0
  34. package/dist/lib/store.js.map +1 -0
  35. package/dist/lib/sync-helpers.js +51 -0
  36. package/dist/lib/sync-helpers.js.map +1 -0
  37. package/dist/lib/utils.js +300 -0
  38. package/dist/lib/utils.js.map +1 -0
  39. package/dist/lib/warning.js +34 -0
  40. package/dist/lib/warning.js.map +1 -0
  41. package/dist/plugins/mgrep/.claude-plugin/plugin.json +9 -0
  42. package/dist/plugins/mgrep/hooks/hook.json +27 -0
  43. package/dist/plugins/mgrep/hooks/mgrep_watch.py +55 -0
  44. package/dist/plugins/mgrep/hooks/mgrep_watch_kill.py +50 -0
  45. package/dist/plugins/mgrep/skills/mgrep/SKILL.md +59 -0
  46. package/package.json +74 -0
@@ -0,0 +1,216 @@
1
+ import * as fs from "node:fs";
2
+ import * as os from "node:os";
3
+ import * as path from "node:path";
4
+ import YAML from "yaml";
5
+ import { z } from "zod";
6
+ const LOCAL_CONFIG_FILES = [".mgreprc.yaml", ".mgreprc.yml"];
7
+ const GLOBAL_CONFIG_DIR = ".config/mgrep";
8
+ const GLOBAL_CONFIG_FILES = ["config.yaml", "config.yml"];
9
+ const ENV_PREFIX = "MGREP_";
10
+ const DEFAULT_MAX_FILE_SIZE = 4 * 1024 * 1024;
11
+ const DEFAULT_MAX_FILE_COUNT = 10000;
12
+ const DEFAULT_LANCEDB_PATH = path.join(os.homedir(), ".mgrep", "lancedb");
13
+ const DEFAULT_SYNC_CONCURRENCY = 20;
14
+ const DEFAULT_EMBED_MODEL = "Qwen/Qwen3-Embedding-4B";
15
+ const DEFAULT_EMBED_DIMENSIONS = 2560;
16
+ const DEFAULT_RERANK_MODEL = "Qwen/Qwen3-Reranker-4B";
17
+ const DEFAULT_LLM_MODEL = "qwen3.5-plus";
18
+ const ConfigSchema = z.object({
19
+ maxFileSize: z.number().positive().optional(),
20
+ maxFileCount: z.number().positive().optional(),
21
+ syncConcurrency: z.number().positive().optional(),
22
+ lancedbPath: z.string().min(1).optional(),
23
+ embedModel: z.string().min(1).optional(),
24
+ embedDimensions: z.number().positive().optional(),
25
+ rerankModel: z.string().min(1).optional(),
26
+ llmModel: z.string().min(1).optional(),
27
+ });
28
+ const DEFAULT_CONFIG = {
29
+ maxFileSize: DEFAULT_MAX_FILE_SIZE,
30
+ maxFileCount: DEFAULT_MAX_FILE_COUNT,
31
+ syncConcurrency: DEFAULT_SYNC_CONCURRENCY,
32
+ lancedbPath: DEFAULT_LANCEDB_PATH,
33
+ embedModel: DEFAULT_EMBED_MODEL,
34
+ embedDimensions: DEFAULT_EMBED_DIMENSIONS,
35
+ rerankModel: DEFAULT_RERANK_MODEL,
36
+ llmModel: DEFAULT_LLM_MODEL,
37
+ };
38
+ const configCache = new Map();
39
+ /**
40
+ * Reads and parses a YAML config file
41
+ *
42
+ * @param filePath - The path to the config file
43
+ * @returns The parsed config object or null if file doesn't exist or is invalid
44
+ */
45
+ function readYamlConfig(filePath) {
46
+ if (!fs.existsSync(filePath)) {
47
+ return null;
48
+ }
49
+ try {
50
+ const content = fs.readFileSync(filePath, "utf-8");
51
+ const parsed = YAML.parse(content);
52
+ const validated = ConfigSchema.parse(parsed);
53
+ return validated;
54
+ }
55
+ catch (error) {
56
+ const message = error instanceof Error ? error.message : String(error);
57
+ console.warn(`Warning: Failed to parse config file ${filePath}: ${message}`);
58
+ return null;
59
+ }
60
+ }
61
+ /**
62
+ * Finds and reads the first existing config file from a list of candidates
63
+ *
64
+ * @param candidates - List of file paths to check
65
+ * @returns The parsed config or null if none found
66
+ */
67
+ function findConfig(candidates) {
68
+ for (const filePath of candidates) {
69
+ const config = readYamlConfig(filePath);
70
+ if (config !== null) {
71
+ return config;
72
+ }
73
+ }
74
+ return null;
75
+ }
76
+ function getGlobalConfigPaths() {
77
+ const configDir = path.join(os.homedir(), GLOBAL_CONFIG_DIR);
78
+ return GLOBAL_CONFIG_FILES.map((file) => path.join(configDir, file));
79
+ }
80
+ function getLocalConfigPaths(dir) {
81
+ return LOCAL_CONFIG_FILES.map((file) => path.join(dir, file));
82
+ }
83
+ /**
84
+ * Loads configuration from environment variables
85
+ *
86
+ * @returns The config values from environment variables
87
+ */
88
+ function loadEnvConfig() {
89
+ const config = {};
90
+ const maxFileSizeEnv = process.env[`${ENV_PREFIX}MAX_FILE_SIZE`];
91
+ if (maxFileSizeEnv) {
92
+ const parsed = Number.parseInt(maxFileSizeEnv, 10);
93
+ if (!Number.isNaN(parsed) && parsed > 0) {
94
+ config.maxFileSize = parsed;
95
+ }
96
+ }
97
+ const maxFileCountEnv = process.env[`${ENV_PREFIX}MAX_FILE_COUNT`];
98
+ if (maxFileCountEnv) {
99
+ const parsed = Number.parseInt(maxFileCountEnv, 10);
100
+ if (!Number.isNaN(parsed) && parsed > 0) {
101
+ config.maxFileCount = parsed;
102
+ }
103
+ }
104
+ const syncConcurrencyEnv = process.env[`${ENV_PREFIX}SYNC_CONCURRENCY`];
105
+ if (syncConcurrencyEnv) {
106
+ const parsed = Number.parseInt(syncConcurrencyEnv, 10);
107
+ if (!Number.isNaN(parsed) && parsed > 0) {
108
+ config.syncConcurrency = parsed;
109
+ }
110
+ }
111
+ const lancedbPathEnv = process.env[`${ENV_PREFIX}LANCEDB_PATH`];
112
+ if (lancedbPathEnv) {
113
+ config.lancedbPath = lancedbPathEnv;
114
+ }
115
+ const embedModelEnv = process.env[`${ENV_PREFIX}EMBED_MODEL`];
116
+ if (embedModelEnv) {
117
+ config.embedModel = embedModelEnv;
118
+ }
119
+ const embedDimensionsEnv = process.env[`${ENV_PREFIX}EMBED_DIMENSIONS`];
120
+ if (embedDimensionsEnv) {
121
+ const parsed = Number.parseInt(embedDimensionsEnv, 10);
122
+ if (!Number.isNaN(parsed) && parsed > 0) {
123
+ config.embedDimensions = parsed;
124
+ }
125
+ }
126
+ const rerankModelEnv = process.env[`${ENV_PREFIX}RERANK_MODEL`];
127
+ if (rerankModelEnv) {
128
+ config.rerankModel = rerankModelEnv;
129
+ }
130
+ const llmModelEnv = process.env[`${ENV_PREFIX}LLM_MODEL`];
131
+ if (llmModelEnv) {
132
+ config.llmModel = llmModelEnv;
133
+ }
134
+ return config;
135
+ }
136
+ /**
137
+ * Loads mgrep configuration with the following precedence (highest to lowest):
138
+ * 1. CLI flags (passed as cliOptions)
139
+ * 2. Environment variables (MGREP_MAX_FILE_SIZE, MGREP_MAX_FILE_COUNT)
140
+ * 3. Local config file (.mgreprc.yaml or .mgreprc.yml in project directory)
141
+ * 4. Global config file (~/.config/mgrep/config.yaml or config.yml)
142
+ * 5. Default values
143
+ *
144
+ * @param dir - The directory to load local configuration from
145
+ * @param cliOptions - CLI options that override all other config sources
146
+ * @returns The merged configuration
147
+ */
148
+ export function loadConfig(dir, cliOptions = {}) {
149
+ const absoluteDir = path.resolve(dir);
150
+ const cacheKey = `${absoluteDir}:${JSON.stringify(cliOptions)}`;
151
+ if (configCache.has(cacheKey)) {
152
+ return configCache.get(cacheKey);
153
+ }
154
+ const globalConfig = findConfig(getGlobalConfigPaths());
155
+ const localConfig = findConfig(getLocalConfigPaths(absoluteDir));
156
+ const envConfig = loadEnvConfig();
157
+ const config = {
158
+ ...DEFAULT_CONFIG,
159
+ ...globalConfig,
160
+ ...localConfig,
161
+ ...envConfig,
162
+ ...filterUndefinedCliOptions(cliOptions),
163
+ };
164
+ configCache.set(cacheKey, config);
165
+ return config;
166
+ }
167
+ function filterUndefinedCliOptions(options) {
168
+ const result = {};
169
+ if (options.maxFileSize !== undefined) {
170
+ result.maxFileSize = options.maxFileSize;
171
+ }
172
+ if (options.maxFileCount !== undefined) {
173
+ result.maxFileCount = options.maxFileCount;
174
+ }
175
+ return result;
176
+ }
177
+ /**
178
+ * Clears the configuration cache.
179
+ * Useful for testing or when config files may have changed.
180
+ */
181
+ export function clearConfigCache() {
182
+ configCache.clear();
183
+ }
184
+ /**
185
+ * Checks if a file exceeds the maximum allowed file size
186
+ *
187
+ * @param filePath - The path to the file to check
188
+ * @param maxFileSize - The maximum allowed file size in bytes
189
+ * @returns True if the file exceeds the limit, false otherwise
190
+ */
191
+ export function exceedsMaxFileSize(filePath, maxFileSize) {
192
+ try {
193
+ const stat = fs.statSync(filePath);
194
+ return stat.size > maxFileSize;
195
+ }
196
+ catch {
197
+ return false;
198
+ }
199
+ }
200
+ /**
201
+ * Formats a file size in bytes to a human-readable string
202
+ *
203
+ * @param bytes - The file size in bytes
204
+ * @returns Human-readable file size string
205
+ */
206
+ export function formatFileSize(bytes) {
207
+ const units = ["B", "KB", "MB", "GB"];
208
+ let size = bytes;
209
+ let unitIndex = 0;
210
+ while (size >= 1024 && unitIndex < units.length - 1) {
211
+ size /= 1024;
212
+ unitIndex++;
213
+ }
214
+ return `${size.toFixed(unitIndex === 0 ? 0 : 2)} ${units[unitIndex]}`;
215
+ }
216
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,35 @@
1
+ import { loadConfig } from "./config.js";
2
+ import { NodeFileSystem, } from "./file.js";
3
+ import { NodeGit } from "./git.js";
4
+ import { createModelStudioConfig, ModelStudioClient } from "./model-studio.js";
5
+ import { LanceStore, TestStore } from "./store.js";
6
+ import { isTest } from "./utils.js";
7
+ /**
8
+ * Creates a configured Store instance.
9
+ */
10
+ export async function createStore() {
11
+ if (isTest) {
12
+ return new TestStore();
13
+ }
14
+ const config = loadConfig(process.cwd());
15
+ const client = new ModelStudioClient(createModelStudioConfig({
16
+ embedModel: config.embedModel,
17
+ embedDimensions: config.embedDimensions,
18
+ rerankModel: config.rerankModel,
19
+ llmModel: config.llmModel,
20
+ }));
21
+ return new LanceStore(config, client);
22
+ }
23
+ /**
24
+ * Creates a Git instance
25
+ */
26
+ export function createGit() {
27
+ return new NodeGit();
28
+ }
29
+ /**
30
+ * Creates a FileSystem instance
31
+ */
32
+ export function createFileSystem(options = { ignorePatterns: [] }) {
33
+ return new NodeFileSystem(createGit(), options);
34
+ }
35
+ //# sourceMappingURL=context.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"context.js","sourceRoot":"","sources":["../../src/lib/context.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAGL,cAAc,GACf,MAAM,WAAW,CAAC;AACnB,OAAO,EAAY,OAAO,EAAE,MAAM,UAAU,CAAC;AAC7C,OAAO,EAAE,uBAAuB,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAC/E,OAAO,EAAE,UAAU,EAAc,SAAS,EAAE,MAAM,YAAY,CAAC;AAC/D,OAAO,EAAE,MAAM,EAAE,MAAM,YAAY,CAAC;AAEpC;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,WAAW;IAC/B,IAAI,MAAM,EAAE,CAAC;QACX,OAAO,IAAI,SAAS,EAAE,CAAC;IACzB,CAAC;IAED,MAAM,MAAM,GAAG,UAAU,CAAC,OAAO,CAAC,GAAG,EAAE,CAAC,CAAC;IACzC,MAAM,MAAM,GAAG,IAAI,iBAAiB,CAClC,uBAAuB,CAAC;QACtB,UAAU,EAAE,MAAM,CAAC,UAAU;QAC7B,eAAe,EAAE,MAAM,CAAC,eAAe;QACvC,WAAW,EAAE,MAAM,CAAC,WAAW;QAC/B,QAAQ,EAAE,MAAM,CAAC,QAAQ;KAC1B,CAAC,CACH,CAAC;IAEF,OAAO,IAAI,UAAU,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AACxC,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,SAAS;IACvB,OAAO,IAAI,OAAO,EAAE,CAAC;AACvB,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,gBAAgB,CAC9B,UAA6B,EAAE,cAAc,EAAE,EAAE,EAAE;IAEnD,OAAO,IAAI,cAAc,CAAC,SAAS,EAAE,EAAE,OAAO,CAAC,CAAC;AAClD,CAAC"}
@@ -0,0 +1,154 @@
1
+ import * as fs from "node:fs";
2
+ import * as path from "node:path";
3
+ import ignore from "ignore";
4
+ /**
5
+ * Default glob patterns to ignore during file indexing.
6
+ * These are not useful for the local text-first LanceDB index.
7
+ */
8
+ export const DEFAULT_IGNORE_PATTERNS = [
9
+ "*.lock",
10
+ "*.bin",
11
+ "*.ipynb",
12
+ "*.pyc",
13
+ "*.safetensors",
14
+ "*.sqlite",
15
+ "*.pt",
16
+ ];
17
+ /**
18
+ * Node.js implementation of FileSystem with gitignore support
19
+ */
20
+ export class NodeFileSystem {
21
+ git;
22
+ customIgnoreFilter;
23
+ ignoreCache = new Map();
24
+ constructor(git, options) {
25
+ this.git = git;
26
+ this.customIgnoreFilter = ignore();
27
+ this.customIgnoreFilter.add(options.ignorePatterns);
28
+ }
29
+ /**
30
+ * Checks if a file is a hidden file (starts with .)
31
+ */
32
+ isHiddenFile(filePath, root) {
33
+ const relativePath = path.relative(root, filePath);
34
+ const parts = relativePath.split(path.sep);
35
+ return parts.some((part) => part.startsWith(".") && part !== "." && part !== "..");
36
+ }
37
+ /**
38
+ * Gets all files recursively from a directory
39
+ */
40
+ *getAllFilesRecursive(dir, root) {
41
+ try {
42
+ const entries = fs.readdirSync(dir, { withFileTypes: true });
43
+ for (const entry of entries) {
44
+ const fullPath = path.join(dir, entry.name);
45
+ if (this.isHiddenFile(fullPath, root)) {
46
+ continue;
47
+ }
48
+ if (this.isIgnored(fullPath, root)) {
49
+ continue;
50
+ }
51
+ if (entry.isDirectory()) {
52
+ yield* this.getAllFilesRecursive(fullPath, root);
53
+ }
54
+ else if (entry.isFile()) {
55
+ yield fullPath;
56
+ }
57
+ }
58
+ }
59
+ catch (error) {
60
+ // Log permission or other filesystem errors
61
+ console.error(`Warning: Failed to read directory ${dir}:`, error);
62
+ }
63
+ }
64
+ *getFiles(dirRoot) {
65
+ // Preload root .mgrepignore to ensure it's cached
66
+ this.getDirectoryIgnoreFilter(dirRoot);
67
+ if (this.git.isGitRepository(dirRoot)) {
68
+ yield* this.git.getGitFiles(dirRoot);
69
+ }
70
+ else {
71
+ yield* this.getAllFilesRecursive(dirRoot, dirRoot);
72
+ }
73
+ }
74
+ getDirectoryIgnoreFilter(dir) {
75
+ if (this.ignoreCache.has(dir)) {
76
+ return this.ignoreCache.get(dir) ?? ignore();
77
+ }
78
+ const ig = ignore();
79
+ // Load .gitignore
80
+ const gitignorePath = path.join(dir, ".gitignore");
81
+ if (fs.existsSync(gitignorePath)) {
82
+ ig.add(fs.readFileSync(gitignorePath, "utf8"));
83
+ }
84
+ // Load .mgrepignore
85
+ const mgrepignorePath = path.join(dir, ".mgrepignore");
86
+ if (fs.existsSync(mgrepignorePath)) {
87
+ ig.add(fs.readFileSync(mgrepignorePath, "utf8"));
88
+ }
89
+ this.ignoreCache.set(dir, ig);
90
+ return ig;
91
+ }
92
+ isIgnored(filePath, root) {
93
+ // Always ignore hidden files
94
+ if (this.isHiddenFile(filePath, root)) {
95
+ return true;
96
+ }
97
+ // Check custom ignore patterns (global/CLI)
98
+ const relativeToRoot = path.relative(root, filePath);
99
+ const normalizedRootPath = relativeToRoot.replace(/\\/g, "/");
100
+ // Check if it's a directory
101
+ let isDirectory = false;
102
+ try {
103
+ const stat = fs.statSync(filePath);
104
+ isDirectory = stat.isDirectory();
105
+ }
106
+ catch {
107
+ isDirectory = false;
108
+ }
109
+ const pathToCheckRoot = isDirectory
110
+ ? `${normalizedRootPath}/`
111
+ : normalizedRootPath;
112
+ if (this.customIgnoreFilter.ignores(pathToCheckRoot)) {
113
+ return true;
114
+ }
115
+ // Hierarchical check
116
+ let currentDir = isDirectory ? filePath : path.dirname(filePath);
117
+ const absoluteRoot = path.resolve(root);
118
+ // Walk up from file directory to root
119
+ while (true) {
120
+ const relativeToCurrent = path.relative(currentDir, filePath);
121
+ if (relativeToCurrent !== "") {
122
+ // If we are checking the directory itself against its own ignore file? No, files inside.
123
+ // But if we are checking a file `a/b.txt`, and we are at `a`, relative is `b.txt`.
124
+ // If we are at `root`, relative is `a/b.txt`.
125
+ const normalizedRelative = relativeToCurrent.replace(/\\/g, "/");
126
+ const pathToCheck = isDirectory
127
+ ? `${normalizedRelative}/`
128
+ : normalizedRelative;
129
+ const filter = this.getDirectoryIgnoreFilter(currentDir);
130
+ // Use internal test() method if available to distinguish ignored vs unignored
131
+ const result = filter.test(pathToCheck);
132
+ if (result.ignored) {
133
+ return true;
134
+ }
135
+ if (result.unignored) {
136
+ return false;
137
+ }
138
+ }
139
+ if (path.resolve(currentDir) === absoluteRoot) {
140
+ break;
141
+ }
142
+ const parent = path.dirname(currentDir);
143
+ if (parent === currentDir)
144
+ break; // Safety break for root of fs
145
+ currentDir = parent;
146
+ }
147
+ return false;
148
+ }
149
+ loadMgrepignore(dirRoot) {
150
+ // Now handled by getDirectoryIgnoreFilter and caching
151
+ this.getDirectoryIgnoreFilter(dirRoot);
152
+ }
153
+ }
154
+ //# sourceMappingURL=file.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file.js","sourceRoot":"","sources":["../../src/lib/file.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,167 @@
1
+ import { spawnSync } from "node:child_process";
2
+ import * as fs from "node:fs";
3
+ import * as path from "node:path";
4
+ import ignore from "ignore";
5
+ /**
6
+ * GitIgnore filter using the ignore package with enhanced pattern support
7
+ */
8
+ export class GitIgnoreFilter {
9
+ ignoreInstance;
10
+ constructor(gitignoreContent) {
11
+ this.ignoreInstance = ignore();
12
+ if (gitignoreContent) {
13
+ this.add(gitignoreContent);
14
+ }
15
+ }
16
+ /**
17
+ * Normalizes a path for gitignore pattern matching
18
+ */
19
+ normalizePathForIgnore(filePath, root) {
20
+ const relativePath = path.relative(root, filePath);
21
+ // Normalize path separators for cross-platform compatibility
22
+ return relativePath.replace(/\\/g, "/");
23
+ }
24
+ /**
25
+ * Checks if a file path should be ignored based on gitignore patterns
26
+ * Handles both files and directories properly
27
+ */
28
+ isIgnored(filePath, root) {
29
+ const normalizedPath = this.normalizePathForIgnore(filePath, root);
30
+ if (!normalizedPath)
31
+ return false; // Root directory itself
32
+ // Check if it's a directory by attempting to stat the path
33
+ let isDirectory = false;
34
+ try {
35
+ const stat = fs.statSync(filePath);
36
+ isDirectory = stat.isDirectory();
37
+ }
38
+ catch {
39
+ // If we can't stat the file, assume it's not a directory
40
+ isDirectory = false;
41
+ }
42
+ // The ignore package expects directories to end with "/"
43
+ const pathToCheck = isDirectory ? `${normalizedPath}/` : normalizedPath;
44
+ return this.ignoreInstance.ignores(pathToCheck);
45
+ }
46
+ /**
47
+ * Adds gitignore patterns from a string
48
+ * The ignore package automatically handles comments and empty lines
49
+ */
50
+ add(patterns) {
51
+ this.ignoreInstance.add(patterns);
52
+ }
53
+ /**
54
+ * Clears all patterns
55
+ */
56
+ clear() {
57
+ this.ignoreInstance = ignore();
58
+ }
59
+ }
60
+ /**
61
+ * Node.js implementation of the Git interface using git CLI commands
62
+ */
63
+ export class NodeGit {
64
+ gitRepoCache = new Map();
65
+ gitIgnoreCache = new Map();
66
+ isGitRepository(dir) {
67
+ const normalizedDir = path.resolve(dir);
68
+ const cached = this.gitRepoCache.get(normalizedDir);
69
+ if (cached !== undefined) {
70
+ return cached;
71
+ }
72
+ let isGit = false;
73
+ try {
74
+ const result = spawnSync("git", ["rev-parse", "--git-dir"], {
75
+ cwd: dir,
76
+ encoding: "utf-8",
77
+ });
78
+ isGit = result.status === 0 && !result.error;
79
+ }
80
+ catch {
81
+ isGit = false;
82
+ }
83
+ this.gitRepoCache.set(normalizedDir, isGit);
84
+ return isGit;
85
+ }
86
+ /**
87
+ * Gets gitignore content from a git repository
88
+ */
89
+ getGitIgnoreContent(repoRoot) {
90
+ try {
91
+ const gitignorePath = path.join(repoRoot, ".gitignore");
92
+ if (fs.existsSync(gitignorePath)) {
93
+ return fs.readFileSync(gitignorePath, "utf-8");
94
+ }
95
+ }
96
+ catch (error) {
97
+ // Log error but don't fail - .gitignore is optional
98
+ console.error(`Warning: Failed to read .gitignore in ${repoRoot}:`, error);
99
+ }
100
+ return null;
101
+ }
102
+ /**
103
+ * Gets files using git ls-files when in a git repository
104
+ */
105
+ *getGitFiles(dirRoot) {
106
+ try {
107
+ const run = (args) => {
108
+ const res = spawnSync("git", args, {
109
+ cwd: dirRoot,
110
+ encoding: "utf-8",
111
+ maxBuffer: 1024 * 1024 * 1024, // 1GB buffer for large repos
112
+ });
113
+ if (res.error || res.status !== 0) {
114
+ console.error(`Warning: git command failed: git ${args.join(" ")}`);
115
+ return "";
116
+ }
117
+ return res.stdout;
118
+ };
119
+ const tracked = run(["ls-files", "-z"]).split("\u0000").filter(Boolean);
120
+ const untracked = run([
121
+ "ls-files",
122
+ "--others",
123
+ "--exclude-standard",
124
+ "-z",
125
+ ])
126
+ .split("\u0000")
127
+ .filter(Boolean);
128
+ const allRel = Array.from(new Set([...tracked, ...untracked]));
129
+ for (const rel of allRel) {
130
+ yield path.join(dirRoot, rel);
131
+ }
132
+ }
133
+ catch (error) {
134
+ console.error(`Warning: Failed to get files from git in ${dirRoot}:`, error);
135
+ }
136
+ }
137
+ /**
138
+ * Gets or creates a cached GitIgnoreFilter for a repository
139
+ * Includes cache invalidation based on .gitignore modification time
140
+ */
141
+ getGitIgnoreFilter(repoRoot) {
142
+ const normalizedRoot = path.resolve(repoRoot);
143
+ const gitignorePath = path.join(repoRoot, ".gitignore");
144
+ // Get current mtime of .gitignore file
145
+ let currentMtime = 0;
146
+ try {
147
+ const stat = fs.statSync(gitignorePath);
148
+ currentMtime = stat.mtime.getTime();
149
+ }
150
+ catch {
151
+ // If .gitignore doesn't exist, use 0 as mtime
152
+ }
153
+ const cached = this.gitIgnoreCache.get(normalizedRoot);
154
+ if (!cached || cached.mtime !== currentMtime) {
155
+ // Cache miss or stale cache
156
+ const filter = new GitIgnoreFilter();
157
+ const gitignoreContent = this.getGitIgnoreContent(repoRoot);
158
+ if (gitignoreContent) {
159
+ filter.add(gitignoreContent);
160
+ }
161
+ this.gitIgnoreCache.set(normalizedRoot, { filter, mtime: currentMtime });
162
+ return filter;
163
+ }
164
+ return cached.filter;
165
+ }
166
+ }
167
+ //# sourceMappingURL=git.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"git.js","sourceRoot":"","sources":["../../src/lib/git.ts"],"names":[],"mappings":"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"}