Egonex-AI/Understand-Anything · error
Invalid ${kind} path in git diff
Error message
Invalid ${kind} path in git diff What it means
parseNameStatusZ parses `git diff --name-status -z` output into change records. For rename (R) or copy (C) entries, the format supplies two paths (old and new); if either normalizes to an empty/invalid path, the parser treats the diff record as corrupt and throws instead of emitting a malformed change.
Source
Thrown at understand-anything-plugin/skills/understand/prepare-incremental.mjs:170
'git',
['rev-parse', '--verify', '--end-of-options', `${value}^{commit}`],
{ cwd: projectRoot },
).trim();
}
function parseNameStatusZ(output) {
if (!output) return [];
const fields = output.split('\0');
if (fields.at(-1) === '') fields.pop();
const changes = [];
for (let i = 0; i < fields.length;) {
const status = fields[i++];
if (!status) continue;
const kind = status[0];
if (kind === 'R' || kind === 'C') {
const oldPath = normalizeRelativePath(fields[i++]);
const newPath = normalizeRelativePath(fields[i++]);
if (!oldPath || !newPath) throw new Error(`Invalid ${kind} path in git diff`);
changes.push({ status, oldPath, newPath });
} else {
const path = normalizeRelativePath(fields[i++]);
if (!path) throw new Error(`Invalid path in git diff for status ${status}`);
changes.push({ status, path });
}
}
return changes;
}
function pathsFromChanges(changes) {
const paths = [];
for (const change of changes) {
if (change.path) paths.push(change.path);
if (change.oldPath) paths.push(change.oldPath);
if (change.newPath) paths.push(change.newPath);
}
return sorted(paths);View on GitHub (pinned to 07edf82a04)
Solutions
- Re-run `git diff --name-status -z <baseCommit>` and inspect the R/C entries for malformed or empty paths
- Exclude the offending path via --exclude if it is an edge-case file not needed for analysis
- Update/verify normalizeRelativePath handles the path form (quoting, prefix stripping)
- Fall back to a full (non-incremental) /understand run, which does not parse the incremental diff
Example fix
// before
const oldPath = normalizeRelativePath(fields[i++]);
const newPath = normalizeRelativePath(fields[i++]);
// after
const oldPath = normalizeRelativePath(fields[i++]);
const newPath = normalizeRelativePath(fields[i++]);
if (!oldPath || !newPath) {
console.warn(`Skipping malformed ${kind} entry`);
continue; // or handle instead of throwing
} Defensive patterns
Strategy: validation
Validate before calling
const out = execSync(`git diff --name-status -z ${baseCommit}`).toString();
const fields = out.split('\0');
for (let i = 0; i < fields.length; ) {
const status = fields[i++];
if (!status) break;
if (status[0] === 'R' || status[0] === 'C') {
if (!fields[i] || !fields[i + 1]) throw new Error('Malformed rename entry in diff');
i += 2;
} else i += 1;
} Type guard
function isValidPath(p) { return typeof p === 'string' && p.length > 0 && !p.startsWith('/') && !p.includes('..'); } Try / catch
try {
const changes = parseNameStatusZ(rawDiff);
} catch (err) {
if (String(err.message).includes('path in git diff')) {
console.warn('Malformed diff entry, falling back to full analysis');
return runFullAnalysis();
}
throw err;
} Prevention
- Inspect `git diff --name-status -z` output for edge-case filenames before incremental runs
- Keep normalizeRelativePath consistent with the git quoting mode used (core.quotePath)
- Fall back to full analysis when diff parsing fails instead of proceeding partially
When it happens
Trigger: A rename/copy entry in the git name-status output where normalizeRelativePath returns falsy for oldPath or newPath — e.g. truncated diff output, a quoted/unusual path that the normalizer rejects, or a malformed field stream after splitting on NUL.
Common situations: Running incremental analysis on a repo whose base diff contains renames with edge-case filenames (unicode, embedded quotes, paths outside the project after normalization), or piping output from a git version/output variant the parser did not anticipate.
Understand the failure class
Background: "git command failed": what it means when a tool shells out to git and git exits non-zero — this error's family across 21 libraries.
Related errors
- Invalid path in git diff for status ${status}
- JSON changed-file list must be an array of strings
- Fingerprint patch does not match the incremental plan commit
- ${command} failed: ${detail}
- File disappeared while preparing incremental update: ${fileP
AI-assisted analysis of Egonex-AI/Understand-Anything@07edf82a04 (2026-09-07).
Data as JSON: /api/errors/864c275a9fea7358.
Report an issue: GitHub.