This guide explains how to perform a complete gitflow release from develop to main and back to develop.
Gitflow is a branching model that uses dedicated branches for releases. The complete flow involves:
- Create a release branch from
develop - Bump version and prepare release
- Merge release to
main(production) - Merge release back to
develop(to sync changes)
# Ensure you're on develop and it's up to date
git checkout develop
git pull origin develop
# Create release branch (e.g., for version 1.1.1)
git checkout -b release/1.1.1# Update version in package.json
# Change "version": "1.1.0" to "version": "1.1.1"
# Commit the version bump
git add package.json
git commit -m "chore(release): bump version to 1.1.1"
# Optional: Run tests to verify everything works
npm ci
npm test
npm run buildThe release branch should be merged to main via a Pull Request:
⚠️ Important: When creating the PR, always verify that the base branch is set tomain, notdevelop. GitHub may default to a different base depending on how the branch was created.
# Push release branch
git push origin release/1.1.1
# Create PR: release/1.1.1 → main ← base MUST be main
# Title: "chore(release): v1.1.1"
# Include:
# - List of changes since last release
# - Version bump details
# - Test resultsPR Description Template:
## Release v1.1.1
Merging release branch to main for version 1.1.1.
### Changes
- List key features, bug fixes, and updates
- Include PR/issue references
### Version
- Version bumped from 1.1.0 to 1.1.1
### Testing
- All tests passing (specify numbers)After PR is merged to main:
# Tag the release on main
git checkout main
git pull origin main
git tag -a v1.1.1 -m "Release version 1.1.1"
git push origin v1.1.1After merging to main, merge the release changes back to develop:
Option A: Via Pull Request (Recommended)
# The release branch already has the version bump
# Create PR: release/1.1.1 → develop (or cherry-pick to new branch)
# If cherry-picking:
git checkout develop
git pull origin develop
git checkout -b chore/merge-release-1.1.1-to-develop
git cherry-pick <release-version-bump-commit-sha>
git push origin chore/merge-release-1.1.1-to-develop
# Create PR: chore/merge-release-1.1.1-to-develop → developOption B: Direct Merge
# Only if you have direct push access
git checkout develop
git pull origin develop
git merge --no-ff release/1.1.1 -m "chore: merge release/1.1.1 back to develop"
git push origin developPR Description Template:
## Merge release v1.1.1 back to develop
Completes the gitflow release cycle by incorporating release changes into develop.
### Changes
- Version bump: 1.1.0 → 1.1.1
### Why This Is Needed
In gitflow, release changes must flow back to develop to ensure:
- Future features start from the correct version
- Develop stays synchronized with production
- No version conflicts in next release
### Testing
- All tests passing# Delete the release branch locally and remotely
git branch -d release/1.1.1
git push origin --delete release/1.1.1Here's a complete example for releasing version 1.1.1:
# 1. Create release branch
git checkout develop
git checkout -b release/1.1.1
# 2. Bump version
# Edit package.json: "version": "1.1.1"
git add package.json
git commit -m "chore(release): bump version to 1.1.1"
# 3. Push and create PR to main
git push origin release/1.1.1
# Create PR: release/1.1.1 → main
# 4. After PR merged to main, tag the release
git checkout main
git pull origin main
git tag -a v1.1.1 -m "Release version 1.1.1"
git push origin v1.1.1
# 5. Merge back to develop
git checkout develop
git pull origin develop
git cherry-pick <version-bump-commit>
git push origin develop
# Or create PR with the cherry-picked commit
# 6. Cleanup
git branch -d release/1.1.1
git push origin --delete release/1.1.1The release branch may contain:
- Version bumps: Essential for next development cycle
- Release notes/changelog updates: Documentation of what shipped
- Last-minute bug fixes: Critical fixes made during release prep
- Build or config changes: Release-specific adjustments
Without merging back to develop:
- ❌ Next feature branches start from old version
- ❌ Version conflicts in next release
- ❌ Missing release-specific fixes
- ❌ Divergent history between main and develop
For the v1.2.0 release:
✅ Step 1: Release branch created from develop ✅ Step 2: Version bumped to 1.2.0 ✅ Step 3: Ready to merge to main (via current PR) ⏳ Step 4: After main merge, needs to merge back to develop ⏳ Step 5: Cleanup release branch
- Always use PRs: Even for develop, use PRs for review and CI/CD
- Test thoroughly: Run full test suite before creating release
- Document changes: Update CHANGELOG if present
- Tag releases: Always tag releases on main for easy reference
- Consistent naming: Use
release/X.Y.Zformat for release branches - Clean history: Use
--no-fffor merge commits to preserve release history
# If you get "refusing to merge unrelated histories"
git merge --allow-unrelated-histories release/1.1.1# Resolve conflicts manually, then:
git add <resolved-files>
git commit# If cherry-picking causes conflicts:
git cherry-pick --abort
# Then manually apply the changes and commit- Gitflow Workflow
- Semantic Versioning
- Project Version: Check
package.jsonfor current version