General Guidelines
What changes together, goes together
Size and Responsibility
Premature splitting is the root of all evil
Always keep in mind: "What changes together, goes together". Do NOT split a microservice by technical concerns
You SHOULD use the Single Responsibility Principle(SRP): Having a limited and a focused business scope for a microservice helps us to meet the agility in development and delivery of services.
During the design phase of the microservices, you SHOULD find their boundaries and align them with the business capabilities (also known as bounded context in Domain-Driven-Design).
You SHOULD NOT split a “large” microservice using technical requirements.
You MUST NOT split into Microservices if you don´t know how it is going to interact with your main application.
You SHOULD NOT design CRUD Microservices. A Microservice provides business behavior (or use cases) and not just Database operations.
Size and Service Boundaries
Pattern: Decompose by subdomain
It is often a good practice to start with relatively broad service boundaries to begin with, refactoring to smaller ones (based on business requirements) as time goes on.
You MUST focus on the scope of the microservice, but understand that it’s not about making the the service smaller.
The (right) size of the service SHOULD be the required size to facilitate a given business capability.
You SHOULD make sure the microservice design ensures the agile/independent development and deployment.
Unlike services in SOA, a given microservice SHOULD have a very few operations/functionalities and simple message format.
Design for failure, and nothing will fail
Designing for failure
A given microservice can fail due to network issues, unavailability of the underlying resources etc. An unavailable or unresponsive microservice SHOULD NOT bring the whole microservices-based application down
Microservices SHOULD be fault tolerant, be able to recover when that is possible and the client has to handle it gracefully.
You SHOULD always design Microservices for failure.
Grown-ups don’t use distributed transactions
Transactions
Stop thinking in a monolith:
The microservice architecture itself encourages the transaction-less coordination between services.
The idea is that, a given service is fully self-contained and based on the single responsibility principle. The need to have distributed transaction across multiple microservices is often a symptom of a design flaw in microservice architecture and usually can be sorted out by refactoring the scopes of microservices.
You MUST NOT implement any type of distributed transactions pattern.
If there is a mandatory requirement to have distributed transactions across multiple services, then such scenarios MUST be realized with the introduction of ‘compensating operations’ at each microservice level.
It is NOT RECOMMENDED to implement a centralized orchestration service to handle distributed transactions of any kind. You SHOULD implement these with a Saga Pattern.
Always favor choreography over orchestration
Asynchronous Communication
You SHOULD NOT communicate services through its APIs and favor always choreography using events over central orchestration.
The direct communication style is considered as an microservice anti-pattern for large scale microservice implementations and MUST NOT be used.
The communication between the consumers/producers is facilitated through a message broker which is based on asynchronous messaging standards (RabbitMQ in our case).
Microservices architecture favors decentralized governance
Decentralized Governance
In microservices architecture there is no requirement to have centralized design-time governance.
Microservices teams SHOULD make their own decisions about its design and implementation. Microservices architecture foster the sharing of common/reusable services.
Some of the run-time governances aspects such as SLAs, throttling, monitoring, common security requirements and service discovery MUST be implemented at API-Gateway level.
Decentralized Data Management
People first...
A strong Microservices Governance foundation contains three elements: people, process, and technology . For a successful functioning governance, these three elements must align
Each microservice SHOULD have a private database to persist the data that requires to implement the business functionality offered from it.
A given microservice MUST only access its own private database but NOT the databases of other microservices.
In some (very rare) business scenarios, you might have to update several database for a single transaction. In such scenarios, the databases of other microservices MUST be updated through its service API only (not allowed to access the database directly).