×
API security best practice for devs: How to secure your APIs

API security best practice for devs: How to secure your APIs

API security best practice for devs: How to secure your APIs

Your APIs are prime targets for bad actors. Here's how to use authorization, observability, and threat hunting to reinforce your API defenses.

The internet is powered by APIs. From the Giphy API receiving 7 billion calls per month to Google maps getting 200 billion API calls a day, modern web applications couldn’t function without APIs. But, like any key technology, they are also a prime target for bad actors. API breaches can bring down services, expose sensitive data, and erode user trust.

To prevent that happening to your API, I’ll share in this article how you can secure your APIs using three techniques: authorization, observability, and threat hunting. Let’s dive straight in!

Looking for a list of tools to use to manage and secure your application’s dependencies? Check out my article, “Top 3 tools to safeguard app dependencies against vulnerabilities.”

Authorization

For those not familiar with the concept, authorization is all about determining who can access what resources in a system. It's the gatekeeper that ensures only authorized users can perform specific actions on data or applications, which in turn maintains data security and integrity. It’s a core concept of Identity and Access Management (IAM).

Authorization works hand-in-hand with authentication, which is about verifying a user’s identity. Think of a security guard at a gate. They might check your photo to see that you are actually the person you’re claiming to be (“Are you authentic?”), then make sure you’re actually allowed access to that area (“Yes, you are who you claim to be, but are you authorized?”). 

In practice, authorization is about specifying access rights or privileges for users or systems to access resources. Let’s look at how authorization is handled in different software use cases.

Authorization in monolithic applications

What is a monolithic application?

A monolithic application is your traditional unified software application. Think of it as an application that is one big chunk: self contained and independent from other applications, like a singular, inflexible monolith (“mono” means one, and “lith” means rock”, so think of Uluru).

How to handle authorization in monolithic applications

In monolithic applications, authorization logic often resides within a single unit — a small chunk of independently executable code. Let’s see a demo of this by looking at some Python code:

class User:  def __init__(self, username, role):    self.username = username    self.role = role  def has_permission(self, permission):    permissions = {      "admin": ["read", "write", "delete"],      "editor": ["read", "write"],      "reader": ["read"],    }    return permission in permissions.get(self.role, [])

Let’s break this down. Here, we have a class that models our user in code. This user has two main characteristics: its username, and a role. 

We’ve also got a has_permission function. In it, we define the different permissions as follows:

An admin can read, write and delete a resource

An editor can just read and write to a resource

A reader can just read a resource.

When we create a new user, we need to specify its username, as well as the role, as per the constructor of the user class:

user1 = User("john", "admin") if user1.has_permission("write"): print("User1 authorized to write")

The code above, if run, will print out that User1 is authorized to write, as user1 was assigned the admin role. This is called Role-Based Access Control, or RBAC. Each role has a predefined set of permissions for specific resources or actions. Access is granted or denied based on the user's assigned role. 

Some other common Authorization Methods are: 

Attribute-Based Access Control (ABAC): Authorization decisions are based on a combination of attributes, including user attributes (role, department), resource attributes (sensitivity, type), environmental attributes (time of day, location), and more. Policies define the combinations of attributes required for access. 

OAuth 2.0A widely used framework for delegated authorization. A user grants an application limited access to resources on their behalf without needing to share their credentials. OAuth uses access tokens to represent granted permissions.

Please set an alt value for this image...

Authorization in microservices
 

All right, we’ve seen how things are done in monolith services. However, nowadays developers will avoid creating monoliths for complex web applications. That’s because, like a real-life monolith, it’s not really great for flexibility or scalability. Instead, developers are now using microservices. 

What is a microservice?

Microservices are small, independent services that each handle a specific task and collaborate with others to build a complete web application. The main advantage of this architecture is that you can easily scale horizontally. Do you need to handle a new task? You just create a new service for it, without having to add more physical resources to power your server. 

Having such a decentralized setup comes with other challenges. Maintaining consistent authorization policies across the entire application is crucial for security and user experience. You don't want a user to be allowed to do something in one microservice but not in another due to inconsistent rules.

How to handle authorization in microservices

Here are some strategies to handle authorization in a microservice architecture, but each approach has its pros and cons, listed below.

1. Using an API gateway

An API gateway intercepts all requests, attaching authentication and authorization information. The requests will go to a dedicated authorization service that can make decisions based on user roles, attributes, and policies. 

Pros: Simplifies implementation within individual microservices, promotes consistency.

Cons: Potential performance bottleneck at the gateway, adds complexity.

2. Creating a reusable library or module

You can make a reusable library or module containing authorization logic. Each microservice incorporates this shared logic and can make authorization decisions. 

Pros: Reduced overhead compared to a centralized gateway. 

Cons: Requires careful coordination and updates to ensure consistency.

3. Have authorization logic for each microservice

Each microservice implements its own authorization logic, often tailored to its specific domain. Microservices might communicate with one another to obtain authorization information when needed. 

Pros: High flexibility for complex, granular permissions. 

Cons: Most complex to manage, potential for authorization discrepancies.

We’ve seen strategies on how to handle authorization for our APIs. Let’s see what else we can do to bulletproof it even further!

Observability

Did you know that the International Space Station (ISS) exposes an API allowing people to see the exact location and information about the crew? ISS understood that to maintain the safety and integrity of their scientists, constant monitoring of this data would be essential. 

Just like with the ISS, observability offers that same level of vigilance for safeguarding the APIs your business relies on. When building an API, you always need to have observability in mind. You need to deeply comprehend the internal states and behavior of your APIs. 

How to achieve observability

Observability is achieved by gathering and interpreting a trifecta of data, known colloquially as the “pillars of observability”: metrics, logs, and traces

Metrics: Numerical indicators that reveal API performance trends, such as response times, error rates, and traffic volume. 

Logs: Detailed records of API events, requests, responses, and any errors or anomalies encountered. 

Traces: The breadcrumbs that follow a request's complete journey across systems, illuminating dependencies and pinpointing bottlenecks.

Observability tools shine a light into the depths of your API interactions. Deviations from normal patterns, unexpected error surges, or suspicious activity can be red flags signaling potential security vulnerabilities or even attacks in progress. 

Three popular tools to use for monitoring your APIs

1. OpenTelemetry

OpenTelemetry is a vendor-neutral, open-source standard for collecting and sending telemetry data (metrics, logs, and traces). It provides a powerful foundation for observability thanks to wide support and flexibility. 

2. Prometheus

Prometheus is a widely used open source monitoring system and time-series database, renowned for scalability and its powerful query language (PromQL). It’s often combined with Grafana for visualization. 

3. ELK Stack (Elasticsearch, Logstash, Kibana)

The Elastic Stack allows for versatile log management and analysis. Logstash collects and transforms data, Elasticsearch stores it, and Kibana provides visualization and search.

Going beyond monitoring to true observability

As an API developer, it is not enough to just monitor; you need to build out an observability system that aligns with your security goals. Gather logs and metrics that directly inform about API authentication, authorization, anomalous user behavior, unusual traffic patterns, and changes to API configuration. 

Proactively define what constitutes abnormal API behavior and configure alerts to trigger when these thresholds are met. Last but not least, connect your observability platform to your Security Information and Event Management software and incident management systems, enabling a centralized security response. 

Consider achieving observability for reliability, too

Outside of security, improving observability has a direct correlation with boosting the reliability of your systems. To read more on this, check out this article by Karun Subramanian: “SRE: How making systems observable improves their reliability.”

Threat Hunting

What is threat hunting?

Threat hunting goes beyond passively waiting for alerts from firewalls or intrusion detection systems. It's an investigative, detective-like approach. Security teams actively search for signs of compromise or malicious activity within API traffic.

As a security operative, you need to understand the API landscape of your organization, mapping out all your APIs, both public and internal, including those forgotten or undocumented (shadow APIs). Armed with knowledge of current attack trends and tactics, threat hunters develop and test theories of how an attacker might target your APIs.

Using observability tools, a threat hunter digs into the wealth of API logs, metrics, and traces, looking for patterns that betray malicious intent. 

How does a threat hunter do that? An e-commerce example

An e-commerce website experiences a spike in API calls directed at the user login endpoint. 

Observability tools reveal a much higher frequency of login requests than normal, especially from a specific range of IP addresses. 

Upon examining the detailed API logs, the threat hunter uncovers a high volume of failed login attempts with incorrect usernames and simple passwords, followed by a small number of successful ones. Traces link the successful logins to suspicious activity like multiple high-value purchases made within a short time frame or unusual changes to shipping addresses.

This threat analysis paints a potential picture of a credential stuffing attack. Attackers likely used a leaked list of usernames and passwords to brute force their way into some user accounts, attempting to exploit them for fraud.

What do threat hunters look for?

There’s no easy recipe for performing threat hunting. One needs to take into account the specifics of every API under surveillance. However, there are some common tips that you can implement in your threat hunting workflow:

Sudden changes in API traffic volume or unexpected patterns could indicate bot activity or brute force attacks. 

Repeated attempts to access sensitive data or suspicious error messages may hint at probes for vulnerabilities. 

Excessive failed login attempts or attempts to access unauthorized resources are major red flags. 

Any unexpected modification to API configurations or behavior warrants investigation.

What tools can I use for threat hunting?

Threat hunters also have a big array of tools that they use on a daily basis. Here are a few of them:

1. OWASP ZAP

OWASP ZAP is a free and open-source web application security scanner that includes API testing capabilities

2. Wireshark

Wireshark is a powerful network protocol analyzer, excellent for deep packet inspection. 

3. Zeek

Zeek is a network security monitoring framework, ideal for custom detection rules. 

4. Splunk

Splunk is used to correlate API events with broader security data sources.

5. Cloud-based tools

There’s a variety of cloud-based tools that help threat hunters effectively defend the APIs hosted in the cloud. Azure Sentinel, for example, is a cloud-based SIEM built specifically for the Microsoft Azure ecosystem. It comes with pre-built hunting queries that security analysts can use to proactively search for suspicious API activity. 

Similar tools can be found in other cloud vendors, such as Security Command Center from Google, or Amazon GuardDuty from AWS.

Want to learn more about being a threat hunter? Check out Pluralsight’s learning path on Threat Hunting, starting with the essential skills to how to perform specialized hunts.

Conclusion

We’ve seen three key elements that can improve the security stance of your APIs. By understanding the principles of authorization, observability, and threat hunting, you empower yourself to outsmart attackers. 

Remember that cybersecurity is an ongoing battle; technology evolves, and attackers adapt. Stay vigilant, keep learning, and reinforce your API defenses at every turn!

If you liked this article, make sure to check out my Pluralsight courses, which deal with other cybersecurity-related topics and techniques worth learning about.

Read More