Git Basics: Catch Staged Whitespace Errors Before Committing
A corrected working file does not automatically repair the snapshot queued for commit. This exercise inserts a trailing space, checks the staged patch, then proves why the correction needs another staging step.
Prepare a scratch directory
Tested on Linux with Git 2.52.0 and GNU Bash 5.2.37. You need Bash, Git, a text editor, and standard mktemp, rm, rmdir, cat, head, wc, and sed utilities. Run from an ordinary shell without repository-selection variables such as GIT_DIR, GIT_WORK_TREE, or GIT_INDEX_FILE set. The script isolates global and system Git configuration and uses fictional identities only in its temporary repository.
Keep the same terminal open. Stop if setup fails, before saving the source:
start_dir="$PWD"
work_dir="$(mktemp -d)" || exit 1
cd -- "$work_dir" || exit 1Run the example
Save this as demonstrate-diff-check.sh:
#!/usr/bin/env bash
set -euo pipefail
export LC_ALL=C
fixture_dir="$(mktemp -d)"
trap 'rm -rf -- "$fixture_dir"' EXIT
export GIT_CONFIG_NOSYSTEM=1
export GIT_CONFIG_GLOBAL=/dev/null
export GIT_AUTHOR_NAME='Example Author'
export GIT_AUTHOR_EMAIL='author@example.invalid'
export GIT_COMMITTER_NAME="$GIT_AUTHOR_NAME"
export GIT_COMMITTER_EMAIL="$GIT_AUTHOR_EMAIL"
export GIT_AUTHOR_DATE='2026-10-29T00:00:00+00:00'
export GIT_COMMITTER_DATE="$GIT_AUTHOR_DATE"
git init -q --object-format=sha1 -b main "$fixture_dir/repo"
cd -- "$fixture_dir/repo"
git config commit.gpgsign false
git config core.hooksPath /dev/null
printf 'mode=basic\n' > app.conf
git add app.conf
git commit -qm 'Start configuration'
printf 'mode=fast \n' > app.conf
git add app.conf
printf 'Staged check:\n'
if git -c color.ui=false diff --cached --check | sed -n '1p'; then
printf 'Expected a whitespace error\n' >&2
exit 1
else
check_status=$?
test "$check_status" -eq 2
printf 'Check exit status: %s\n' "$check_status"
fi
printf 'mode=fast\n' > app.conf
printf 'Working copy corrected; staged check still fails: '
if git diff --cached --check > /dev/null; then
exit 1
else
test "$?" -eq 2
printf 'yes\n'
fi
git add app.conf
git diff --cached --check
printf 'After staging the correction: clean\n'Run it:
bash demonstrate-diff-check.shObserved output:
Staged check:
app.conf:1: trailing whitespace.
Check exit status: 2
Working copy corrected; staged check still fails: yes
After staging the correction: cleanRead the result
The first check fails on the staged trailing space. The script prints only its first diagnostic using sed; pipefail keeps the Git failure visible through that pipeline. The exit value of 2 is the observed result for this fixture, not a general promise for every Git failure. After rewriting the file, the staged copy still contains the error. Only the final git add updates it.
Apply it carefully
Use git diff --cached --check for staged changes and git diff --check for unstaged changes. A nonzero result needs investigation. This check does not validate program behavior, and whitespace rules can be configured with core.whitespace. Do not combine this mode with --exit-code.
The official Git reference documents these options. The script creates and removes only its own temporary fixture; it does not contact a remote or change your existing repository.
Clean up
Remove the saved script, return to the starting directory, and remove the empty practice directory:
rm -- demonstrate-diff-check.sh
cd -- "$start_dir" || exit 1
rmdir -- "$work_dir"
unset start_dir work_dirIf the directory is not empty, inspect its remaining files rather than deleting unknown content.
Acknowledgements
This post was created with assistance from AI.