MCPcopy Create free account
hub / github.com/colbymchenry/codegraph / getChangedFiles

Method getChangedFiles

src/extraction/index.ts:2935–3022  ·  view source on GitHub ↗

* Get files that have changed since last index. * Uses git status as a fast path when available, falling back to full scan.

()

Source from the content-addressed store, hash-verified

2933 * Uses git status as a fast path when available, falling back to full scan.
2934 */
2935 getChangedFiles(): { added: string[]; modified: string[]; removed: string[] } {
2936 const gitChanges = getGitChangedFiles(this.rootDir);
2937
2938 if (gitChanges) {
2939 // === Git fast path ===
2940 const added: string[] = [];
2941 const modified: string[] = [];
2942 const removed: string[] = [];
2943
2944 // Deleted files — only report if tracked in DB
2945 for (const filePath of gitChanges.deleted) {
2946 const tracked = this.queries.getFileByPath(filePath);
2947 if (tracked) {
2948 removed.push(filePath);
2949 }
2950 }
2951
2952 // Modified + added files — read + hash, compare with DB. Untracked (`??`)
2953 // files stay untracked in git even after indexing, so they must be
2954 // hash-compared like modified files instead of always counting as added —
2955 // otherwise status reports them as pending forever. (See issue #206.)
2956 for (const filePath of [...gitChanges.modified, ...gitChanges.added]) {
2957 const fullPath = path.join(this.rootDir, filePath);
2958 let content: string;
2959 try {
2960 content = fs.readFileSync(fullPath, 'utf-8');
2961 } catch (error) {
2962 logDebug('Skipping unreadable file while detecting changes', { filePath, error: String(error) });
2963 continue;
2964 }
2965
2966 const contentHash = hashContent(content);
2967 const tracked = this.queries.getFileByPath(filePath);
2968
2969 if (!tracked) {
2970 added.push(filePath);
2971 } else if (tracked.contentHash !== contentHash) {
2972 modified.push(filePath);
2973 }
2974 }
2975
2976 return { added, modified, removed };
2977 }
2978
2979 // === Fallback: full scan (non-git project or git failure) ===
2980 const currentFiles = new Set(scanDirectory(this.rootDir));
2981 const trackedFiles = this.queries.getAllFiles();
2982
2983 // Build Map for O(1) lookups
2984 const trackedMap = new Map<string, FileRecord>();
2985 for (const f of trackedFiles) {
2986 trackedMap.set(f.path, f);
2987 }
2988
2989 const added: string[] = [];
2990 const modified: string[] = [];
2991 const removed: string[] = [];
2992

Callers 1

mainFunction · 0.45

Calls 10

logDebugFunction · 0.90
getGitChangedFilesFunction · 0.85
hashContentFunction · 0.85
scanDirectoryFunction · 0.85
getFileByPathMethod · 0.80
hasMethod · 0.80
getAllFilesMethod · 0.65
getMethod · 0.65
joinMethod · 0.45
setMethod · 0.45

Tested by

no test coverage detected