You’ve probably heard of the OWASP top ten or the top ten vulnerabilities that threaten web applications. OWASP also periodically selects a list of top ten vulnerabilities that threaten APIs, called the OWASP API top ten. The current API top ten are Broken Object Level Authorization, Broken User Authentication, Excessive Data Exposure, Lack of Resources & Rate Limiting, Broken Function Level Authorization, Mass Assignment, Security Misconfiguration, Injection, Improper Assets Management, and Insufficient Logging & Monitoring.
Many of these vulnerabilities affect application components besides APIs, but they tend to manifest themselves in APIs. Last time, I talked with you about one of the most prevalent API vulnerabilities: Broken Object Level Authorization.
From my experience hacking APIs, I am convinced that most API implementations suffer from at least one instance of Broken Object Level Authorization. This time, let’s talk about OWASP API #2: Broken User Authentication.
Authentication is hard for APIs. Often, prompting for user credentials or using multi-factor authentication is not feasible during API calls. So authentication in API systems is often implemented using access tokens: tokens embedded into individual API calls to authenticate the user. If authentication is not implemented correctly, attackers can exploit these misconfigurations to masquerade someone else.
First of all, an API can lack authentication mechanisms altogether. Sometimes, API developers assume that APIs endpoints will only be accessed by authorized applications and will not be discovered by anyone else. So the API is made available to anyone who knows its endpoints and query structure. In this case, anyone is free to request data or execute actions via APIs if they could figure out its query structure.
But APIs that lack authentication is becoming less common. Most of the time, Broken User Authentication is caused by faulty access token design or implementation instead.
One common mistake is not generating access tokens properly. First of all, if tokens are short, simple, or predictable, attackers might be able to brute force tokens. This can happen when tokens are generated with insufficient entropy or derived from user information using weak encryption or hashing algorithms. For instance, what is wrong with the following API token?
The token is simply the base64 encoding of the user’s username, “vickieli”!
APIs that don’t use a simple access token string can be insecure too. For instance, JSON Web Tokens (JWTs) can also be improperly signed or missing signatures altogether. This issue is especially dangerous if the insecure tokens are used to authenticate admins or others with special privileges into the API. If you are interested in learning more about the potential pitfalls of JWTs, read my previous post here:
Even if tokens are generated properly, improper token invalidation could also cause trouble. Long-lived tokens are a huge security issue in many API implementations.
API tokens should expire periodically and after sensitive actions such as logout, password change, account recovery, and account deletion. If access tokens are not properly invalidated, attackers can maintain access to the system indefinitely after stealing a token.
And that brings us to the issue of token leaks. Sometimes, developers transport access tokens insecurely, such as in URLs or via unencrypted traffic.
If a token is transmitted via a URL, anyone with access to the URL via browser extensions or browsing histories can steal the token.
And if a token is transmitted via unencrypted traffic, attackers could launch a Man in the Middle (MITM) attack to intercept a victim’s traffic and steal the API token.
Broken user authentication is devastating for APIs because a single mistake can enable attackers to take over users’ accounts and access restricted data and functionality.
Preventing this issue requires a comprehensive approach. First, you need to ensure that you are implementing access control for all sensitive data and functionalities. This is addressed in my last blog post about Broken Object Level Authorization. After all, authentication is futile unless you use it to restrict access to the system!
Next, make sure that your API tokens are long, random, unpredictable strings. If you are using tokens derived from user information, use strong algorithms and secret keys to ensure that users cannot forge their own tokens. Finally, if your API uses signature-based authentication such as the JWT, implement a strong signature on the token and validate it properly.
Invalidate tokens periodically and after actions like logout, password reset, account recovery, and account deletion. Finally, treat access tokens as secrets and never transport them in a URL or unencrypted traffic.
Broken User Authentication can cause serious security incidences, so preventing them should be your top priority as a developer. Next time, let’s look at the OWASP API top ten #3, Excessive Data Exposure, the vulnerability I find most often in APIs. Up next, why you should always grep API responses to find bugs.
What other security concepts do you want to learn about? I’d love to know. Feel free to connect on Twitter @vickieli7.
Want to learn more about application security? Take our free OWASP top ten courses here: https://www.shiftleft.io/learn/.