Git cheat sheet

A scannable Git reference: 26 short snippets across 12 topics, each linking back to the lesson it came from.

At a glance

TopicWhat it covers
Git basicsGit moves content through the working tree (your files), the index (staged snapshot), and the repository (committedlesson
Branching and mergingA branch is just a movable pointer to a commit — creating one costs almost nothing, which is why branching per task islesson
Remotes and collaborationCloning, pushing, fetching versus pulling, and understanding what origin/main actually points atlesson
Undoing mistakesrevert does not erase anything: it adds a new commit that applies the inverse change. That is exactly why it is thelesson
Conflicts, stash and cherry-pickGit merges line by line. A conflict means both sides changed overlapping lines and Git will not silently choose — whichlesson
Reading history: log, diff, blame and bisectFormat your log instead of scrolling it, search history with the pickaxe, find which commit last touched a line, andlesson
Clean history: interactive rebase, squash and amendReorder, squash, split and reword commits before anyone else sees them, use fixup and autosquash, and know the safetylesson
Tags, releases and semantic versioningThe describe output reads as: the closest reachable tag, the number of commits since it, and the abbreviated commit idlesson
Hooks, aliases and automationA hook is an ordinary executable. Git runs it, and a non-zero exit status stops the operation — that is the entirelesson
Forks, pull requests and review workflowsFork versus branch models, syncing with upstream, protected branches and required checks, review etiquette, andlesson
Worktrees, submodules and large repositoriesA worktree lets two branches be checked out at the same time in different directories, with no second clone and nolesson
Repository health, LFS and recoveryGit runs git gc automatically when the number of loose objects grows, so manual runs are mostly for recovery work, sizelesson

Quick snippets

Git basics

Three areas, one mental model

git init                 # create a repository here
git status               # always the first question
git add index.html       # working tree -> index
git commit -m 'Add landing page'
git log --oneline --graph --decorate

Commits that read well

git commit -m 'Cap retries at three attempts

Upstream timeouts occasionally last 30s; unbounded
retries kept workers busy during incidents.'

Ignoring files

# .gitignore
node_modules/
.env
*.log
.DS_Store

# stop tracking a file that is already committed
git rm --cached config.local.json

Full lesson: Git basics →

Branching and merging

Branches are cheap

git branch feature/search
git switch feature/search        # modern equivalent of checkout
# or create and switch in one step
git switch -c feature/search

git branch -a                    # list local + remote branches
git switch -                     # back to previous branch

Merging

git switch main
git merge feature/search        # creates a merge commit
git merge --ff-only feature/x   # refuse unless it can fast-forward
git branch -d feature/search    # delete once merged

git log --oneline --graph

Rebase vs merge

# replay your branch onto the latest main
git switch feature/search
git rebase main

# tidy up the last three commits interactively
git rebase -i HEAD~3

Full lesson: Branching and merging →

Remotes and collaboration

Connecting

git clone [email protected]:user/repo.git
cd repo

git remote -v
git remote add upstream <url>
git remote set-url origin <new-url>

fetch vs pull

git fetch origin          # download objects, change nothing local
git diff main origin/main # now you can inspect before integrating
git merge origin/main     # integrate deliberately

git pull --rebase         # fetch + replay your commits on top

Pushing

git push -u origin feature/search   # first time: set upstream
git push                            # afterwards
git push --force-with-lease         # safer than --force

git push origin --delete old-branch

Full lesson: Remotes and collaboration →

Undoing mistakes

Revert keeps history honest

git revert <sha>          # single commit
git revert <old>..<new>   # range (not including old)
git revert -m 1 <merge>   # specify parent for a merge commit

reflog: the safety net

git reflog
git reset --hard HEAD@{3}          # return to that state
git checkout -b recovered <sha>    # rescue onto a new branch

Full lesson: Undoing mistakes →

Conflicts, stash and cherry-pick

What a conflict actually is

<<<<<<< HEAD
const limit = 20;
=======
const limit = 50;
>>>>>>> feature/paging

What a conflict actually is

git status                # shows which files are unmerged
git checkout --ours f     # keep your side wholesale
git checkout --theirs f   # keep their side wholesale
git add f                 # mark resolved
git merge --continue

git merge --abort         # give up, return to pre-merge state

Stashing work in progress

git stash push -m 'half-done refactor'
git stash list
git stash pop              # restore and drop
git stash apply            # restore but keep the entry
git stash -u               # include untracked files

Full lesson: Conflicts, stash and cherry-pick →

Reading history: log, diff, blame and bisect

Log that answers questions

git log --oneline --graph --decorate --all
git log --oneline -20
git log --author="Ada" --since="3 weeks ago" --until=yesterday
git log --grep="clamp" --regexp-ignore-case
git log -p -- src/api/retry.ts          # patches for one path
git log --follow -- src/api/retry.ts    # keep following it through renames
git log --stat --oneline
git log --pretty=format:"%h %ad %an %s" --date=short
git log --merges
git log --no-merges
git shortlog -sne                        # commit counts per author

Full lesson: Reading history: log, diff, blame and bisect →

Clean history: interactive rebase, squash and amend

Amend and fixup

# last commit, message only
git commit --amend -m "Validate the coupon before applying it"

# last commit, with the file you forgot
git add src/coupons.ts
git commit --amend --no-edit

# a fix for an older commit: create the commit, then mark it
git commit --fixup a1b2c3d
git rebase -i --autosquash main      # the fixup! line is moved into place automatically

git log --oneline -1                 # note that the commit id changed

Interactive rebase

git rebase -i HEAD~5
# or, better, against the branch you will merge into
git rebase -i main

# the editor opens a plan, oldest commit first
# pick   a1b2c3d  Add retry logic
# squash 4d5e6f7  Fix typo
# reword 8a9b0c1  Wip
# edit   2b3c4d5  Extract client
# drop   9f8e7d6  Debug logging

Full lesson: Clean history: interactive rebase, squash and amend →

Tags, releases and semantic versioning

Tagging a commit

# annotated: a real object with a tagger, a date and a message
git tag -a v1.4.0 -m "Release 1.4.0: pagination and retry limits"
git tag -a v1.4.0 9f3c1ab -m "Release 1.4.0"   # tag a commit that is not HEAD

# lightweight: a bare pointer, fine for local bookmarks
git tag v1.4.0-rc1

git tag -l "v1.4.*"
git show v1.4.0
git tag -d v1.4.0                 # local only
git push origin --delete v1.4.0   # and on the remote

Semantic versioning and changelogs

# the raw material for a changelog
git log --oneline --no-merges v1.3.0..v1.4.0

# grouped by conventional-commit prefix
git log --format="%s" v1.3.0..v1.4.0 | sed -n 's/:.*//p' | sort | uniq -c | sort -rn

# publish a release with the built artefacts (GitHub CLI)
gh release create v1.4.0 dist/app.zip --notes-file RELEASE_NOTES.md

Full lesson: Tags, releases and semantic versioning →

Hooks, aliases and automation

Where hooks run

# client hooks live in .git/hooks and are not cloned
ls .git/hooks

# so ship them in a tracked directory instead
git config core.hooksPath .githooks
chmod +x .githooks/*

A pre-commit and commit-msg hook

#!/bin/sh
# .githooks/pre-commit
set -e

files=$(git diff --cached --name-only --diff-filter=ACM -- "*.js" "*.ts")
[ -z "$files" ] && exit 0

echo "$files" | xargs npx prettier --write
echo "$files" | xargs npx eslint --max-warnings=0

# a formatter rewrote the files, so stage them again
git add $files

A pre-commit and commit-msg hook

#!/bin/sh
# .githooks/commit-msg
msg=$(head -1 "$1")
echo "$msg" | grep -Eq '^(feat|fix|docs|chore|refactor|test): .+' || {
  echo "Commit subject must look like 'fix: handle request timeouts'"
  exit 1
}

Full lesson: Hooks, aliases and automation →

Forks, pull requests and review workflows

Stacking pull requests

# a stack: three dependent pull requests
git switch -c part-1/schema main
# ... PR #101 opens against main ...
git switch -c part-2/api part-1/schema
# ... PR #102 opens against part-1/schema ...
git switch -c part-3/ui part-2/api
# ... PR #103 opens against part-2/api ...

# after part-1 is rebased, move the branch above it onto the new base
git rebase --onto part-1/schema old-part-1 part-2/api

Full lesson: Forks, pull requests and review workflows →

Worktrees, submodules and large repositories

Worktrees

# a second working tree for the same repository
git worktree add ../project-hotfix main
git worktree add -b release/2.4 ../project-2.4 main
git worktree list
git worktree remove ../project-hotfix
git worktree prune                  # clean up metadata for trees deleted by hand

# each worktree has its own files and index, and shares the object store
cd ../project-hotfix && git status

Making a large repository bearable

# sparse checkout: only materialise the directories you need
git sparse-checkout init --cone
git sparse-checkout set apps/web packages/ui
git sparse-checkout list
git sparse-checkout disable

# shallow and partial clones
git clone --depth 1 <url>                     # one commit, no history
git clone --filter=blob:none <url>            # full history, file contents on demand
git clone --filter=blob:none --sparse <url>   # both
git fetch --unshallow                         # get the history later when you need it

Full lesson: Worktrees, submodules and large repositories →

Repository health, LFS and recovery

Health checks and housekeeping

git count-objects -vH          # loose objects, packs and total size
git fsck --full                # verify every object and link
git fsck --unreachable         # objects nothing points at

git gc                         # pack loose objects, prune what is safe
git gc --aggressive            # slower and better compressed, rarely worth it
git prune --expire=now         # remove unreachable objects immediately
git repack -ad                 # rebuild packs without redundant ones
git reflog expire --expire=now --all

Full lesson: Repository health, LFS and recovery →

FAQ

Is this Git cheat sheet free to use?
Yes. No sign-up and no tracking: the page is static, every example is on the page itself, and you can print it or save it as a one-page reference.
Where do the examples come from?
Every snippet is taken from the 12 lessons of the Git course on this site, and each section links back to the lesson it was pulled from.
How do I go deeper than a cheat sheet?
Open the full Git course — it carries the worked explanations, the edge cases and the exercises behind every line here.

Linux Docker Kubernetes Nginx CI / CD Bash Scripting

Last refreshed 2026-09-27.