Branching Strategies

Course 2 · Ch 1
Branching Strategies
Git Flow, GitHub Flow, and trunk-based development — and how to pick the right one for a given project

Course 1 covered branches mechanically — create, switch, merge. What it didn't cover is the bigger question: which branches should exist, what are they for, and when do they get merged? That's a branching strategy — a set of conventions a team (or even a solo developer) agrees to follow, so collaboration stays predictable. This chapter covers the three most common approaches and how to choose between them.

Git Flow — The Original, Structured Approach

Git Flow was one of the earliest formalised branching models, built around scheduled releases. It defines several long-lived branch types, each with a specific job.

main develop feature/x release/1.2 hotfix/x
main = production · develop = integration · feature/* branches off develop · release/* stabilises before merging to main · hotfix/* patches production directly
  • main — always reflects what's currently in production, nothing else.
  • develop — the integration branch where finished features accumulate between releases.
  • feature/* — one branch per feature, branched from develop, merged back into develop when done.
  • release/* — cut from develop when preparing a release; only bug fixes happen here while it stabilises, then merges to both main and develop.
  • hotfix/* — branched directly from main for urgent production fixes, merged back to both main and develop.
Git Flow is heavier than most projects need today
Designed in 2010 for software shipped in discrete, infrequent versions (think: installed desktop software, not a constantly-deployed website). For a project that deploys continuously — most web apps and SaaS products today — the release/* branch layer often adds process overhead without a corresponding benefit. Worth knowing because it's still common in larger, versioned software projects, but rarely the right default for a new project today.

GitHub Flow — Simpler, Continuous Deployment

GitHub Flow strips this down to almost nothing: one long-lived branch (main), and short-lived feature branches that get reviewed via PR (Course 1, Chapter 7) and merged straight back in.

main feature/a feature/b
main is always deployable · each feature branch merges straight back via a reviewed PR, then gets deployed

No develop, no release/*, no hotfix/* — every change follows the exact same path: branch → commit → open PR → review → merge → deploy. This matches how most modern web projects actually ship, including continuous deployment setups where every merge to main can trigger an automatic deploy (Chapter 8 covers the GitHub Actions side of this).

Trunk-Based Development — The Leanest Option

Trunk-based development pushes simplicity even further: developers commit directly to main (the "trunk") as much as possible, using very short-lived branches — often merged within hours, not days — or sometimes feature flags instead of branches entirely, to hide unfinished work from users without needing a separate branch at all.

  • Branches, when used, live for hours, not days. The goal is minimising how far any branch diverges from main before merging back.
  • Feature flags hide incomplete work — code can be merged to main and deployed while disabled behind a flag, separating "merged" from "visible to users" entirely.
  • Requires strong automated testing to be safe — without a solid CI pipeline catching regressions before they reach main, frequent direct commits to main become risky fast.
Trunk-based development isn't "no branches" — it's "short branches"
A common misconception is that trunk-based means committing straight to main with no review at all. In practice, most teams still use very short feature branches and PRs (matching GitHub Flow closely) — the defining trait is the short lifespan, not the total absence of branches.

Comparing the Three

🌳
Git Flow
Best for: versioned releases
Desktop software, mobile apps with app-store release cycles, anything shipped in discrete numbered versions rather than deployed continuously.
Most structure, most overhead — worth it only when that structure maps to how the software actually ships.
🚀
GitHub Flow
Best for: most web projects
Websites, SaaS products, internal tools — anything continuously deployed where "merged to main" and "live" are close together in time.
The sensible default for the vast majority of new projects, including everything else covered in this course.
Trunk-Based
Best for: mature CI/CD, larger teams
High-velocity teams with strong automated test coverage, where merge conflicts from long-lived branches become a genuine bottleneck.
Needs investment in testing infrastructure first — adopting this without solid CI is how main branches get broken.

Choosing for Your Own Project

QuestionIf yes →
Do you ship in discrete numbered versions?Git Flow
Do you deploy continuously, every merge can go live?GitHub Flow
Solo project or very small team?GitHub Flow — simplest to maintain alone
Large team, strong CI, frequent merge conflicts a real pain point?Trunk-based, with feature flags
Not sure / starting fresh?GitHub Flow — easiest to adopt, easiest to explain to new contributors
Don't over-engineer this decision
The branching strategy is a convention, not a technical constraint — switching strategies later is entirely possible if a project's needs change. For almost any new project, especially a solo one, GitHub Flow is the right starting point: simple enough to need no documentation, and exactly what the rest of this series already assumes.

Chapter 1 Quick Reference

  • Git Flow — main/develop/feature/release/hotfix branches; built for versioned, infrequent releases
  • GitHub Flow — main + short feature branches + PRs; built for continuous deployment; the sensible default for most projects
  • Trunk-based — very short-lived branches or direct commits to main, often paired with feature flags; needs strong CI first
  • Choosing: versioned releases → Git Flow; continuous deploy → GitHub Flow; high-velocity team with strong tests → trunk-based
  • When unsure, default to GitHub Flow — simplest to adopt and explain
  • Next chapter: merge vs rebase — what's actually happening under the hood, and when to use each