Advanced Git Workflows
Explore popular workflows such as Git Flow, GitHub Flow, and Trunk-Based Development.
Advanced Git Workflows
Git workflows define how teams organize their development with Git. This tutorial explores the most popular methodologies and helps you choose the one that best fits your team and project.
Introduction to Workflows
A Git workflow is a set of rules and conventions that define:
- How to create and name branches
- When and how to merge
- Who can do what
- How to manage releases
Git Flow
Principle
Git Flow is a structured workflow with specialized branches for different types of development.
Branch Structure
Main Branches
main (or master)
- Production code
- Always stable
- Each commit = new version
develop
- Integration branch
- Latest developed features
- Base for new features
Supporting Branches
feature/
# Créer une feature branch
git checkout develop
git checkout -b feature/user-authentication
# Développer la fonctionnalité
# ... commits ...
# Merger dans develop
git checkout develop
git merge --no-ff feature/user-authentication
git branch -d feature/user-authentication
release/
# Créer une release branch
git checkout develop
git checkout -b release/1.2.0
# Finaliser la release (bug fixes, version bump)
echo "1.2.0" > VERSION
git commit -am "Bump version to 1.2.0"
# Merger dans main et develop
git checkout main
git merge --no-ff release/1.2.0
git tag -a v1.2.0 -m "Release version 1.2.0"
git checkout develop
git merge --no-ff release/1.2.0
git branch -d release/1.2.0
hotfix/
# Créer un hotfix depuis main
git checkout main
git checkout -b hotfix/critical-security-fix
# Corriger le bug
# ... commits ...
# Merger dans main et develop
git checkout main
git merge --no-ff hotfix/critical-security-fix
git tag -a v1.2.1 -m "Hotfix version 1.2.1"
git checkout develop
git merge --no-ff hotfix/critical-security-fix
git branch -d hotfix/critical-security-fix
Git Flow Tools
# Installation de git-flow
# macOS
brew install git-flow
# Ubuntu
sudo apt-get install git-flow
# Initialisation
git flow init
# Commandes git-flow
git flow feature start user-auth
git flow feature finish user-auth
git flow release start 1.2.0
git flow release finish 1.2.0
git flow hotfix start critical-fix
git flow hotfix finish critical-fix
Pros and Cons
✅ Pros:
- Clear, predictable structure
- Clean separation of environments
- Robust release management
- Ideal for products with release cycles
❌ Cons:
- High complexity
- Overhead for small teams
- Not suited to continuous deployment
- Long-lived branches
GitHub Flow
Principle
A simplified workflow centered on the main branch with short-lived feature branches.
Step-by-Step Workflow
# 1. Créer une branche depuis main
git checkout main
git pull origin main
git checkout -b feature/improve-performance
# 2. Développer et commiter
# ... développement ...
git add .
git commit -m "feat: optimize database queries"
# 3. Pousser régulièrement
git push origin feature/improve-performance
# 4. Ouvrir une Pull Request
gh pr create --title "Improve database performance" \
--body "Optimizes queries to reduce load time by 50%"
# 5. Review et discussion
# ... code review ...
# 6. Merger dans main
gh pr merge --squash
# 7. Déployer
# Déploiement automatique depuis main
GitHub Flow Rules
- main is always deployable
- Descriptive branches created from main
- Frequent pushes to origin
- Pull Request for every change
- Mandatory review before merging
- Immediate merge and deployment
GitHub Configuration
# .github/branch-protection.yml
protection_rules:
main:
required_status_checks:
strict: true
contexts:
- continuous-integration
- security-scan
enforce_admins: true
required_pull_request_reviews:
required_approving_review_count: 2
dismiss_stale_reviews: true
restrictions:
users: []
teams: ["core-team"]
Pros and Cons
✅ Pros:
- Maximum simplicity
- Easy continuous deployment
- Fast feedback
- Ideal for web apps
❌ Cons:
- No explicit staging
- Difficult for planned releases
- Requires robust CI/CD
- Can become chaotic without discipline
Trunk-Based Development
Principle
Development directly on the main branch, with very short-lived branches (< 1 day).
Key Practices
Frequent commits
# Commits multiples par jour sur main
git add .
git commit -m "feat: add user validation (partial)"
git push origin main
# Quelques heures plus tard
git add .
git commit -m "feat: complete user validation"
git push origin main
Feature Flags
// Utiliser des feature flags pour le code non terminé
function processPayment(amount) {
if (featureFlags.newPaymentSystem) {
return newPaymentProcessor(amount);
}
return legacyPaymentProcessor(amount);
}
Very short-lived branches
# Branche de maximum 1-2 jours
git checkout -b quick-fix/typo-correction
# ... correction rapide ...
git push origin quick-fix/typo-correction
# ... PR et merge immédiat ...
Releasing from Trunk
# Release branches depuis main
git checkout main
git checkout -b release/2024.03.15
git tag v2024.03.15
git push origin release/2024.03.15
git push origin v2024.03.15
# Hotfixes directement sur main
git checkout main
# ... fix ...
git commit -m "hotfix: critical security patch"
git tag v2024.03.15.1
git push origin main
git push origin v2024.03.15.1
Pros and Cons
✅ Pros:
- Maximum continuous integration
- No merge hell
- Immediate feedback
- Extreme simplicity
❌ Cons:
- Requires strict discipline
- Automated tests are mandatory
- Complex feature flags
- Not suited to every type of project
GitLab Flow
Principle
A combination of GitHub Flow with environment branches.
Structure with Environments
# Branches d'environnement
main # Développement
staging # Tests d'intégration
production # Production
# Workflow
git checkout main
git checkout -b feature/new-api
# Développement
git push origin feature/new-api
# ... Pull Request vers main ...
# Déploiement staging
git checkout staging
git merge main
git push origin staging
# Tests en staging
# ... validation ...
# Déploiement production
git checkout production
git merge staging
git push origin production
Release Branches
# Pour les releases planifiées
git checkout main
git checkout -b release/2.1.0
# Cherry-pick des features
git cherry-pick feature-commit-1
git cherry-pick feature-commit-2
# Déploiement de la release
git checkout production
git merge release/2.1.0
git tag v2.1.0
Forking Workflow
Principle
Each developer has their own fork of the main repository.
Complete Workflow
# 1. Fork du dépôt principal (via GitHub)
# 2. Clone de votre fork
git clone https://github.com/VOUS/projet.git
cd projet
# 3. Ajouter l'upstream
git remote add upstream https://github.com/ORIGINAL/projet.git
# 4. Créer une branche feature
git checkout -b feature/awesome-feature
# 5. Développer
# ... commits ...
# 6. Synchroniser avec upstream
git fetch upstream
git rebase upstream/main
# 7. Pousser vers votre fork
git push origin feature/awesome-feature
# 8. Créer une Pull Request vers l'upstream
Fork Maintenance
# Synchronisation régulière
git fetch upstream
git checkout main
git merge upstream/main
git push origin main
# Nettoyage des branches
git branch -d feature/completed-feature
git push origin --delete feature/completed-feature
Choosing the Right Workflow
Decision Criteria
Comparison Table
| Workflow | Complexity | Team | Deployment | Releases |
|---|---|---|---|---|
| GitHub Flow | Low | Small-Medium | Continuous | Frequent |
| Git Flow | High | Medium-Large | Scheduled | Scheduled |
| Trunk-Based | Low | Any | Continuous | Continuous |
| GitLab Flow | Medium | Medium | Mixed | Flexible |
| Forking | Medium | Open Source | Variable | Variable |
Setting Up a Workflow
GitHub Flow - Configuration
# .github/workflows/ci.yml
name: CI/CD
on:
push:
branches: [main]
pull_request:
branches: [main]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- name: Run tests
run: npm test
deploy:
needs: test
if: github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
steps:
- name: Deploy to production
run: ./deploy.sh
Git Flow - Scripts
#!/bin/bash
# scripts/git-flow-feature.sh
FEATURE_NAME=$1
if [ -z "$FEATURE_NAME" ]; then
echo "Usage: $0 <feature-name>"
exit 1
fi
# Créer la feature branch
git checkout develop
git pull origin develop
git checkout -b "feature/$FEATURE_NAME"
echo "Feature branch feature/$FEATURE_NAME created"
echo "When done, run: git-flow-feature-finish.sh $FEATURE_NAME"
Trunk-Based - Hooks
#!/bin/bash
# .git/hooks/pre-push
# Vérifier que les tests passent avant push
npm test
if [ $? -ne 0 ]; then
echo "Tests failed. Push aborted."
exit 1
fi
# Vérifier que le code est formaté
npm run lint
if [ $? -ne 0 ]; then
echo "Linting failed. Push aborted."
exit 1
fi
Practical Exercises
Exercise 1: Simulate GitHub Flow
# 1. Créer un dépôt de test
mkdir github-flow-demo
cd github-flow-demo
git init
echo "# GitHub Flow Demo" > README.md
git add README.md
git commit -m "Initial commit"
# 2. Simuler le développement d'une feature
git checkout -b feature/add-calculator
echo "function add(a, b) { return a + b; }" > calculator.js
git add calculator.js
git commit -m "feat: add calculator function"
# 3. Simuler une Pull Request (merge)
git checkout main
git merge --no-ff feature/add-calculator
git branch -d feature/add-calculator
# 4. Répéter avec d'autres features
git checkout -b feature/add-tests
echo "// Tests for calculator" > calculator.test.js
git add calculator.test.js
git commit -m "test: add calculator tests"
git checkout main
git merge --no-ff feature/add-tests
git branch -d feature/add-tests
Exercise 2: Experiment with Git Flow
# 1. Initialiser Git Flow
git flow init
# 2. Créer une feature
git flow feature start user-authentication
echo "function login() { /* auth logic */ }" > auth.js
git add auth.js
git commit -m "feat: add login function"
git flow feature finish user-authentication
# 3. Créer une release
git flow release start 1.0.0
echo "1.0.0" > VERSION
git add VERSION
git commit -m "bump: version to 1.0.0"
git flow release finish 1.0.0
# 4. Simuler un hotfix
git flow hotfix start critical-fix
echo "// Fixed critical bug" >> auth.js
git add auth.js
git commit -m "fix: resolve critical authentication bug"
git flow hotfix finish critical-fix
Cross-Cutting Best Practices
Commit Messages
# Convention Conventional Commits
feat: add new user authentication system
fix: resolve login timeout issue
docs: update API documentation
style: format code according to style guide
refactor: restructure user service
test: add unit tests for payment module
chore: update dependencies
Branch Protection
# Via GitHub CLI
gh api repos/:owner/:repo/branches/main/protection \
--method PUT \
--field required_status_checks='{"strict":true,"contexts":["ci"]}' \
--field enforce_admins=true \
--field required_pull_request_reviews='{"required_approving_review_count":2}'
Automation
# .github/workflows/workflow-enforcement.yml
name: Workflow Enforcement
on:
pull_request:
branches: [main]
jobs:
check-branch-name:
runs-on: ubuntu-latest
steps:
- name: Check branch name
run: |
if [[ ! "${{ github.head_ref }}" =~ ^(feature|fix|hotfix)/.+ ]]; then
echo "Branch name must start with feature/, fix/, or hotfix/"
exit 1
fi
Additional Resources
Workflow Tools
- Git Flow AVH: Enhanced Git Flow extension
- GitHub CLI: Automation of GitHub workflows
- GitKraken Glo: Integrated project management
- Sourcetree: Graphical interface with workflow support
Documentation
Conclusion
Choosing a Git workflow depends on many factors: team size, project type, deployment frequency, and company culture. What matters is to choose a workflow that fits your context and to stick with it consistently.
In the next tutorial, we’ll explore Git submodules and subtrees for managing complex projects with external dependencies.
Estimated reading time: 35 minutes
Level: Advanced
Previous step: Conflict Resolution
Next step: Git Submodules and Subtrees