From Monolith to Microservices






#nodejsarm
Varik Matevosyan
Steadfast.tech/CTO

varik@steadfast.tech

github.com/var77
linkedin.com/in/varik-matevosyan-99200a108/

Overview
- What is a monolithic application
- Moving to microservices
- Monolith vs microservices
- My experience with microservices
What is a monolithic application
When talking about monolithic application consider it as a big monster application in which all the services are included, and there is single shared source of data

Problems with monolithic applications
- Inefficient scalability
- Service crash === application crash
- Project maintenance
When talking about monolithic applications some people think that they are not scalable, but that's not true you can easily scale the monolith application horizontally, but when talking about the efficiency it can take a lot more resources than scaling the application with microservice architecture.
Inefficient scalibility
Consider the following scenario, you have a monolithic chat application, and you notice that the socket part is in a high load, so you should scale your application, but you can not scale just the socket part you should scale the whole monolith.
Inefficient scalibility
Socket
API
UI
DB
Socket
API
UI
DB
Now consider the following you have made change in your application's UI renderer and now should update it, so you should restart the whole application, which means you'll have downtime in your socket connections. Or if there would be some bug in you API the UI and Socket will be also crashed because of that.
Server downtime
Socket
API
UI
DB
Despite the quick start up of monolithic applications it's pretty hard to maintain the project as it gets bigger, and it's twice harder for new developers, it's like a big spaghetti code which can be broken easily if you do something wrong by mistake.
Project flexibility and maintenance

Moving to Microservices
"Do you have time to do it twice?"
"We don't have time to do it right!"
Moving to Microservices
Let's split our monolithic application into Microservices, for that firstly we should combine functions that have similar functionality and then wrap them into a single microservice, we should also consider about splitting our database, but we'll talk about it a bit later
But before we start, let's talk about some Nodejs frameworks and libraries designed for microservices and what should they provide us.
- Seneca, a microservices toolkit for Node.js
- Zeronode — minimal building block for NodeJS microservices
- Kitoo-Core — NodeJS microservice library built on top of Zeronode
What we should expect from the good microservice library
- Transport for service to service communication (HTTP, TCP)
- Service registry to dynamically register a new service
- Service discovery to discover new registered services automatically
- Load balancing between services
Now we can start splitting our monolith, for the first we can split Socket, API and UI parts to separate services, so our application will look something like this.
Socket
API
UI
DB
API
Socket
UI
DB
For efficient microservice architecture our microservices should satisfy to some requirements
- Each service should have it's own data store and state
- Services should be independent, isolated and loosely coupled
- Access to service's state should be only external via the API provided by the service
Now it's better than monolith, but it's far from the good microservice architecture
- Services should be small and responsive for exactly one thing or be meaningful
Let's look what is wrong in our example, and what can we do to make it better.
API
Socket
UI
DB
Here we have Socket service which can be also split into parts for example, pure chat service which will send messages between users, flood/spam checker service, link/markdown parser service, etc...
Messaging
Spam
Parser
API
UI
DB
Now we can consider to be done with the socket service, but there's also one thing left here the data, so we can take our messages collection out from our database and move it to a separate one
Messaging
Spam
Parser
DB
messages
DB
API
UI
We are now done with our socket service, and now we have 3 separate microservices which can be used not only in this project, but internally. Now let's move on and refactor our API service
Messaging
Spam
Parser
DB
messages
DB
Auth ( + social auth)
Payment
(sticker packs etc..)
User management
DB
users
DB
orders
Proxy
We've finished splitting our API service and we got 3 separate microservices and we get rid of the single database, so now each service has it's own data store. We also added a proxy layer to proxy front-end calls to our microservices, to use a single endpoint in the client side. Now let's compare our monolith and microservice architectures
Socket
API
UI
DB
Monolithic Architecture
UI
Microservice Architecture
Messaging
Spam
Parser
DB
messages
Auth ( + social auth)
Payment
(sticker packs etc..)
User management
DB
users
DB
orders
Proxy
UI
For the first it can be more messy and complicated, but it solves a lot of problems and speed up development for big projects and big teams, now let's look how we could solve the same scaling problem in this architecture
Messaging
Spam
Parser
DB
messages
Auth ( + social auth)
Payment
(sticker packs etc..)
User management
DB
users
DB
orders
Proxy
Messaging
As we can see, we just run one more messaging microservice and do not scale the whole application, and as I told you before service registry, discovery and balancing should be handled from our microservice framework or library. With the same approach now if we would like to change something in our parser service, then we can only restart that microservice and our changes will be live without affecting other services.
Monolith VS Microservices
Now let's compare this two architectures and see both advantages and disadvantages.
It's not necessary to use the microservices for each project, it depends on the needs and sizes of team/project, there can be cases where using monolithic architecture would be better than microservices.
So what are the advantages of using microservices
- Independent and reusable services
for example if we build another application which will have a chat, we can easily integrate our messaging, parser, spam/flood checker, microservices there.
- Easy unit and integration testing
- Independent scalability
we can scale our application partially saving resources.
- Parallel and fast development
It's incredibly fast to develop with microservices with a team, as they the microservices are independent they can be developed parallel and the language do not matter, they just should give an API interface and work with I/O scheme
- New developers can get into the project more easily
It's the same as trying to understand a big function with lots of conditions and a function which is separated into smaller functions.
Disadvantages of microservices
- Slow startup
compared to monolith application the project set up can be more slow, because in monolith it's just all in one place so you can not think about service to service communication, splitting databases, what microservices you should have, etc..
- Devops and building into production
it could be more difficult to do the devops part of microservice application, service management, debugging and log management can be more difficult than in monolith application.
- End to end testing
writing ent-to-end tests for application can be pretty hard, because you should connect all the microservices together to be able to make the test
- Database joins
it's hard to do database joins with microservices, but there are some techniques to do it.
My experience with microservices
In our company (Steadfast) we are using microservices a lot, and we use our libraries and frameworks to manage them (zeronode, kitoo-core, wirentity)
My experience with microservices
We are mainly doing game projects, and we use microservices to separate logic parts for games, and to split API into several parts.
My experience with microservices
So in our last project which was a board game, we were using microservice architecture, with kitoo-core to connect services each other. It's pretty easy and handful to do microservices with kitoo-core because you just define your request handlers, and give a name to your service, after that you just need to run one or multiple instances of kitoo-core routers and connect your service to them, then service registry, discovery and load balancing is done automatically for you.
My experience with microservices
So by using it we managed to give an MVP in about 2 weeks via doing parallel development. We make about 12 microservices and cover each microservice with about ~90% unit tests. There the microservices were mostly stateless so our data model did not matter for request/response pattern to match with database model.
My experience with microservices
For API we had 4 microservices which were shipped with their clients. It's always a good habit to make a client for you microservice so there will be all available interface of your microservice. And for process management we are using pm2 which is a great tool for managing NodeJS applications.
Thank you!
Don't hesitate move to microservices!

From Monolith To Microservices
By Varik Matevosyan
From Monolith To Microservices
- 154