Will Modular Monolith Replace Microservices Architecture?

Itiel Maayan
AT&T Israel Tech Blog
7 min readAug 3, 2022

Modular Monolith vs Miniservices vs Microservices

Last year, there was a lot of buzz around the modular monolith; we could see this in many trend graphs. Many R&D managers are asking if this is a replacement/alternative to microservices or something else. And, if the answer is “something else” — what is it, and how will it fit in our architectural patterns landscape.
In this article, I’ll explain what modular monolith is, why some people think it is a replacement for microservices, and my recommendations for using the different architectural patterns.

Monolith Cons = Microservices Pros

There are many disadvantages to the monolith architecture pattern. These pushed almost everyone to switch to the microservices pattern. Having said that, microservices are not all good and they have their challenges and weak spots which I’ll describe briefly later.
The key monolith disadvantages and microservices advantages are:

  • Dependencies — internal code and database dependencies
  • Isolation — each function impacts other functions (performance, security, etc.)
  • Reusability — limited reuse of object
  • Code complexity — a huge amount of code with internal references
  • Performance — impossible to tune and address performance only in the functions it’s needed, and the cost is enormous
  • Maintainability
  • Scalability — no option to scale only a specific function, it’s all or nothing
  • Resiliency — no option to implement resiliency only where needed and in a cost-effective way
  • Test cycle time — each change, even minor, requires a full system test
  • Using multiple technologies (the right technology for each business need)
  • Parallel engineering
  • Agile SDLC
  • CI/CD

Microservices

Cloud Native which is comprised of microservices, containers, CI/CD, and DevOps was a gamechanger; it changes the way we build and deploy applications. Microservices as a basis were created to solve these monolith challenges.
Microservices, in simple words, are an architectural pattern that breaks down an application into smaller, independent components that are not dependent on a specific technology stack (coding language, database, etc.). These small components are known as “services” and are typically deployed to a container.

The best practice for a microservice “size” is a feature in a business domain or business entity such as payment, check inventory, customer CRUD, product catalog, product pricing, shipping address, shipping management, etc.

Microservices are not all good, and they have challenges of their own, such as:

  • Cost of work — many pipelines, security rules, etc.
  • Cost of infrastructure — many containers/pods
  • Solution complexity — many components
  • Data sharing — app level and business domain level tables/entities
  • Code sharing (unless MonoRepo is used)
  • Data ownership — specific table/entity owned by multiple services
  • Caching
  • Business domain reports and dashboards
  • Cross microservice features
  • GUI (if micro frontend architecture is implemented)
  • End-to-end testing
  • Logging and problem root cause analysis

Modular Monolith

Modular monolith is not new. The theoretical best practice, which in most cases hasn’t been fully implemented, was always to break the system into modules. Splitting the system to modules the right way is a modular monolith. A common alternate name for modular monolith is “macroservice.” Macroservices break the system into capabilities (a capability is comprised of multiple business domains).

High-level technical characteristics of modular monolith/macroservices:

  • In the modular monolith, like microservices, each module communicates with another module via APIs, preferably loosely coupled asynchronous communication.
  • In a modular monolith just like the monolith, the system has one database schema, as opposed to microservices where each microservices should have its own schema.
  • Typically, all modules in a modular monolith run on the same VM. or each module runs on a specific dedicated VM. Modules are too big to fit into a container.

Working with modules has many advantages over the de-facto monolith implementation:

  • Easier and simpler management
  • More isolation
  • Fewer dependencies
  • Less CR risks
  • Increased reusability
  • Better maintainability
  • Simpler testing
  • Better security

Now that we understand why it’s better to switch from a monolith to a modular monolith, we will compare the modular monolith to microservices. The advantages of modular over microservices are:

  • Simpler operations and support
  • Less APIs result in better performance
  • Lower infrastructure cost
  • Native data sharing, reporting, and dashboarding

The advantages of microservices over a monolith are precisely the same as those over a modular monolith, so the immediate conclusion is that modular monolith cannot replace microservices when building a system from scratch.

Holding the stick from both ends, monolith on one side and microservices on the other, are miniservices.

Miniservices

Miniservices are separate, loosely-coupled components, just like microservices, but in the business domain rather than the business domain feature. Using the below example, miniservices will be “products” including all product features such as catalog, inventory, pricing, specs, marketing info, legal, etc.
In many cases, miniservices are the right balance between monolith and macroservices (or modular monolith to use its “trendy” name) to microservices. They allow you to enjoy maximum gain with minimum pain.

Having said that, there are cases in which microservices are a better choice, for example, “payments” which we want to share across apps and business domains.

Monolith-Modular Monolith-Miniservices-Microservices Breakdown Examples

e-Commerce App

e-Commerce monolith-modular monolith-mini-micro example

General Insurance App

General insurance monolith-modular monolith-mini-micro example

The general insurance example deep dive

In the old days, general insurance was a giant system, a monolith, just like pensions, long-term saving, life, health, shipping, etc.
There are numerous options to break the monolith into modular monoliths — vertically or horizontally. Vertically will be based on the general insurance types, such as cars, homes, travel, etc. Horizontally will be based on the functions: customers, policies, claims, etc.
Breaking the monolith into miniservices will be a combination of the vertical and horizontal and will result car policies (car policy has almost nothing in common with home, travel and business policies), car claims , travel policies, travel claims, etc.
Breaking the monolith into microservices is a feature or business entity within each miniservice and will result: car customers, car policies, car policy coverages, car policy billing, car policy payments, car policy documents, car suppliers, car appraisers, car claims, car claims legal, car claims insurance payments, car claims indemnifications, etc.
We can use a combination of miniservices and microservices for the breakdown: Payments are the same, no matter if it is car insurance, home insurance, etc. so we have a payments microservice. Managing documents and archive is the same so we have a document microservice. Customers are mostly the same, so we have a customers microservice (debatable. Some will prefer to have car customer microservice because there are some unique attributes and then manage the customer-360 in an external system or a dedicated microservice. My preference is to have a customer microservice for most of the attributes are the same, and we want to look at a customer with all his info centrally. In this case, we can manage customer unique info in the car policy microservice, travel policy microservice, etc.). For each insurance (car, travel, etc.) I’ll have a dedicated policy miniservice (e.g. car policies, travel policies, etc.) that will include the policy, the coverages, the underwriting, the exclusions, etc.

Summary and Recommendations

In this article I described what are modular monolith (macroservices), miniservices, and microservices, and what are the advantages and disadvantages of each one of them.

Comparison of monolith, modular monolith, miniservices, microservices and min-micro combination

Comparison of the monolith, modular monolith, miniservices, microservices and mini-micro combination

My recommendation for the preferred architecture depends on the type of the project- whether it is a modernization project or a project built-from-scratch.

In modernization projects, we take an existing system, probably a monolith, and rebuild it. The need for rebuilding may be due to many reasons: cloud migration, technology debt, security risks, cost of ownership, ability to deliver business requirements, and more.
In modernization projects, one of the first decisions that must be made is whether we are going to migrate the system or build the system from scratch. In some cases, even though the cost of building the system from scratch is much higher — it is still worth it, either because of the level of technology debt or because of the volume of new and future business requirements.
If we choose the modernization path, I prefer to use the modular monolith architecture pattern as it lowers our risks and costs, enables incremental migration, and improves the current monolith situation.

When building a new system from scratch, I prefer to use a combination of microservices and miniservices.
The disadvantages of the modular monolith are so high that, in my opinion, this is not a viable option.

--

--