Microservices vs Monolith: Complexity and Mitigation
There are 2 ways to look at complexity; Inherent complexity and what I'll call "aggregate" complexity.
Inherent (or perhaps "initial") complexity is rather simple to define. It is how complicated a solution is up front. How complex it is "necessarily". Aggregate complexity on the other hand is how complicated a solution becomes over time. Neither are particularly easy to measure however, and therein lies the problem.
I watched a Tim Corey video the other night on EF vs. Dapper. In it, he made a point which sort of stuck with me; Dapper doesn't hide the underlying DBMS so, developers using Dapper tend to get a better understanding of the persistence layer of their application. As a result, they tend to be better equipped to deal with issues in that layer.
I would fire back and suggest his data may be skewed. I suspect that a large base of Dapper users are also those with more pre-existing database understanding rather than people who were made better developers by virtue of choosing one over the other.
But, there is nonetheless a valid point in there somewhere. I also thought back over a lot of problems I've seen or been a part of over the years. And it has its roots in why I recommend architecting with microservices in mind, even if you think you will build and stick with a monolith.
Dapper is inherently more complicated than EF. If you start both with zero knowledge, you have to learn both Dapper and some amount of the underlying DBMS you want to put it on top of. EF you need much less DB specific knowledge.
But, EF tends to come with more aggregate complexity. Which is to say, while it allows you to get started more quickly, when things go wrong, and they eventually will (or you should at least that assume they will), then you will then be burdened with an even bigger complexity. Now you'll need both a better understanding of the underlying database and EF on a much more granular scale.
If you take Entity Framework *BECAUSE* it is easier and do not bother with the depth of learning/training then it will *BECOME* harder to deal with later.
As with my other topics; if you're skilled developer on a skilled team and you understand the tools thoroughly enough... then why are you here reading this? You wouldn't take this advice even if it did apply to you, and it perhaps it doesn't.
While this wasn't the exact point Tim was making, it IS the a point that I make on the microservices front. I assume that if you're looking for guidance that you don't fully understand the domain of the problem and/or the scope of where the project will go. So, I assume (as you should) that it will become something bigger and more complex than planned.
This, in turn, will undoubtedly drive you to investigate microservices if you went monolith or other possible broad architecture changes. But the aggregate complexity of pivoting architectures by the time things start to go sideways is often much bigger than any organization can deal with. And they instead fall into a cycle of rapid-fire maintenance cycles.
By starting with a multi-pronged approach you're biting off as a TON of inherent complexity. I won't lie. But, you're also hedging your bets against a world of aggregate complexity later. The more architectures and approaches you understand up front, the more you know how to integrate them, the less guess work and foundational work you have when things go sideways.
However, I want to add one more feather in the cap of microservices; mitigation.
When things go sideways, they almost always go sideways in very acute ways. One or two areas of the system are bringing everything down. When you are all in on a monolith there is no separating the festering wound from the rest of the healthy body of your app.
If you already have a microservices or hybrid architecture there are 3 possible scenarios:
- You got lucky and anticipated this and the problem code IS the entirety of a single microservice. In this case you can maybe scale resources for that one service while you work on things and you can address the code in isolation as well.
- You had a hybrid architecture, but this code was in the more monolithic part. In this case, you already have a microservices architecture. You have patterns you can follow. If it hurts bad enough you can amputate the service into a new microservice. And depending on where the issues are you may even be able to then use the same sorts of remedies.
- You have a hybrid architecture and the problem is a part of another Microservice. The situation here is probably the same or easier than #2.
Comments
Post a Comment