How to Secure Microservices: The 6 Things You Can't Forget
Microservices bring many benefits: flexibility, ease of upgrading parts of the application, and much more. However, they are not a golden solution to all problems, and they also come with their own disadvantages. One of them is a complex mesh of network connectivity. And when you have complex networking, another issue arises: security.
The more complicated the network, the more difficult security is, too. And the more microservices you have, the more complicated the network. But the network is only one aspect. When it comes to securing microservices, there are a few more things you need to keep an eye on. But fear no more, because in this post, you'll learn six things that will help you secure your microservices.
How to Secure Microservices—What Do You Need to Know?
Before we dive into the six things you can't forget when securing your microservices, we need to start with some general information about securing microservices. It's important because you can't focus 100 percent on microservices themselves. When it comes to securing microservices, you need to think of your entire microservices ecosystem. This means you need to secure CI/CD pipelines, your container orchestrator, and the way you build your microservices.
1. Start With the Secure Base Image
It shouldn't be a surprise that when you're building microservices, the base image of your Docker containers plays a crucial role. Actually, a well-chosen base image is good not only from a security perspective, but it's also a good practice in general. So, what does a "good" base image mean? First of all, forget about base images from random people. Choose only verified images from well-known companies. For example, if you need an Ubuntu image, take one directly from official Docker images. It's tempting to use third-party images that have a few additional tools built in, but it's way better to add those tools yourself than risk using images from untrusted sources.
But using official images doesn't automatically bring you added security. They drastically increase your security posture, but they are not bulletproof. You need to ask yourself if you really need an actual distro-based image (like Ubuntu or CentOS images). Try using more minimalistic images like Alpine or Distroless.
2. Scan Your Images
Even if you pick a relatively secure base image, it doesn't mean your Docker image is safe. You will add quite a few layers to that image yourself. Of course, you won't intentionally introduce vulnerabilities into your own images, but don't forget about dependencies. You may not even realize that almost anything you install brings some (sometimes hidden) dependencies. That's why it's important to perform vulnerability scanning of your images, especially since it's a pretty easy thing to do and some image registries even have that function built in.
3. Container Runtime Analysis
If you want to go even further, one of the best security improvements you can make to your microservices is to implement runtime scanning. Runtime analysis is a process of monitoring every single action that's happening in your container. Especially in a microservices environment, it's really efficient because you always know exactly what should be running in a specific container. Therefore, anything out of the ordinary usually means trouble. Did someone execute a shell script in your container? A curl or wget commands? Pretty much anything that hackers would usually do is very different from how a normal microservice would behave. Therefore, runtime analysis scanners are really efficient at what they do and are a great security improvement.
4. Take Good Care of Your Secrets
In a Kubernetes environment, we tend to think we're covered when it comes to passwords and tokens because Kubernetes provides built-in "secret" resources. Their purpose is exactly that: securely storing secrets in your Kubernetes so you don't need to pass them in plain text to your container. But there is a catch. First of all, you somehow need to bring your secrets to your Kubernetes cluster first. They are secured once they are in, but how do you make sure that they are not in plain text when deploying them to Kubernetes?
This is a common issue. Since everything in Kubernetes is defined as a YAML file, we tend to store all those YAML definitions in Git. But your actual passwords, tokens, and other secrets when they are in YAML file (before being applied on the cluster) are in plain text. So, you can't store these files in Git. And no, don't do it, even if your Git repository is private. There is no universal solution for this as it will depend on your infrastructure and which cloud provider you are using. But whenever possible, try using a secure secret store like HashiCorp Vault. Many secure stores have plugins or other mechanisms to securely transfer your secrets to the Kubernetes cluster.
5. The Network
Last but not least: the network. If you are using Kubernetes, by default all your microservices can talk to each other. This means an attacker only needs to get access to one of them in order to be able to connect to anything in your cluster. And while your core back-end microservices may be well secured (in terms of the code itself), there are always some forgotten, not important side services that don't play any major role in the whole system and therefore no one cares about them. Well, guess what—hackers love these kinds of services.
The solution is simple: implement some network policies or even encryption within your cluster. There are Kubernetes built-in network policy objects that let you implement simple network segregation and rules. But there are also plenty of other tools, some of which can even implement Layer-7 network policies.
Another possibility is encryption. There are tools that allow you to encrypt all the traffic between all the pods within your cluster. Encrypting all the traffic doesn't automatically make it secure but definitely makes hackers' lives more difficult.
6. Monitor All the Layers
Another important security-related task is to make sure you have a cloud native security monitoring system. What does that mean? It means that your monitoring system is able to monitor and correlate data from all the layers of your infrastructure (microservices, container orchestrator, and cloud services).
This is important because traditional on-premises systems can easily get confused in the multilayer cloud environment. It's crucial that your tools understand cloud services and the dependencies between them. For example, when you create a DNS server in the cloud, you may not find an actual DNS server. You'll find a service that works like one, but you won't find an actual machine that is your DNS server. And this may be a problem for traditional tools because they usually operate on servers. And hackers like to take advantage of that and navigate between the layers undetected.
Summary
I wish we could give you a simple-to-follow, step-by-step guide for securing microservices, but the truth is that microservices-based environments are usually complex. Securing such environments also differs quite a lot from one cloud provider to another, but we tried to combine the most universal tips that will hopefully help you stay relatively safe. If you really care about security, make sure to check our other articles and take a look at our Free API Security Solution.
This post was written by Dawid Ziolkowski. Dawid has 10 years of experience as a Network/System Engineer at the beginning, DevOps in between, Cloud Native Engineer recently. He’s worked for an IT outsourcing company, a research institute, telco, a hosting company, and a consultancy company, so he’s gathered a lot of knowledge from different perspectives. Nowadays he’s helping companies move to cloud and/or redesign their infrastructure for a more Cloud-Native approach.
The Inside Trace
Subscribe for expert insights on application security.