Transition from monolith to microservices
Each more or less successful product comes to a state where adding new features to an existing code base becomes so difficult that the cost of new functionality exceeds all possible benefits from its use. Of course, a good and attentive architect will take care of the application in advance and direct the development in the right direction. The most popular approach at the moment involves sawing one large piece of code into many small projections, each of which is responsible for its specific capabilities. When designing such a system, a huge responsibility looms. It is necessary to think over and develop this type of interaction between these separately lying pieces so that future changes do not require rewriting everything to hell.
Of course, there are a lot of expert articles on the web that show us the importance of such an architecture and talk about which architecture can be called good and which not so good. There are a huge number of methods of interaction between individual programs of a large application with their own protocols, versioning the protocol and documentation, writing documentation on program interfaces, a way to deploy and synchronize all this stuff together. Of course, each such article or method is logical and consistent, and especially if the described method is confirmed by practice. But the trouble is not that the designers do not know which system they want to get in the end. The trouble is how to switch to such a proper architecture and when can you stop writing a monolithic application and start writing adult microservices already,
Firstly, the widespread “first monolith” approach is fully justified and seems to be a reasonable compromise between the cost of development and the speed of development. A small monolithic application has several quite obvious advantages, one of the main ones is the speed of adding new functionality. In our monolithic project, it’s easier to look at the coherence of the code base and make sure that the new, just added, functionality works. Undoubtedly, an experienced reader will notice that microservices can achieve poor connectivity of different parts of the application, but do not forget that in most cases actively developing monolithic projects have a code base of not the highest quality.
Do not get away from microservices
The second statement is that an infinitely huge application with infinite functionality cannot be monolithic. Sooner or later, parts of the application appear that run on different servers, or at least just different processes.
The main thing to start
The third conclusion is derived from the first two and it says that any monolithic application will sooner or later change its architecture to microservice. Accordingly, there is a point in time in application development when it is necessary to change the development strategy and begin to introduce microservices.
The above three statements pose two questions for us: when and how. Let's go in order.
How to understand that the moment has come that it is time to cut microservices already?
Let's approach this issue purely in practice, and limit the desired time point above and below. Definitely, it’s too early to cut a monolith if all the team members are still oriented in any part of the application. Also a sign of the timeliness of monolithic architecture is that a newcomer to the team can easily and naturally begin to develop new functionality immediately after familiarization.
It’s already becoming too late to allocate microservices if you want to cache the entire html-page because it slows down, but to speed up, you need to rewrite half of the application, replace ORM, or even rewrite everything in another language, where everything is fine and applications do not slow down.
It is too early to switch to architecture with microservices if any of the types of Fowler refactoring can be easily applied in a monolithic application. But it would be necessary to replace the monolithic architecture for a long time, if simple refactoring is not foreseen, or in general it’s hard to find such a place that could be reformed in a purely Fowler way.
And the most important criterion for the need to start switching to microservice architecture is when the cost of adding a new feature starts to exceed the benefits of this feature.
Where to start the migration of architecture in favor of microservices?
There are several strategies for changing the paradigm. The simplest of them and almost always incorrect is to develop a microservice architecture from scratch, using a monolithic application, as an example to follow. Probably, the prevalence of this approach is the main argument of adherents to write applications directly on microservices. But this seriously adds value to the initial application development.
A more adequate approach to the transition from a monolith to microservices is the gradual budding of microservices and the writing of new functionality separately from the main application. The approach is good and working, but has one significant drawback - the main monolithic application will not disappear in the foreseeable future. As a result, we will have a monolith and a bunch of auxiliary services, instead of a set of independent microservices.
Ultimately, a sane way to switch to microservice architecture is the way in which the main monolithic application is divided into several large-caliber applications with strong mutual connectivity. After that, the subapplications are considered and refactored separately, simultaneously hitting the neighbors and forcing them to adapt and change together. Gradually, this approach will lead to a decrease in connectivity and the emergence of a well-established interface for each sub-application. Upon reaching such a well-established time point, it seems possible to make changes to the sub-applications without affecting the neighboring ones. And this subapplication is considered as a monolith simpler and lower. And similar procedures are being done with him. Gradually, the application beats into more or less equal parts. Some parts in the process become unnecessary, some duplicate existing parts or even merge into one common service to eliminate duplication. As a result, sooner, or rather late, it turns out a well-established application on a microservice architecture.
Instead of conclusions.
Microservices are good. Monolith is good. Good code is good. Working code is good. The article does not urgently change the development principle in applications that slow down, are crookedly written or written differently than we would like. Also, microservice architecture is not a panacea for all the troubles of developers. The article describes the points and methods of transition from monolithic to microservice architecture.
“Fault tolerance”, “distribution”, “scalability” are certainly good, but this is not the main advantage of microservice architecture. The most important thing that this approach gives is the reduction in the cost of making changes.