fix(cmds/git/diff): preserve POSIX/git contract for programmatic consumers#1981
Open
YOMXXX wants to merge 1 commit into
Open
fix(cmds/git/diff): preserve POSIX/git contract for programmatic consumers#1981YOMXXX wants to merge 1 commit into
YOMXXX wants to merge 1 commit into
Conversation
…umers Issues rtk-ai#1918 / rtk-ai#1869 / rtk-ai#1081 / rtk-ai#1869: 'rtk git diff' and 'rtk diff' were emitting decorative output that broke 'git apply', 'patch', shell loops over '--name-only', and exit-code-based predicates. Because the PreToolUse hook silently rewrites 'git diff' to 'rtk git diff' for agents, those decorations silently distorted any patch/script workflow. Two surfaces are fixed: 1. 'rtk git diff' (proxy for 'git diff') - Detect non-TTY stdout AND machine-friendly flags (--name-only, --name-status, --check, --exit-code, --raw, -z, --no-color, --numstat, --shortstat, --dirstat, --patch-with-raw, --patch-with-stat, --output[=...]). - When either is true: emit raw 'git diff' output verbatim, with byte-for-byte fidelity (print! not println!) so trailing newlines are preserved for 'git apply'. - Propagate git's actual exit code rather than forcing 0. 2. 'rtk diff' (RTK's GNU-diff-like file compare) - Returns 0 when files are identical, 1 when they differ, 2 on missing-file / I/O error -- the GNU diff exit-code contract. - The '[ok] Files are identical' status now goes to stderr, so 'rtk diff a b > patch.diff' produces an empty patch on identical files (which is what scripts expect) rather than text in stdout. Eight new tests cover: machine-friendly flag detection (name-only, name-status, stat variants, raw, -z, exit-code, output[=...]); normal args bypass passthrough; identical files exit 0; different files exit 1; missing file exits 2. Fixes rtk-ai#1918, rtk-ai#1869 Refs rtk-ai#1081 (duplicate of rtk-ai#1918)
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
`rtk git diff` and `rtk diff` were emitting decorative output that broke `git apply`, `patch`, shell loops over `--name-only`, and exit-code-based predicates. Because the `PreToolUse` hook silently rewrites `git diff` to `rtk git diff` for hooked agents, those decorations silently distorted any patch / script workflow that used to work. Issue #1918 (and its duplicates #1081 / #1869) ask for the POSIX/git contract to be honored.
Two surfaces are fixed:
`rtk git diff` (proxy for `git diff`)
`rtk diff` (RTK's GNU-diff-like file compare)
Reproduction
```bash
rtk git diff round-trip
mkdir -p /tmp/g && cd /tmp/g && git init -q
git config user.email t@t.t && git config user.name t
printf '1\n2\n3\n' > f && git add f && git commit -q -m x
printf '1\n2x\n3\n' > f
rtk git diff > rtk.patch
git stash -q
git apply --check rtk.patch && echo "applies"
Before this PR: 'No valid patches in input'
After this PR: 'applies'
rtk git diff --name-only
Before this PR: 'f\n\n--- Changes ---\n f (...) ...'
After this PR: 'f'
rtk diff exit codes
printf 'a\n' > /tmp/a && printf 'b\n' > /tmp/b
rtk diff /tmp/a /tmp/b; echo "exit=$?"
Before this PR: exit=0 (silently wrong)
After this PR: exit=1 (GNU diff convention)
rtk diff /tmp/nonexistent /tmp/a; echo "exit=$?"
Before this PR: exit=1
After this PR: exit=2 (GNU diff convention)
```
Behavior changes
The compact-diff experience for interactive `rtk git diff` users is unchanged.
Test plan
Out of scope (deferred to a follow-up)
Fixes #1918, #1869
Refs #1081 (duplicate of #1918)