Microservices tutorial: how to build scalable applications

Microservices tutorial

Share This Post

As we use software to solve more and more complex problems, applications get smaller. Despite what it may sound like, the bigger the problem, the smaller the app. Even more, the more users you want to serve, the smaller the app. How is this possible? Well, my friend, it is time we meet microservices. In this microservices tutorial, we will see how to design an application with them, and why they are important.

Of course, this tutorial focuses on the design of the software, and we won’t get into the technical details. Imagine it like the blueprint of a building, where you get the picture of the entire building. However, you don’t get a detailed diagram of the electrical circuits and plumbing. We will see the same level of detail here.

Microservices tutorial

What is a microservice?

A microservice is exactly what the name suggests, a very small service. To be more specific, it is a small standalone application, typically a container.

A microservice is a very small service.

We have two important concepts to focus on “small” and “standalone”.

We all know what small means, but it is not so obvious when it comes to applications. However, microservices are small in any possible sense. They do a small simple task (or a few simple tasks). They also consume little resources in terms of RAM and CPU. Furthermore, this simplicity translates into a smaller amount of code to create that service. As a result, it takes a few developers to create and maintain the service. Amazon has the “two pizzas’ rule”, that says the entire team working on a microservice should be easily fed with two pizzas, at most. If you are not into (American) pizzas, that’s about 8 people.

The entire team working on a microservice should be easily fed with two pizzas, at most.

Well-known motto inside AWS.

Standalone is also easy to understand. It means that the single service can work on its own, and does not need other services to live. Of course, when alone, the service can do just some simple tasks. But that’s their own tasks, and it can do them without relying on other services.

Microservices tutorial: the microservice architecture is comprised of several standalone services
In a microservice architecture, the application is segmented in blocks (microservices) that talk with each other.

This does not mean the microservice must process an entire transaction on its own, not necessarily. Instead, it means that it can work on its part of the transaction autonomously, and with clear boundaries. This translates into the service implementing an API. With an API, you call the service and ask it to do something. And it does exactly that. The API defines exactly what the service does, it is the scope boundary.

Containers and microservices

Of course, this is a microservices tutorial and not a tutorial on containers. Yet, containers are a key technology enabling microservices. This is because they are the best way to do a small standalone application.

With a container, you define the entire stack: OS, runtime, configuration, and code. You effectively have a pre-configured server ready to run exactly your service. But this server is virtual, and it consumes just a tiny amount of resources (as low as 50MB of RAM). That’s the magic containers bring to the table.

Furthermore, as we will see, we need many different containers to create complex applications. And containers come with orchestration platforms that allow you to manage your containers easily. That’s just what we need.

If you want to learn more about containers, you can start from this easy tutorial about Docker, the leading container platform.

Building a scalable application

Building a scalable application means you use microservices. It means you split your larger applications into many different microservices. And that’s the whole challenge. How do you decide what each microservice should do? When it makes sense to split, and when it makes sense to aggregate in a single microservice? Those are good design questions to ask.

To answer those questions, we need to understand what are the benefits and drawbacks of having few or many microservices.

Microservices benefits vs drawbacks

The more microservices you have, the more your application can scale. Even more, having many microservices means that you can make changes only on a small part of the application (one microservice) without affecting the other parts (other microservices). This translates into better risk management, as you don’t risk to blow everything up. And, as a result of that, you can have faster deployment cycles and thus easier management and maintenance.

Awesome. But everything comes at a cost.

The more microservices you have, the more you add overhead to your app. Imagine you have a piece of code that calls a function. That is simple, and incredibly fast: calling a function is virtually the same as executing all the code in the same place. Instead, if part of the task is on another microservice, you need to call its API. This means going out of the CPU and to the network card. It means spending time crafting HTTP requests and responses. All of that slows your application.

Furthermore, having separate containers add a little bit of extra resource usage. Each container has to use some resources for its runtime, and while this extra burden is negligible with few containers, it must be managed if you have many. You don’t want to use your computing resources at 60% for the runtime and at 40% for your actual business logic.

Another item to consider is data access. If all microservices access the same data source, like the same database, you have a problem with locks.

Comparing benefits and drawbacks of using many microservices. The more you use, the easier your application can scale but the slower it is. The less you use them, the more your application will be fast but harder to scale.
You need to balance segmenting your application in many microservices. Too many and it will be to slow, too little and it will be hard to scale.

Deciding the boundary

So, in the end, it is all about deciding the boundary. You need to decide which tasks go in each microservice. As you can imagine, there is no golden rule about that. There is no absolute way of being right or wrong. However, there are some good practices that you can follow, as well as common sense.

You can find below a list of properties that each of your microservice should have.

Easy to articulate

It should be easy to articulate the scope of the microservice. In other words, you should have no problem describing what the service does, possibly in one sentence.

Some examples of good scopes below:

  • Verify the identity of the user.
  • Translate between FTP and REST calls.
  • Provide real-time stock exchange information.
  • Central API gateway that the frontend application engages when the user performs an action.
  • Provide cached static content.

And now, some examples of bad scopes. One rule to remember, the more “and” you use, the worse the scope is.

  • Verify the user identity and authorized payments transactions.
  • Provide cached static content and allow the user to upload new content.
  • Accepts calls from the frontend and from an FTP integration.

One language

Ideally, you should not use multiple programming languages inside the same microservice. Instead, using different programming languages in different microservices is more than welcome.

Each language is better for doing something. If you use more than one in a single service, maybe you are trying to do multiple things.

Of course, some small exceptions apply. For example, you might have a Python application with a core module in C++ for performance.

Reusability!

The good thing about microservices is that you can use and re-use them. For example, the authentication microservice is something you may want to use in many different applications.

Thus, whenever you have a chance to reuse that component (e.g. authentication, middleware), it is better to split than to concentrate.

Data access for microservices

One goal you should pursue is trying to ensure that one type of data is accessed by only one microservice. This does not mean other microservices should not have access to it. It means you have just one microservice that is in charge of reading and writing from disk or database.

This is of crucial importance if your data structure is a relational database. If it is, other microservices should call the other microservice to get data from the database for them.

Things get simpler when you have document databases like MongoDB. In that case, you don’t need to have one microservice having exclusive access to the database. However, you may want to coordinate well which microservices access which collections.

Data access is a complex topic, and it would take an entire book or more. For sure, more than we can cover in this microservices tutorial.

Microservices tutorial summary

Microservices are cool and are a great way to abstract and scale any kind of application. Without any surprise, they are key design paradigms of all the Internet giants, from Google to Amazon.

Implementing microservices is easy, as we saw in this microservices tutorial. To do that, split your application into different modules, and have each module in its own containers. To allow communication, make sure each container exposes some APIs that the other microservices can call.

The challenge with microservices comes in the software design phase. You have to decide how to split all your business logic in different containers. The more you split, the easier you make scalability and management, but the more you make your application slow and greedy of resources. So, follow these great principles to know when to split.

  • Split only if the scope of the to-be microservice is easy to articulate.
  • Split if you have parts of the application written in different languages.
  • Consider reusability, if you plan to reuse this part of code in other application then it is time to split.
  • Keep inside the same microservices pieces of code that work on the same data.

Hopefully, this microservices tutorial will help you design better applications and scale them as your business grows!

Picture of Alessandro Maggio

Alessandro Maggio

Project manager, critical-thinker, passionate about networking & coding. I believe that time is the most precious resource we have, and that technology can help us not to waste it. I founded ICTShore.com with the same principle: I share what I learn so that you get value from it faster than I did.
Picture of Alessandro Maggio

Alessandro Maggio

Project manager, critical-thinker, passionate about networking & coding. I believe that time is the most precious resource we have, and that technology can help us not to waste it. I founded ICTShore.com with the same principle: I share what I learn so that you get value from it faster than I did.

Alessandro Maggio

2020-04-30T16:30:08+00:00

Unspecified

Dev

Unspecified