Software development process required different environments for different purpose as we will see, each environment should be isolated for different team role to do their job and not accessed by other teams but should still similar in using the deployment workflow. Having solid and well-defined deployment workflow is tremendously important if you want to have smooth and solid deployment pipeline to production and follow the best practices for DevOps.
So if you would like to know and to follow the best practices for DevOps , Continuous Integration and Continuous Delivery, this post will help you know more about how to do that.
You can look at more info about DevOps in my post, DevOps: The Three Stage Conversation – People, Process, Products which will give you an idea about DevOps if you it’s pretty new to you, if you would like more depth but still prefer the high level, you might look at my quick guide about Basic Principles of Devops which will give you an overview about DevOps and the big picture but still in a high level view.
Lately I’ve been hearing a lot about pros and cons about deploying with Feature Branches in comparison with deploying with Feature Toggle. The difference between two strategies is quite huge from many perspectives and still both strategies are part of Continuous Integration and Continuous Delivery Chain. Key importance to remember is that deployment should be considered as a part of development process and not as alternative or afterthought.
If you would like to know more about CI/CD you can look at my post: Configure CI (Continuous Integration) and CD (Continuous Delivery Pipeline), if you want more focus on VSTS Release Management, you can see my video: Release Management and Build Automation with TFS/VSTS
In this post, I will try to address key differences between both deployment strategies, as well as benefits and drawbacks of each.
For purpose of having good understanding of this post we’ll be using in both scenarios same environments: Development, QA and Production. Let’s see first the differences between each environment:
- Development environment is where we’ll be actually using the whole set of processes and tools in order to create a product. Developers can use their machines for development environment or the team can set the remote development environment, which allows definitely better flexibility and accessibility.
- QA is many times referred also as Staging environment and it’s the place where testers come into play and starts with verifying that the Feature works as intended.
- Production environment is the last step in this chain and it represents the environment where the Feature will be deployed after testing. Usually after Feature deployment from QA to Production, its Feature Branch should be deleted.
Deploying strategy with Feature Branches is already an old, but yet very widely used deployment approach in software development. It’s known to be pretty simple approach, where you have the ability to organize coding in a way to have simple tracking of work in progress with already completed code, which has been completed and tested.
If we consider the environments as presented above, the workflow of deployment with Feature Branches would look like this:
To understand this workflow diagram, I will explain each step:
- Developer or group of developers will be working on Features (it could be also on bugs) in separate Feature Branch Let’s say that one developer is working on Feature called “Display navigation bars in Admin area”. The second developer is working on Feature called “Display product list” and the third developer is working on a Feature called “Display grid view for lists”.
- When the Features will be implemented they will be deployed into the QA or Staging environment for quality assurance.
- After successful completition of testing the Feature Branch will be merged into Development Branch.
- When the release will be ready, the development Branch will be merged into Master Branch and then deployed into Production environment.
This practice is commonly used as it gives the team the flexibility to deploy to the production only Features which are fully developed and tested. If the team has only 1 Feature Branch, which is ready for release, they will only merge this 1 Feature Branch to the Master Branch and then deploy it to production. In this case the team will be continuing the development work on other 2 Branches and they will merge them with Master and include in future releases.
As you can probably understand by now the philosophy behind Feature Branches, the purpose is to isolate the code for each Feature until the code is fully developed and ready for release.
One of the major problems in development by Feature Branches is that every time when Feature Branch will be ready for release, it will be prior to release merged into Master Branch. This will cause a really big Changeset in the Main Branch, which means that all other Feature Branches will need also to merge that huge Changeset back with their Feature Branches. Definitely other developers working on their Feature Branches will be the ones who will feel the pain with merging their changes. Actually, in many cases, it happens that the team refuses to merge their changes with the Master Branch, because this can cause them to much pain in merging what they have developed so far with the Master. This resistance is opposed to CI as there is no frequent integration between the code and it means couple of step back in development.
Feature Toggle, which is often referred to as Feature Flag is really good alternative to development and deployment by Feature Branches. Feature Flag will avoid some of the drawbacks coming from Feature Branches.
What it basically means? Let’s the image below:
As you can see, it means that we will do all the work in one single Branch, where we’ll use mechanisms, which will enable turning on or off specific Features. This is usually done via config file.
The workflow diagram in this case is completely different. All developers will work on the same Branch and they will include and enable Feature Toggles in their config files. Once when the development of the Feature will be finished, they will simply remove all entries for Feature Toggle, as their last step before merging to the Master Branch.
Build once and promote the same artifacts to different environments
For developers, this would mean that they would be simply building the code just one time and they will not build the code for each environment or branch. They will build code just once, merge it to Master branch and from there they will deploy the same code first to Development environment, then to the QA environment and finally to the Production environment.
It should be like the following:
Develop —-> merge to master—– > build ——> upload to storage —–> deploy to Dev —–> test—— > approve——> deploy to QA ——–> test—– > approve —–> deploy to Pre-Prod ———> test ——-> Deploy to n Prod
Don’t map branches to environments
Using strategy with Feature Toggles would mean that branches are not linked directly to environments which mentioned is the previous way of deployment when we use feature branch with middle litigation branch (dev branch)
As you can see promoting or moving the code from one environment to another will be implemented with deployments tools not with different branch. In previously explained strategy for example we would be promoting code by branch merging.
Using Feature Toggle means, that we are always promoting the same code (branch) trough different environments. The same code or the same artefacts go through all staging environments. We deploy code to environment, test it and deploy the same code to next environment, where we again test the same code and deploy it to the next environment.
With Feature Toggle, it avoids merge conflicts with the master branch after test complete
Another important aspect to avoid getting later errors for what we already tested is the recommendation to consider QA stage for complete product testing and not only to individual features, as testing only individual features in isolation will bring us to think that we have good quality of the code, while there are actually some merging or integration errors existing and we didn’t even know about them.
With Feature Toggle, you can disable the feature that you can’t fix and don’t delay the release
The main goal of the Feature Toggle is that since we using the same branch and if we have some bugs related to a particular feature and we don’t have time enough to our release or cadence, we can switch it off so we can release our cadence and don’t delay it.
Using Feature Toggle after release
Another important point that I would like to mention here is the rollback if something goes wrong after the release. Previously I’ve mentioned that developers can remove the Feature Toggle in their config file prior to merging to Master Branch. This necessarily doesn’t have to be the case, as they can leave Feature Toggle mechanisms just the way they are in order to being able turning off the Feature even after the release. This gives the team a full independency in fixing the Feature without impacting other Features, without having to roll back the whole version.
With Feature Toggles, we also have the possibility to target just a specific group of people or specific area. For example, we can turn on or off the Feature Toggle for specific users of your system, such as beta users or we can target just specific geographic area or countries.
Both strategies have their pros and cons, and at the end it depends also on team preferences with which strategy they will feel more comfortable to ensure Continuous Integration. As a part of being MVP, I know for a fact that Microsoft uses Feature Toggles broadly. Many of Microsoft’s new Features are turned on just for MVPs for Microsoft team to get quickly the feedback on the newly build Features. This new direction is living also inside VSTS for some time now and it gives both sides, users and developers insights about development direction.