Change recommended git configuration

`git-difftool` has strictly less information than `git-diff`.
`git-difftool` therefore produces worse results, and we shouldn't
recommend it.

`git-difftool` does not have file rename information, and sometimes
makes difftastic claim that file permissions have changed (depending
on the permissions of the temporary directory used).

Instead, recommend `git-diff` with an external diff configured, and
update `git-mergetool` instructions to emulate `git-diff` as much as
possible (respecting $MERGED).

Also link to the upstream git bug on segfaults with external diff
tools.

Thanks to @poliorcetics and @gthb for researching this bug and
discussing possible solutions.

Closes #734
Fixes #620
fix_newline_splitting
Wilfred Hughes 2024-09-22 13:45:15 +07:00
parent a31948384b
commit 393845ddcb
2 changed files with 93 additions and 45 deletions

@ -1,5 +1,9 @@
## 0.61 (unreleased)
**Recommended git configuration has changed! Please update your
`~/.gitconfig` to match the manual, regardless of your difftastic
version.**
## 0.60 (released 1st August 2024)
### Diffing

@ -1,30 +1,45 @@
# Git
Difftastic has good support for git.
Difftastic can be used an external diff command in git, allowing
difftastic to be used with any git subcommand.
<div class="warning">
Warning: git v2.43.1 and earlier [can
crash](https://github.com/git/git/commit/85a9a63c9268b18b24f25f6a14d6ae9966c3566d)
when using an external diff and file permissions have changed.
If you can't upgrade git, use the `difftool` configuration described
below.
</div>
## One-Off Usage
You can use
[`GIT_EXTERNAL_DIFF`](https://git-scm.com/docs/diff-config#Documentation/diff-config.txt-diffexternal)
for a one-off git command.
You can set the `diff.external` configuration option when running `git
diff`, or set the
[`GIT_EXTERNAL_DIFF`](https://git-scm.com/docs/diff-config#Documentation/diff-config.txt-diffexternal) environment variable.
View uncommitted changes with difftastic:
```
$ GIT_EXTERNAL_DIFF=difft git diff
$ git -c diff.external=difft diff
```
Other git commands also require the `--ext-diff` argument in order to
use `diff.external`.
View changes from the most recent commit with difftastic:
```
$ GIT_EXTERNAL_DIFF=difft git show HEAD --ext-diff
$ git -c diff.external=difft show --ext-diff
```
View changes from recent commits on the current branch with
difftastic:
```
$ GIT_EXTERNAL_DIFF=difft git log -p --ext-diff
$ git -c diff.external=difft log -p --ext-diff
```
## Regular Usage
@ -32,46 +47,26 @@ $ GIT_EXTERNAL_DIFF=difft git log -p --ext-diff
If you like difftastic, we recommend that you configure git aliases
so you can use difftastic more easily.
Add the following to your `~/.gitconfig` to use difftastic as a
[difftool](https://git-scm.com/docs/git-difftool).
```ini
[diff]
tool = difftastic
[difftool]
prompt = false
[difftool "difftastic"]
cmd = difft "$LOCAL" "$REMOTE"
[pager]
difftool = true
```
You can now use the following command to see changes with difftastic,
equivalent to `git diff`:
```
$ git difftool
[alias]
# Difftastic aliases, so `git dlog` is `git log` with difftastic and so on.
dlog = -c diff.external=difft log --ext-diff
dshow = -c diff.external=difft show --ext-diff
ddiff = -c diff.external=difft diff
```
We recommend that you set up a shorter alias for this command in your
`~/.gitconfig`:
The author likes the following additional aliases to reduce typing:
```ini
# `git dft` is less to type than `git difftool`.
[alias]
dft = difftool
```
# `git log` with patches shown with difftastic.
dl = -c diff.external=difft log -p --ext-diff
For other commands, we also recommend that you set up aliases that are
equivalent to the one-off commands shown above.
# Show the most recent commit with difftastic.
ds = -c diff.external=difft show --ext-diff
```ini
# `git dlog` to show `git log -p` with difftastic.
[alias]
dlog = -c diff.external=difft log -p --ext-diff
# `git diff` with difftastic.
dft = -c diff.external=difft diff
```
## Difftastic By Default
@ -81,17 +76,66 @@ following to your `~/.gitconfig`.
```ini
[diff]
external = difft
external = difft
```
This only applies to `git diff`. For other git commands, you still
need to specify `--ext-diff`, or use an alias as described above.
This changes `git diff` to use difftastic, and other commands now only
require `--ext-diff`.
```
$ git diff
$ git show HEAD --ext-diff
$ git show --ext-diff
$ git log -p --ext-diff
```
Conversely, if you need to copy/paste a diff in the standard diff format, you
can use `git diff --no-ext-diff`.
If you've configured difftastic as the default diff tool, you can
opt-out for an individual command with `--no-ext-diff`.
```
$ git diff --no-ext-diff
```
## Difftool
Git also has a [difftool
feature](https://git-scm.com/docs/git-difftool) which allows users to
invoke CLI or GUI comparison tools.
For best results, we recommend using `-c diff.external=difft` as
described above. Git passes more information to the external diff,
including file permission changes and rename information, so
difftastic can show more information.
To define a difftool named `difftastic`, add the following to your
`~/.gitconfig`.
```ini
[difftool "difftastic"]
# See `man git-difftool` for a description of MERGED, LOCAL and REMOTE.
cmd = difft "$MERGED" "$LOCAL" "abcdef1" "100644" "$REMOTE" "abcdef2" "100644"
```
You can now use difftastic as a difftool:
```
$ git difftool -t difftastic
```
For the best results when using difftastic as a difftool, we recommend
the following additional git configuration:
```ini
[difftool]
# Run the difftool immediately, don't ask 'are you sure' each time.
prompt = false
[pager]
# Use a pager if the difftool output is larger than one screenful,
# consistent with the behaviour of `git diff`.
difftool = true
[diff]
# Set difftastic as the default difftool, so we don't need to specify
# `-t difftastic` every time.
tool = difftastic
```