Git Patch Workflow — Complete Guide
In this tutorial, you'll learn about Git Patch Workflow. We cover key concepts, practical examples, and best practices.
Git patches are portable representations of commits that can be emailed, reviewed, and applied without requiring a shared remote repository.
In this tutorial, you'll learn the Git patch workflow — how to create patches from commits, apply them to other repositories, manage patch series, and use patches for code review and offline collaboration. Patch workflows are essential for open source contribution via email (Linux kernel style), air-gapped environments, and situations where you can't share a remote repository. By the end, you'll manage a full patch-based contribution workflow.
Real-world use: Durga Antivirus Pro's security research team works in an air-gapped environment. They transfer patches via encrypted USB drives. Doda Browser accepts third-party contributions via patch files for security-sensitive components.
flowchart LR A[Developer commits changes] --> B[git format-patch] B --> C[Patch files .patch / .mbox] C --> D[Share via email / USB / upload] D --> E[Reviewer receives patches] E --> F[git am / git apply] F --> G[Patches applied to target repo] G --> H[New commits created]
Creating Patches
Generate patch files from commits using git format-patch.
# Create a patch for the latest commit
git format-patch -1 HEAD
# Create patches for the last 3 commits
git format-patch -3 HEAD
# Create patches for all commits since a specific commit
git format-patch a1b2c3d..HEAD
# Create patches since a tag
git format-patch v1.0..HEAD
# Output to a specific directory
git format-patch -3 HEAD -o ./patches/
Expected output:
$ git format-patch -3 HEAD
0001-Refactor-auth-middleware-to-use-JWT.patch
0002-Fix-null-handler-in-login-callback.patch
0003-Add-OAuth2-login-with-Google-and-GitHub.patch
$ cat 0001-Refactor-auth-middleware-to-use-JWT.patch
From a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6e7f8a9b Mon Sep 17 00:00:00 2001
From: Jane Doe <jane@example.com>
Date: Mon, 24 Jun 2026 10:00:00 +0000
Subject: [PATCH] Refactor auth middleware to use JWT
---
src/middleware/auth.js | 15 ++++++++++-----
1 file changed, 10 insertions(+), 5 deletions(-)
Each patch file contains the commit message, author, date, and the diff — everything needed to recreate the commit identically.
Customizing Patch Output
Control patch content and format.
# Include number of files changed stat
git format-patch -1 HEAD --stat
# Add a cover letter for patch series
git format-patch -3 HEAD --cover-letter --output-directory=./patches
# Include signature in patches
git format-patch -1 HEAD --signature="DodaTech Code Review"
# Number patches starting from a custom counter
git format-patch -3 HEAD --start-number=42
# Create patches as a single mbox file
git format-patch -3 HEAD --stdout > all-patches.mbox
The cover letter is useful for patch series with multiple commits, explaining the overall purpose.
Applying Patches
Two main methods: git am (applies with commit metadata) and git apply (applies raw diff).
# Apply a single patch (preserves author, message, date)
git am 0001-Refactor-auth-middleware-to-use-JWT.patch
# Apply a series of patches
git am *.patch
# Apply patches from a directory
git am ./patches/*.patch
# Apply with custom recipient
git am --signoff 0001*.patch
# Dry run — check if patches apply cleanly
git am --dry-run 0001*.patch
Expected output:
$ git am 0001*.patch
Applying: Refactor auth middleware to use JWT
$ git log --oneline -1
a1b2c3d Refactor auth middleware to use JWT # Author and date preserved
Using git apply
For raw diffs (output of git diff) that don't include commit metadata.
# Create a raw diff
git diff > changes.patch
# Apply the diff to working tree (no commit)
git apply changes.patch
# Apply and stage changes
git apply --index changes.patch
# Check if the patch applies cleanly
git apply --check changes.patch
# Apply with offset (lines shifted)
git apply --reject changes.patch
# Creates .rej files for rejected hunks
Expected output:
$ git apply --check changes.patch
# No output = patch applies cleanly
$ git apply changes.patch
$ git diff --stat
src/middleware/auth.js | 15 ++++++++++-----
1 file changed, 10 insertions(+), 5 deletions(-)
Handling Patch Conflicts
When a patch doesn't apply cleanly, resolve conflicts.
# If git am fails, it stops and reports the conflict
$ git am 0002*.patch
Applying: Fix null handler in login callback
error: patch failed: src/handler.js:25
error: src/handler.js: patch does not apply
Patch failed at 0002 Fix null handler in login callback
hint: Use 'git am --show-current-patch' to see the failed patch
# Resolve conflicts
git status
# Edit the conflicted files manually
git add src/handler.js
git am --continue
# Or skip this patch
git am --skip
# Or abort the entire am session
git am --abort
# For git apply conflicts:
git apply --reject patch.diff
# Apply what it can, leave .rej files for the rest
# Manually fix .rej files, then delete them
Patch Series Workflow
A complete workflow for contributing via patches.
# Contributor side
git checkout -b feature/new-algorithm
# Make changes across multiple commits
git commit -m "feat: add compression algorithm interface"
git commit -m "feat: implement LZ4 compression"
git commit -m "feat: add decompression tests"
# Create patches
git format-patch main --output-directory=./patches --cover-letter
# This creates:
# patches/0000-cover-letter.patch
# patches/0001-feat-add-compression-algorithm-interface.patch
# patches/0002-feat-implement-LZ4-compression.patch
# patches/0003-feat-add-decompression-tests.patch
# Reviewer side
git checkout -b review/new-algorithm main
git am ./patches/*.patch
# If patches apply cleanly, merge
git checkout main
git merge review/new-algorithm
Sending Patches via Email
For projects that use email-based workflows (Linux kernel, git itself).
# Configure git-send-email
git config sendemail.smtpServer smtp.gmail.com
git config sendemail.smtpServerPort 587
git config sendemail.smtpEncryption tls
git config sendemail.smtpUser your-email@gmail.com
# Send a patch series
git send-email \
--to=maintainer@project.org \
--cc=mailing-list@project.org \
--cover-letter \
./patches/*.patch
# Send a single patch
git send-email \
--to=maintainer@project.org \
0001-My-change.patch
Patch Review Workflow
Review patches without applying them.
# View the patch stat
git apply --stat 0001*.patch
# View the full patch content
git diff --stat 0001*.patch
cat 0001*.patch
# Check if the patch applies to current HEAD
git apply --check 0001*.patch
# Apply to a temporary branch for testing
git checkout -b test-patch main
git am 0001*.patch
# Run tests, inspect code, then delete the branch
git checkout main
git branch -D test-patch
Common Errors
patch does not apply— The target code has diverged from the source. Rebase the patch series on the latest target branch, or usegit am --3wayto enable three-way merge fallback.- Trailing whitespace warnings — Patches fail if the linter catches whitespace. Use
git am --whitespace=fixto automatically fix trailing whitespace. git amrequires a clean working tree —git amrefuses to run with uncommitted changes. Stash or commit before applying patches.- Binary file patches are large — Patches for binary files are sent as base64-encoded full files. Consider using Git LFS for binaries and excluding them from patches with
.gitattributes. - Wrong patch order — Applying patches in the wrong order creates conflicts. Use
git format-patchoutput which numbers patches sequentially, and apply withgit am *.patch(sorted order).
Practice Questions
Challenge
Simulate a complete patch-based contribution workflow. Fork a repository, make three related commits on a feature branch, generate patches with a cover letter, transfer the patches to a fresh clone (no remotes), apply them with git am, resolve any conflicts by editing the patches, and verify the commits match the original (same author, message, and diff).
Real-World Task
The security research team at Durga Antivirus Pro needs to share signature updates with the main development team across an air-gapped network. Set up a patch workflow: researchers generate patches from their internal repository, transfer them on encrypted media, and the development team applies them via git am. The workflow must preserve commit authorship, include a cover letter describing each batch, handle conflicts gracefully, and verify patch integrity with GPG signatures.
Previous: Git Diff & Patch | Related: Git Hooks | Related: GPG Signing
Built by the developers of Doda Browser, DodaZIP, and Durga Antivirus Pro.
Built by the developers of DodaTech
Doda Browser, DodaZIP & Durga Antivirus Pro