Bamboo Best Practice - Branching and DVCS
No matter how scary it may seem, branching your code is unavoidable - and also a very powerful way to let developers work in isolation on different aspects of your project.
The simplest branching model is that of a master branch and a development branch. The master (or mainline) branch contains the production versions for release. Parallel to master runs the development branch, where developers work on features that will be merged back into master. When sufficient new features have been developed, they will be merged back into master and form the next production release.
The simple model can be extended with other branches to make development work more flexible. These include:
- Feature branches
- Release branches
- Hotfix branches
But because a developer isn't constantly merging changes from master into their development branch, there may be uncertainty about whether the code will work when it is eventually merged back into master. The last thing you want is to pollute your master with non-functioning code from the branch.
Bamboo offers a number of useful tools for tackling branches. This best practice guide explores some of the ways that Bamboo handles branching to improve your development practices.
You may also want to refresh your Git knowledge with the Atlassian Git tutorials page before you read any further.
Best practice approaches
Feature branching with Bamboo plan branches
Objectives and learning outcomes
Understand what feature branching is, and how it can be useful as a development process. After completing this section, you will understand:
- How feature branching works
- How feature branches improve quality by eliminating risky merges
What is feature branching?
Feature branching is a lightweight way for a developer to make changes to a software project without having to worry about sharing those changes if they are uncompleted.
The main reasons to use feature branching are to ensure accurate conflict mitigation and to reduce the possibility of pushing code into the master branch or to other people until you are ready to do so. Utilizing rapid, regular code merges assists in reducing code drift across the development process.
Bamboo uses a concept called plan branches to help teams easily test branches using continuous integration and to avoid "merge hell".
Let's examine the following scenario for traditional feature branching:
- A developer assigns an issue to themselves and creates a new branch (the feature branch) from master.
- The developer works on the code, makes regular local commits to the feature branch, reaches a finishing point and pushes the commits to the repository.
- When the issue is completed, the feature branch is merged back into master.
So, what's wrong with this? The developer hasn't run their builds on the feature branch and it is unknown whether the tests pass or not and any defective code from the feature branch will reach the rest of the team when it's merged to master.
Now let's see how it works using JIRA and Bamboo plan branches:
- A developer assigns the issue to themselves in JIRA and creates a new branch from master. The name of the branch starts with the issue key so that it can be easily identified and tracked by both Bamboo and JIRA.
- Bamboo detects the new feature branch and creates a new plan branch. A plan branch is created automatically for any build that has plan branching enabled.
- The developer works on the code, makes regular local commits and pushes the commits to the repository.
- Bamboo identifies the changes and builds the corresponding plan branch.
- Optionally, to ensure that the branch and master will work together when merged, Bamboo can then merge the contents of master (including any new changes the team has made) into the the feature branch and have the build run.
- If the tests pass, Bamboo pushes the updated feature branch back to the repository.
- When the issue is completed, the feature branch is merged back into master with the knowledge that their new feature will not break on master.
We can already see that the Bamboo plan branch helps us by running build plan tests against the newly merged code. Only if the tests are passed is the code pushed, which prevents incorporating defective code. If the build fails, the merge is thrown away and the developer is notified.
Extending feature branching
We can usefully extend the concept of feature branching to include an integration branch workflow. This concept mirrors the approach of feature branching in that it also advocates frequent merging. However, it provides an integration branch during development of a particular story. When the story is completed, it is merged into master, but offers two different approaches to working around the integration branch:
- Some teams merge their code into the integration branch while the story development is in progress; when the story is complete, it is then merged directly into master and closed
- Other teams may work exclusively around the integration branch during their code development, but will wait until the very end when their stories are tested and validated before merging integration onto master.
Feature branching offers a flexible and accurate conflict mitigation tool for developers. By using frequent and regular code merges, code drift and defective code implementation across the project is minimized. Feature branching works particularly well when developers have permission to toggle auto merging on and off to suit their individual development cycle. And of course, Bamboo provides an ideal environment to give developers access to these permissions.
Approaches to branching
Objectives and learning outcomes
Identify and describe how Bamboo can use feature and plan branches. After completing this section, you will understand:
- The two mechanisms for merging branched code back into the master branch
- A high level concept view of the branching process
Feature (or topic) branches are used to develop new features for an upcoming or future release. A feature branch exists only as long as the feature is being developed, and will eventually be merged back into the development branch.
Plan branches represent a branch in the version control system for development of a specific feature. The plan branch inherits all of the configuration defined by the parent plan, but may be built against any other specified plan. Any new branch created can be automatically built and tested using the same build configuration as that of the parent plan. Alternatively you can override the parent plan and individually configure the branch plan. When the branch succeeds, it is merged back into master.
There are two ways in which plan branches can be merged with the master branch.
Let's consider the following branch scenarios:
Scenario 1: Gatekeeper
The gatekeeper method works in the following way:
- Both master and feature branch are checked out from the repository
- Changes are merged into master from the feature branch
- The build plan is run against the merged code, and held in memory by Bamboo
- If successful, the merged code is pushed to master
You should use the Gatekeeper strategy when you want to:
- Automatically merge your feature branch back into the master branch after a successful build of the merged changes
- Quickly identify when a build of combined changes fails, preventing the feature branch from being merged back into the master branch
Scenario 2: Build Updater
The build updater is an alternative approach where changes flow in the opposite direction. It works in the following way:
- Both master and a feature branch are checked out from the repository
- Changes are merged into the plan branch from master
- The build plan is run against the merged code and held in memory by Bamboo
- If successful, the merged code is pushed to the feature branch
You should use the Build Updater strategy when you want to:
- Automatically merge changes from the team's master branch into your feature branch, either after a successful build of the master branch, or at the start of builds against the feature branch.
- Get notified when the changes on your feature branch are no longer compatible with the team's master branch.
Now we know how plan branching works, but how do we implement it using Bamboo? Bamboo actually makes it very easy for us. Let's have a look at another example:
Scenario 3: Plan branching in DVCS
This is a typical high level DVCS plan branching scenario:
Step 1: Create branch - Use your version control system's branching feature to create a new branch in your repository
Step 2: Branch detection - Bamboo will auto detect the new branch for Git, Mercurial and SVN. Perforce and CVS users will have to manually create the branch on Bamboo's behalf. This can be done from the Branches tab in your build plan's configuration screen.
Step 3: Plan cloning - Bamboo automatically clones all plans associated with the repository and connects the clones to the new branch
Step 4: Configure plan variables - The configuration of plans pointing to the master branch will be inherited by the plan branches. Jobs, stages, and artifact sharing work exactly as defined in the original plan. Variables, notifications and triggers may be customized for each plan branch. Other configuration options for plan branches include:
- Merge strategies (see gatekeeper and build updater above)
- Toggling auto cleanup on/off
- Branch removal after a defined inactivity period
Step 5: Branch build - The feature branch is built in accordance with its triggers. The optional merge strategies are applied at build time.
Feature and plan branching offers a range of flexible methods for developers to branch and work on different code segments during the development process. The Gatekeeper and Branch Updater methods allow alternative approaches to branching your code, while plan branching in DVCS allows Bamboo to automatically detect new branches in Git, Mercurial and SVN repositories.
Branching with JIRA integration
Objectives and Learning Outcomes
Understand how JIRA integration can be used to track development changes branching, and how it improves oversight of a development project. After completing this section, you will understand:
- What JIRA integration is
- How it can be used to track changes within the code development
JIRA integration in plan branches relies on including a JIRA issue key as part of the branch name. Bamboo and JIRA work together to ensure that JIRA issues are attached to development branches, allowing developers and other interested parties to examine which issue has informed the code development within the branch.
Let's examine the following scenario for JIRA integration:
- A developer picks up a JIRA issue and creates a feature branch for it
- Bamboo creates a link between the issue and the branch, and all the branch's builds
- The developer works on the issue, makinkg regular pushes to the feature branch, which are built by the corresponding plan branch/es in Bamboo
- The JIRA issue shows the current build status of the feature branch
- When work on the feature branch is complete, it can be merged to master manually through the version control system, or automatically, by enabling Bamboo's gatekeeper merge strategy
Why use JIRA integration?
By including a related JIRA issue as part of the branch name, Bamboo can link the issues to the related builds and to the branch itself. This makes oversight of individual stories much easier:
- Product owners can view the development of user stories from within the JIRA issue
- QA can select an artifact for testing from within JIRA, and identify which issues have informed its development
- Developers can examine builds and artifacts, and see which JIRA issues have informed the development process.
The JIRA Bamboo plugin
The JIRA Bamboo plugin provides enhanced information sharing between JIRA and Bamboo, allowing you to view the status of all builds and branches associated with an issue from within the issue itself. Apart from DVCS and branching, the plugin also surfaces deployment information for issues when Bamboo's deployment projects are used.
Learn more about the JIRA Bamboo plugin here.
JIRA integration with branching provides an effective mechanism for tracking changes in code development and identifying what issues have informed the process. JIRA integration also provides an effective way for interested parties to track progress and locate relevant artifacts.