XplormityXplormity
HomeHandbooks
Browse
Xplormity

TLDR developer handbooks for
seasoned developers.

Handbooks

RustNestJSNext.jsGitDockerTypeScriptReactNode.jsDSASQLSystem DesignTailwind CSS

Site

HomeHandbooksAboutPrivacyTerms

Connect

GitHubTwitterLinkedIn

© 2026 Xplormity. All rights reserved.

HandbooksGitBranching Strategies & Workflows

Branching Strategies & Workflows

branchinggitflowtrunk-basedworkflowhandbook

TL;DR

  • Trunk-Based Development: Everyone commits to main (with short-lived feature branches). Best for CI/CD.
  • GitFlow: Structured branches (develop, release, hotfix). Best for versioned software.
  • GitHub Flow: Simple — main + feature branches + PRs. Best for web apps.
  • Choose based on team size, release cadence, and deployment model.

Step 1: Trunk-Based Development

Trunk-based development is the oldest and simplest branching model — everyone commits to main (or trunk) with short-lived feature branches that last hours, not days. It was popularized by Google and Facebook because long-lived branches create merge hell, hide integration issues, and delay feedback. If your team has CI/CD, feature flags, and automated testing, trunk-based gives you the fastest path from code to production and forces small, reviewable changes that reduce risk.

The simplest and most CI/CD-friendly approach. Used by Google, Facebook, and most modern SaaS teams.

How It Works

main: ──A──B──C──D──E──F──G──H──
              \     /
feature:       X──Y  (short-lived, 1-2 days max)

Rules

  1. Main is always deployable — every commit on main should pass CI
  2. Feature branches live < 2 days — merge quickly, deploy often
  3. Use feature flags for incomplete features
  4. Rebase before merge — keep history linear
# Typical workflow
git checkout -b feature/quick-fix
# ... work for a few hours, max 1-2 days ...
git rebase main
git push
# Create PR → Review → Merge → Deploy automatically

When to Use

✅ Continuous deployment (web apps, SaaS) ✅ Small teams with high trust ✅ Strong CI/CD pipeline and test suite ❌ Not ideal for versioned releases or long feature development


Step 2: GitHub Flow

GitHub Flow was created as a simpler alternative to GitFlow for teams that deploy continuously. It has one rule: main is always deployable, and all work happens in feature branches that get merged via pull request. It's the sweet spot for most web teams — more structured than trunk-based (PRs give you code review gates) but without GitFlow's complexity of release branches, hotfix branches, and develop branches. If you deploy multiple times per day and don't need versioned releases, this is your model.

GitHub's own workflow. Simple and effective for most web teams.

How It Works

main: ──A──B──────────C──D──────E──
              \       /       \    /
feature-1:     X──Y──Z        |  |
                           feature-2: P──Q

Rules

  1. main is always deployable
  2. Create descriptively named feature branches from main
  3. Push regularly and open a Pull Request early (for discussion)
  4. After review + CI passes → merge to main
  5. Deploy immediately after merge
# 1. Create feature branch
git checkout -b feature/user-notifications

# 2. Work and push
git add . && git commit -m "feat: add notification bell"
git push -u origin feature/user-notifications

# 3. Open PR on GitHub
# 4. After review, merge (squash merge recommended)
# 5. Delete feature branch
git checkout main && git pull
git branch -d feature/user-notifications

PR Merge Strategies

Strategy History When
Squash merge 1 commit per feature Messy feature history
Merge commit Preserves all commits Clean, meaningful commits
Rebase merge Linear, no merge commit Small PRs

Step 3: GitFlow

GitFlow was invented in 2010 for software that ships versioned releases (mobile apps, desktop software, libraries). It separates "what's being developed" (develop), "what's being prepared for release" (release branches), and "what's in production" (main). It adds overhead that continuous-deployment teams don't need, but it's essential when you maintain multiple versions simultaneously, need release candidates for QA, or have compliance requirements around release processes. Don't use it for web apps that deploy on merge.

More structured. Best for software with explicit version releases.

Branch Structure

main:     ──v1.0──────────────────v2.0──────────
                \                /
develop:   ──A──B──C──D──E──F──G──H──────────
                   \     /   \      \
feature:            X──Y      \      \
                          release/2.0: R1──R2
                                              \
                                    hotfix/2.0.1: H1

Branches

Branch Purpose Lives
main Production releases only Forever
develop Integration branch Forever
feature/* New features Until merged to develop
release/* Release preparation Until merged to main + develop
hotfix/* Emergency production fixes Until merged to main + develop

Workflow

# Start a feature
git checkout develop
git checkout -b feature/payment-system
# ... work ...
git checkout develop && git merge feature/payment-system

# Prepare a release
git checkout develop
git checkout -b release/2.0.0
# ... bug fixes, version bumps ...
git checkout main && git merge release/2.0.0
git tag v2.0.0
git checkout develop && git merge release/2.0.0

# Emergency hotfix
git checkout main
git checkout -b hotfix/2.0.1
# ... fix critical bug ...
git checkout main && git merge hotfix/2.0.1
git tag v2.0.1
git checkout develop && git merge hotfix/2.0.1

When to Use

✅ Versioned software (libraries, mobile apps, desktop apps) ✅ Longer release cycles (weekly/monthly) ✅ Multiple versions in production simultaneously ❌ Overkill for web apps with continuous deployment


Step 4: Comparison Table

Choosing a branching strategy depends on your deployment frequency, team size, and release model. Teams deploying 10x/day with feature flags should use trunk-based; teams with weekly deploys and PR reviews fit GitHub Flow; teams shipping versioned software with QA cycles need GitFlow. The wrong choice either adds unnecessary ceremony (GitFlow for a 3-person startup) or insufficient safety (trunk-based without CI for a 50-person team with no tests).

Aspect Trunk-Based GitHub Flow GitFlow
Complexity Low Low High
Branch count 1-2 2-5 Many
Release cadence Continuous Continuous Scheduled
Feature flags needed Often Sometimes Rarely
Team size Any Small-medium Medium-large
Best for SaaS, web apps Web apps, APIs Libraries, mobile
CI/CD requirement Strong Strong Moderate

Step 5: Conventional Commits

Conventional Commits is a specification for commit messages that was created to enable automated tooling: auto-generating changelogs, determining semantic version bumps (patch/minor/major), and filtering commits by type. Without a standard format, changelogs are manually written (and forgotten), version bumps are guessed, and commit history is unsearchable noise. The type(scope): description format takes seconds to learn and unlocks tools like semantic-release, commitlint, and auto-changelog.

Standard format for commit messages. Enables auto-changelog, semantic versioning:

<type>(<scope>): <description>

[optional body]

[optional footer]

Types

Type Description Version Bump
feat New feature Minor (1.x.0)
fix Bug fix Patch (1.0.x)
docs Documentation None
style Formatting (no code change) None
refactor Code change (no feat/fix) None
perf Performance improvement Patch
test Adding tests None
chore Build/tooling changes None

Examples

feat(auth): add OAuth2 login with Google
fix(api): handle null response from payment gateway
docs(readme): update installation instructions
refactor(db): extract connection pooling to separate module

# Breaking change (triggers major version bump)
feat(api)!: change response format for /users endpoint

BREAKING CHANGE: Response now returns { data: [...] } instead of bare array

Step 6: Git Hooks for Workflow Enforcement

Git hooks automate quality gates that humans forget: linting before commit, running tests before push, validating commit message format, checking for secrets in staged files. They were built into Git from the start because code review catches problems too late — after the developer has context-switched. Hooks with tools like Husky and lint-staged run instantly on git commit, blocking bad code before it enters history. They're the cheapest form of quality enforcement and eliminate entire categories of PR review comments.

Pre-commit (lint + format)

#!/bin/sh
# .git/hooks/pre-commit
npm run lint-staged

Commit-msg (validate format)

#!/bin/sh
# .git/hooks/commit-msg
commit_msg=$(cat "$1")
pattern="^(feat|fix|docs|style|refactor|perf|test|chore)(\(.+\))?!?: .{1,72}"

if ! echo "$commit_msg" | grep -qE "$pattern"; then
  echo "❌ Invalid commit message format!"
  echo "Expected: type(scope): description"
  echo "Example:  feat(auth): add login page"
  exit 1
fi

Using Husky (Recommended)

npx husky init
echo "npm run lint-staged" > .husky/pre-commit
echo "npx commitlint --edit \$1" > .husky/commit-msg

Interview Questions

  1. What's the difference between trunk-based and GitFlow?

    • Trunk-based: everyone commits to main with short-lived branches (< 2 days). GitFlow: structured long-lived branches (develop, release, hotfix) for versioned releases.
  2. When would you choose trunk-based over GitFlow?

    • When you deploy continuously (SaaS, web apps), have a strong CI/CD pipeline, and want simple workflow. Feature flags replace long-lived branches.
  3. What are conventional commits?

    • A standardized commit message format (type(scope): description) that enables automated versioning, changelogs, and better collaboration.
  4. What merge strategy do you prefer for PRs?

    • Squash merge for PRs with messy history (keeps main clean). Regular merge for PRs with meaningful, well-crafted commits. Rebase for linear history preference.
Cherry-Pick, Bisect & Recovery

On this page

  • TL;DR
  • Step 1: Trunk-Based Development
  • How It Works
  • Rules
  • When to Use
  • Step 2: GitHub Flow
  • How It Works
  • Rules
  • PR Merge Strategies
  • Step 3: GitFlow
  • Branch Structure
  • Branches
  • Workflow
  • When to Use
  • Step 4: Comparison Table
  • Step 5: Conventional Commits
  • Types
  • Examples
  • Step 6: Git Hooks for Workflow Enforcement
  • Pre-commit (lint + format)
  • Commit-msg (validate format)
  • Using Husky (Recommended)
  • Interview Questions