Aider-AI/aider · error · DiffError
Duplicate action for file: {path}
Error message
Duplicate action for file: {path} What it means
Raised during patch parsing when an '*** Add File: <path>' block uses a path that already has an entry in patch.actions. Unlike deletes (where exact duplicates are ignored with a warning), add actions are strictly unique per path.
Source
Thrown at aider/coders/patch_coder.py:385
continue
else:
raise DiffError(f"Conflicting actions for file: {path}")
if path not in current_files:
raise DiffError(
f"Delete File Error - file not found: {path}"
) # Check against known files
patch.actions[path] = PatchAction(type=ActionType.DELETE, path=path)
continue
# ---------- ADD ---------- #
elif norm_line.startswith("*** Add File: "):
path = norm_line[len("*** Add File: ") :].strip()
index += 1
if not path:
raise DiffError("Add File action missing path.")
if path in patch.actions:
raise DiffError(f"Duplicate action for file: {path}")
# Check if file exists in the context provided (should not for Add).
# Note: We only have needed files, a full check requires FS access.
# if path in current_files:
# raise DiffError(f"Add File Error - file already exists: {path}")
action, index = self._parse_add_file_content(lines, index)
action.path = path # Ensure path is set
patch.actions[path] = action
continue
# If we are here, the line is unexpected
# Allow blank lines between actions
if not norm_line.strip():
index += 1
continue
raise DiffError(f"Unknown or misplaced line while parsing patch: {line}")
View on GitHub (pinned to 5dc9490bb3)
Solutions
- Merge the two Add blocks into one, keeping the intended content
- Remove the earlier action for that path if the file should only be added
- Retry the edit so the model produces one action per file
Example fix
// before *** Add File: a.py +one *** Add File: a.py +two // after *** Add File: a.py +one +two
Defensive patterns
Strategy: validation
Validate before calling
from collections import Counter
def no_duplicate_adds(patch_text: str) -> bool:
adds = [l[len("*** Add File: "):].strip() for l in patch_text.splitlines()
if l.startswith("*** Add File: ")]
acts = [l.split(": ", 1)[1].strip() for l in patch_text.splitlines()
if l.startswith("*** ") and ": " in l]
return max(Counter(acts).values(), default=0) <= 1 and not (set(adds) & (set(acts) - set(adds))) Try / catch
try:
edits = coder.get_edits(reply)
except DiffError as e:
if "Duplicate action for file" in str(e):
reply = merge_duplicate_add_blocks(reply)
edits = coder.get_edits(reply)
else:
raise Prevention
- Ask for one action block per file and merge content yourself if needed
- Detect repeated '*** Add File:' headers in generated patches before parsing
- Keep patches small — long patches invite the model to restart and duplicate
When it happens
Trigger: Two '*** Add File: same.py' blocks in one patch; an '*** Update File: same.py' earlier in the patch followed by an Add for the same path.
Common situations: Model emits the new file twice (often when the content is long and it restarts); concatenated retries in one response; add-after-update confusion in model output.
Related errors
- Delete File action missing path.
- Add File action missing path.
- Unknown or misplaced line while parsing patch: {line}
- Invalid Add File line (missing '+'): {line}
- Bad/missing filename. The filename must be alone on the line
AI-assisted analysis of Aider-AI/aider@5dc9490bb3 (2026-08-15).
Data as JSON: /api/errors/cfeee0b37a713d33.
Report an issue: GitHub.