so-fancy / diff-so-fancy

Good-lookin' diffs. Actually… nah… The best-lookin' diffs. :tada:
MIT License
17.27k stars 330 forks source link

dfs skips copied files with diff.renames=copies #349

Open kapsh opened 4 years ago

kapsh commented 4 years ago

I have git config diff.renames copies set and having an issue with dfs skipping copied file in git show. I'll try to explain it with examples.

Without paging through dfs: deluge_plain.txt Processed with dfs: deluge_fancy.txt

Here is also output with default value diff.renames true: deluge_plain_wo_copies.txt deluge_fancy_wo_copies.txt

In plain git diff you can notice that deluge-1.3.15-r3.exheres-0 was copied to deluge-2.0.3.exheres-0 and then renamed to deluge-scm.exheres-0. However, fancy output shows only rename. With default diff.renames value dfs output is consistent with plain output: one file renamed and other is "new" (but it's not, this is literal copy of 1.5.3 file).

scottchiefbaker commented 4 years ago

Can you explain git config diff.renames copies? I'm not familiar with that setting for git.

kapsh commented 4 years ago

@scottchiefbaker this setting tells git how to display renamed (same or similar content, new name, old file is missing) and copied (same or similar content, new name, old file present) files. By default git only detects renames, any copy is shown as new file. diff.renames copies works also for second case.

To illustrate this one can create dummy repository as

git init
echo "hurr-durr" > first_file
git add .
git commit -m "first"

After that copy and stage (or commit) some file:

cp first_file copied_file
git add .

And inspect this change:

❯ git --no-pager diff --staged
diff --git a/copied_file b/copied_file
new file mode 100644
index 0000000..d7b6a5e
--- /dev/null
+++ b/copied_file
@@ -0,0 +1 @@
+hurr-durr

/tmp/copy-example master*
❯ git --no-pager diff -C --staged  # -C has the same meaning
diff --git a/first_file b/copied_file
similarity index 100%
copy from first_file
copy to copied_file

I hope this narrowed down example helps better than original ones. Looks like fancy just doesn't know how to parse copy from/to headers in diff.

scottchiefbaker commented 4 years ago

Yeesh... that's a cool git feature, but it would probably be a nightmare for d-s-f to support this.

d-s-f works line by line, and we'd have to see the diff --git line, which we already look for, and then look ahead three lines. I'll ponder for a while, but it's not simple.

OJFord commented 4 years ago

Wouldn't the handling be the same as for rename, it looks the same just s/rename/copy/g?

$ git mv diff-so-fancy dsf
$ git --no-pager diff --staged
diff --git diff-so-fancy dsf
similarity index 100%
rename from diff-so-fancy
rename to dsf
phil-blain commented 3 years ago

Relevant parts of the Git doc: