git show: look at one commit in full

Updated July 31, 2026

git show prints one object from the repository in full: the commit message, the author, the date and the whole diff of that commit. Where git log gives you a list of commits and git status a list of files, show unfolds exactly one point in history with every detail.

$ git log --oneline
63eb0e4 clarified the sales figure
e9a4cd4 first draft of the report

$ git show 63eb0e4
commit 63eb0e4b93079c92deb7b85b7a5e299383ffbf6d
Author: Anna Petrova <anna@example.com>
Date:   Tue Mar 17 11:05:19 2026 +0300

    clarified the sales figure

diff --git a/report.txt b/report.txt
index 5182f7c..1fa7666 100644
--- a/report.txt
+++ b/report.txt
@@ -1,3 +1,3 @@
 Q3 report
 
-Sales grew.
+Sales grew by 12%.

The top part is the same header git log prints: hash, author, date, message. Below it is the diff of that commit against its parent, in the git diff format. One screen tells you both why the commit was made and what it changed. With no argument the command shows HEAD, so git show and git show HEAD are the same thing.

The contents of a file in a commit

After the hash you can name a path to a file, separated by a colon. Then show prints not a diff but the contents of that file as they were in that commit:

$ git show HEAD:report.txt
Q3 report

Sales grew by 12%.

Your working directory is left untouched; you are only looking into the archive. This is how you pull an old version of a file without switching branches or rolling anything back. The path is counted from the repository root, not from your current directory.

A reflog entry and a tag

show accepts any reference to a commit, not only a raw hash. A reflog entry is a reference too: HEAD@{1} means "where HEAD was one move ago", HEAD@{2} two moves ago. Through it you reach a commit that git log no longer lists:

$ git reflog
63eb0e4 HEAD@{0}: reset: moving to HEAD~1
19748c5 HEAD@{1}: commit: added the hiring section
63eb0e4 HEAD@{2}: commit: clarified the sales figure
e9a4cd4 HEAD@{3}: commit (initial): first draft of the report

$ git show HEAD@{1}
commit 19748c5366e1374bfc77840358e92f5e40505f4b
Author: Anna Petrova <anna@example.com>
Date:   Tue Mar 17 11:52:40 2026 +0300

    added the hiring section

diff --git a/report.txt b/report.txt
index 1fa7666..9f85de5 100644
--- a/report.txt
+++ b/report.txt
@@ -1,3 +1,4 @@
 Q3 report
 
 Sales grew by 12%.
+We hired two people.

A tag name goes in the same slot. For an annotated tag, show first prints the tag itself - who created it and when - and then the commit it points to:

$ git show v1.0
tag v1.0
Tagger: Anna Petrova <anna@example.com>
Date:   Tue Mar 17 12:10:00 2026 +0300

first release

commit 63eb0e4b93079c92deb7b85b7a5e299383ffbf6d

On tags, see git tag.

show, log and diff

The three are easy to mix up. git log is a list of commits, the view of history from above. git show takes one object from that list and unfolds it in full. git diff compares any two states and prints the difference between them. In short: log is "which commits there were", show is "what is inside this commit", diff is "how these two points differ".

Common mistakes

git show <hash> and git show <hash>:path are different requests. The first prints the whole commit with its diff; the second prints the contents of one file in that commit. Drop the colon and path and you get the diff of the entire commit, not the file you wanted to read.

A show diff is always against a parent, and a merge commit has two parents. By default show prints a combined diff for a merge, and on a clean merge it often comes out empty, leaving only the header. To see what the merge brought in, use git show -m: it shows the diff against each parent in turn.

Where this is in the book

Looking at commits and the difference between states is covered in chapter 4.

Chapter 4. Inspect, undo, ignore