Modular Monolith

A modular monolith keeps one deployable application while enforcing strong internal module boundaries.

Core Idea

A modular monolith is a single deployable unit that is internally decomposed into well-defined modules. Each module owns its data, exposes a public API to other modules, and hides its implementation details. Unlike a traditional monolith where everything is tangled together, a modular monolith maintains clear boundaries while avoiding the operational complexity of distributed systems.

Use Cases

Module Boundaries

Each module should:

Data Ownership

In a well-designed modular monolith, each module owns its database tables. Other modules cannot query another module's tables directly — they must go through the module's public API. This ensures that internal schema changes do not ripple across the system.

In practice, this is often enforced through separate database schemas, namespace conventions, or architectural fitness functions that detect cross-module data access.

Benefits

Trade-offs

How It Differs from a Distributed Monolith

A distributed monolith is a system that has the deployment complexity of microservices but the coupling of a monolith. Services cannot be deployed independently because they depend on each other's internals, share databases, or require coordinated releases.

A modular monolith avoids this trap by being honest about its deployment model: it is one application, and it embraces that simplicity. The focus is on internal modularity, not on distribution.

Comparison with Microservices

Aspect Modular Monolith Microservices
Deployment Single unit Independent per service
Communication In-process method calls Network (HTTP, messaging)
Data isolation Separate schemas, same database Separate databases per service
Consistency Strong (transactions available) Eventual (sagas, compensation)
Operational complexity Low High
Team independence Moderate High
Scaling Whole application Per service

Related Styles