Skip to content
Git Basics: Trace One File Back Through a Rename

Git Basics: Trace One File Back Through a Rename

October 29, 2026

A file may have a longer history than its current name suggests. Create a configuration file, rename it without changing its contents, and then edit it to compare two history queries.

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 1

Run the example

Save this as demonstrate-log-follow.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 'timeout=10\nmode=basic\n' > old.conf
git add old.conf
git commit -qm 'Create original configuration'
git mv old.conf service.conf
git commit -qm 'Rename configuration'
printf 'timeout=20\nmode=basic\n' > service.conf
git commit -qam 'Raise timeout'
printf 'Current path only:\n'
git log --format=%s -- service.conf
printf 'Following the rename:\n'
git log --follow --format=%s -- service.conf
test "$(git log --follow --format=%s -- service.conf | wc -l)" -eq 3

Run it:

bash demonstrate-log-follow.sh

Observed output:

Current path only:
Raise timeout
Rename configuration
Following the rename:
Raise timeout
Rename configuration
Create original configuration

Read the result

The current-path query shows the timeout edit and the rename that introduced service.conf. Adding --follow also reaches the commit that originally created old.conf. This fixture makes the rename unambiguous by preserving the entire file in the rename commit.

Apply it carefully

Git detects renames from content similarity rather than storing a permanent file identity. --follow accepts a single file and can behave poorly on nonlinear history. A heavily edited rename may not be recognized; inspect neighboring commits and earlier paths if the result looks incomplete. This example follows reachable history from the current branch, not every remote branch.

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-log-follow.sh
cd -- "$start_dir" || exit 1
rmdir -- "$work_dir"
unset start_dir work_dir

If the directory is not empty, inspect its remaining files rather than deleting unknown content.

Acknowledgements

This post was created with assistance from AI.

Last updated on