Making sense of all the continuous practices
The flood of continuous practices and jargons around some of the new ways of working can be unnerving to new teams, here's an attempt to simplify and put it all together in one picture
The last four years have witnessed remarkable changes in the way we perform most of the post development tasks in a typical Agile methodology based software development. And with the excitement also comes confusion of not just the why? but what? and how? too. In this blog post I'll try to break down continuous cycle and re-assemble(based on my experience) to help readers make sense of it.
If I've to put it in one diagram "Continuous Delivery" would essentially look like this
As novel as it may seem, I agree it is quite hard to figure out what the implementation would look like. So let's start creating some pictures (worth a thousand words) to see what the typical continuous delivery cycle is made up of. Lets look at the two steps Code & Build. These two in continual cycles is what we call Continuous Integration.
Continuous Integration is a software development practice where members of a team integrate their work frequently, usually each person integrates at least daily - leading to multiple integrations per day. Each integration is verified by an automated build (including test) to detect integration errors as quickly as possible. - Martin Fowler
The idea is that we keep the source code in a centralised repository to which all members keep adding their code regularly (at least once a day or even better many times a day in small batches) and this addition of code would trigger a build, including tests. The passing or failure of build then becomes a quick feedback about whether the "new code" has added working functionality to the systems or broken regression (or both ;-) ). Let's look at a diagram of how we our team gets it done here.
As you can see there's quite a bit of "integration" going on to get get continuous integration working, we have Git as the Version Control System, a Project/Product Lifecycle Management Tool, Mr. Jenkins and whole lot of analysis and reports. It's important to understand the flow none-the-less; which starts in our case as soon as a developer "pushes" code to our Git Repository.
The git repository runs some of it'd own check primarily validating comments are in a particular format or not
it then notifies our build server to run a build
It also notifies the life cycle management tool to update revision history and build status to in progress (there's a radiator view from this ALM which is on display on this floor)
The build, maven on jenkins in our case runs a in four steps, static code analysis using Sonar, we're using an approach here of failing the build at first error, so this is the first litmus test, confirming code follows a certain coding standard
It then runs the compilation and similar tasks
This is followed by tests, as defined in maven build life cycles, we run unit and "integration tests" here via maven life cycles
The reports from all of these are provided as feedback to the developer and publish in the builds dashboard too
In case of failure, our ALM creates a defect and assigns it to the developer, other than letting others know who broke the build
This cycle by itself does solve a lot of issues in terms of keeping the code healthy and ensuring regression hasn't broken. However, defects don't just come from bad engineering; they also come due to misunderstanding of features. So we need more that just continuous unit / component / service tests to be sure our product works as expected. Typically what really matters is that the users, who would actually use your system in one or more "flows" are delivered a non-buggy experience. To get to that stage is to ask ourselves after every continuous integration cycle.
Is this enough to put the product in production?
If the answer is no, you start tracing answers to why? from production backwards to your development, you'll sooner or later come down to one or more of following activities pending before we could be certain
Functional Regression and Testing to new features
End-To-End Use cases to be tested
Configuration, hardening or similar activities etc
So we need to find a way where we could run all of these in continuous cycles, hence comes the word "Continuous Testing" which in my experience is bringing heavy automation to testing so as to enable running all the above mentioned tests in continuous cycle just like build and development. Going by that, we're simply adding another spoke to our continuous wheel.
Typically you will be creating separate jobs in Jenkins one each for deployment, preparing every kind of test fixture and running these tests. I'd prefer to deploy in parallel to one environment dedicated for each of functional, nonfunctional test cases such as security etc., and performance tests and run jobs for thes heavier tests in them, stopping any further deployment if any of these tests fail.
Now to actually get there and be at a position to use all of this you'd need a way to be able to continuously deploy to environments, yup that's where Continuous Deployment fits in (and keeps it self only to this context); it is the ability to deploy to any target environment in a repeatable, automated manner, ideally with all continuation changes too, at the click of a button. So if I had to explained our previous diagram I'd just highlight one of the places where it is comping to picture in the continuous cycles.
Even with all of this automation in place, you'd still require manual verification at some stage, we should keep all such steps for the "pre-production" or staging environment IMHO. And finally deploy to production once all other pre-requisites are fulfilled.
You'll notice I haven't put in steps related to business process or planning and budgeting around releases; other than the fact that they cannot be automated; we have to address them in small batches too, that's like bringing in "Agile" to planning (here I mean beyond the sprint planning) too, or may be some sort of continuous planning in for example twice a quarter. They have to be addressed none the less in a way they fit better with the small batch high paced world of software product development that the world is slowly moving towards, when you realise moving these process to a more "agile" way is when you attain what we showed in the first diagram; Continuous Delivery!
It's important to realise why we are doing all of this so as to be able to understand what these practices are and hence build competency to utilise them in your software development lifecycle.