can1357/oh-my-pi · error · ApplyPatchError

No files were modified.

Error message

No files were modified.

What it means

applyCodexPatch parses the patch into hunks and refuses to proceed when the parse yields zero hunks — i.e. the patch contains no Add/Delete/Update File operations. It throws ApplyPatchError rather than silently succeeding with 'nothing done'.

Source

Thrown at packages/coding-agent/src/edit/apply-patch/index.ts:41

	/** Affected file paths grouped by operation, for the §9.1 summary. */
	affected: {
		added: string[];
		modified: string[];
		deleted: string[];
	};
}

/**
 * Apply a full Codex `*** Begin Patch` envelope.
 *
 * Note: renames are reported under `modified` with the original path (spec
 * §9.1), not as a delete + add.
 */
export async function applyCodexPatch(patchText: string, options: ApplyPatchOptions): Promise<ApplyCodexPatchResult> {
	const hunks = parseApplyPatch(patchText);

	if (hunks.length === 0) {
		throw new ApplyPatchError("No files were modified.");
	}

	const results: ApplyPatchResult[] = [];
	const affected = {
		added: [] as string[],
		modified: [] as string[],
		deleted: [] as string[],
	};

	for (const hunk of hunks) {
		const result = await applyPatch(hunk, options);
		results.push(result);
		recordAffected(affected, hunk, result);
	}

	return { results, affected };
}

View on GitHub (pinned to 9690622007)

Solutions

  1. Inspect the patch text: ensure it contains at least one '*** Add File:', '*** Delete File:', or '*** Update File:' hunk between the markers
  2. If the patch came from a model, re-prompt — the operation produced no changes
  3. Treat 'no files were modified' as expected and skip calling applyCodexPatch when the patch body is empty (pre-validate)

Example fix

// before
await applyCodexPatch(patchText); // throws when patch has no hunks
// after
if (parseApplyPatch(patchText).length === 0) {
	return { applied: false, reason: 'patch contained no file operations' };
}
await applyCodexPatch(patchText);
Defensive patterns

Strategy: validation

Validate before calling

if (parseApplyPatch(patchText).length === 0) {
	throw new SkipOperation('patch has no file operations');
}

Try / catch

try {
	await applyCodexPatch(patchText, opts);
} catch (err) {
	if (err instanceof ApplyPatchError && err.message === 'No files were modified.') {
		return { applied: false };
	}
	throw err;
}

Prevention

When it happens

Trigger: Calling applyCodexPatch(applyLegacyPatch result path) with text that parses to an empty hunk list: only the Begin/End markers, only comments, or whitespace/blank content inside the markers.

Common situations: An LLM/agent emitted a patch with no file operations; the patch body was stripped by upstream processing; a template rendered only the wrapper markers; passing an already-applied or truncated patch.

Related errors


AI-assisted analysis of can1357/oh-my-pi@9690622007 (2026-08-31). Data as JSON: /api/errors/5fdb599e2ec9c9c4. Report an issue: GitHub.