In Part 1-Deployment Patterns I have tried to elaborate on the architectural patterns in terms of application deployment ways. In this article, I am trying to target what are the possible ways to manage your data & the pros/cons of each approach.
Now that we have identified & figured out the possible deployable units defined in a bounded context, the question arises how about your transactional & reporting data management.
Our services can be polygot same applies in terms of DB selection, have the best possible fit as per your application need.
First thing first, an organization need to come out of that long bureaucratic process of DB or Schema procurement from DBAs, since a lot of organizations are in the mode of shared services model where infrastructure is managed external to application team, so DevOps is an important aspect for Microservices architecture.
Second things the more privacy we maintain about data as per service it helps in data contention & follows the basic principle of bounded context as per service. All the data need to exposed via the service APIs. It helps in service binding with frontend services also.
Basically, there are multiple ways you can design the backend for your microservices.
1. Private Tables per service:–
As shown in Figure 1, there are three microservices & Microservices 1 & Microservices 2 are residing in the same database. You can see that these tables are as per each microservice & they don’t have any referential integrity in between them.
Pros: Easier maintenance & you can still continue to follow your shared service model for support.
- DB maintenance or DB scalability is not a possible individual to microservice. One application can still access the tables of other microservices.
- Possibility of data contention.
- DB should be made sure to accept multiple connections.
This approach only works if you think for multiple services can have similar DB type & have similar configuration needs at the DB level.
2. Schema per Service:-
As shown in figure 2, this pattern will work when you decide to reuse a similar database type but the visibility is further separated from each other by Schema and there is no data contention & you have one level higher restriction to Private tables per service.
Pros: Easier maintenance & you can still continue to follow your shared service model.
Cons: DB maintenance or DB scalability is not a possible individual to microservice. Schema replication is much easier as compared to a private table.
*Notes:- Schema concept doesn’t exist in all the databases, so this might not be applicable in all the database types.
3. Database per service :-
As shown in Figure 3, you prefer to have DB per service & it also means different DB types per service. Here you have one or more level of abstraction & here you have the liberty to chose multiple database types irrespective of other microservices,
Pros: You have complete independence to upgrade make DB changes without impacting any other application.
Cons: Maintenance overhead as this needs to be managed & supported individually in terms of patching & db patch upgrades.
As per 12 factor app recommendations, your services should be bindable, which also proposes to have separate DB service instance for each application. As I mentioned in my earlier post if you decide to move for a microservices architecture, it does make sense to invest in infrastructure but is it worth to do that much investment. Once you have invested too much into it then it generally becomes uphill battle either to defend the architecture for a long time or knowingly stick with it, till you extract the value of it & no one knows future, today microservice tomorrow could be something else. Cloud Foundry, PCF has invested heavily in these patterns & they provide a simple solution to tackle such problems very easily.
Conclusion:- I have seen multiple organizations following multiple practices but I personally implemented all three of the way of implementation private tables as well as schema per service. The only word of precaution when you go for a private table is since you can see other tables during future developments, if developers are not made aware of bounded context properly you might end up in building pseudo microservice with same DB & someone could unknowingly cross the boundaries of particular microservice. This needs to be thought through thoroughly before making a decision on which DB scheme works for you.
*I will explain reporting needs in another blog once we discuss other architectural patterns like API Gateway, Eventual consistency, CQRS. There is some dependency on these patterns before we start talking about reporting needs.