The digital era in which we live nowadays requires us to bring several changes to our way of doing things. Businesses that are still seeing software development as a costly burden and not as a strike force, will soon face many important challenges. To surf on the technological wave, businesses need to be able to adapt to today’s reality. To stay competitive, we need to launch products on the market sooner, improve them quickly and the right way, and offer an excellent experience to our customers.
To reach these goals, businesses doing Agile development need to integrate Agility and adaptability on three different levels:
- The people: they have to be comfortable with experimentation and change;
- The processes: they need to be iterative and optimized for learning;
- The technology: it needs to support quick delivery of the product.
Technical Agility cannot be ignored; Agile people with Agile processes cannot compensate for deficient technology.
Evolution of Agile development
Since the Agile Manifesto’s publication in 2001, development methods have changed a lot. Building on the Manifesto’s principles, several practices have been put forward to address recurring problems frequently blocking or slowing down teams.
Continuous integration comes from Extreme Programming and aims at combining all software components as soon as possible to minimize efforts invested in fixing integration issues. By adding automated testing, the risk linked to quality is greatly diminished and confidence toward the product is constant. If we address blockers during the programming process, it’s normal to continue for delivery.
Continuous delivery uses the same concept and applies it to a more external vision of the product. By defining an automated deployment process, the validated increment is delivered to the final user as quickly as possible. On this level, we need to take Scrum’s “functional and usable increment” at face value. We can thus benefit from transparency on the product and the development process instead of having a rarely functional environment and disappointed users.
By allowing programmers to take charge of deployments in production environments, we can question the traditional division between development and operations teams. By combining the two types of teams, always with the objective of optimizing product delivery, we can afford to address new blockers that were the responsibility of operational teams until now. This time, we have access to new tools coming from development teams. The DevOps movement supports this collaboration by encouraging programmers to consider the operational perspective in the solutions’ design, and by inviting operations to use a more scientific approach to issues usually managed procedurally.
Several pioneers who have followed this Agile evolution have found themselves with an optimized delivery process, but also with a solution delivered in a single piece. As the solution’s complexity and scope grow, this architecture slows down the development of new functionalities and becomes an obstacle to the extensibility that cloud computing can offer. Some businesses, like SoundCloud, have discovered that by dividing their monolithic applications into several microservices, they can better support their Agile delivery and establish a DevOps culture. Microservices then come into play…
What is a microservice?
Before tackling the concept of microservice, it is important to understand what a monolithic architecture is. Let us imagine that you are presently creating a carpooling application. With the different architectural components (database, user interface, business logic and a few services coming from third parties), we end up with hexagonal architecture:
The more time goes by, the more this application gets bigger and you quickly have to face the scaleability needs of certain parts of the application to be able to support the workload. It is a relatively simple task, we only have to install the application (or parts of it) on several servers behind a load balancer. By automating this part, we can benefit from the elasticity concept and have a solution that adapts to the required load.
On the other hand, since every implementation stays vulnerable to mistakes that could be introduced in the common code, there is always a reluctance to make architectural changes since we do not want to destabilize the whole system. Furthermore, we tell ourselves that once caught up in it, we will have to migrate all the code to use this new technology.
To summarize, the application might be in several environments, but it is still considered as a whole. Microservices act more like mini-applications that have their own architecture and only concern a business domain. The development teams can then work without being afraid of having an impact on the rest of the application, provided that the API’s contract is respected.
It becomes more interesting to try new technologies and to experiment, because communication between each module is configurable. This advantage brings us closer to A/B testing, which consists in experimenting with several variants of a same module to determine which version gives the best results.
Also, by keeping a database in a separate environment for each module, we end up with an unchangeable application that does not have the necessary data to process to memory. In this context, it is possible to create containers (with Docker for example) and to benefit from a very light server environment, easy for the development, operation and infrastructure teams to migrate. Since the software dependencies are managed by containers, there is no longer any need to worry about the presence of all necessary components before installing the application.
Like most software development practices, using microservices is not a solution to every possible issue. On the other hand, when using them gradually to connect with existing systems and services, they offer the Agility and development speed allowing businesses to move forward and innovate with means that were previously unavailable.
In the second part of this article that will be published shortly, we will continue to explore microservices, and notably how we can use Domain Driven Design to create them.