Understanding OAuth 2.0 Authorization Methods


When diving into modern authentication mechanisms, OAuth 2.0 stands out as one of the most widely adopted standards. I learned about key OAuth 2.0 authorization flow methods, each tailored to specific use cases. In this post, I'll walk through what I've learned about these methods, their purpose, and how they compare.

1. Authorization Code Grant

Explanation

The Authorization Code Grant is the most common OAuth 2.0 flow, designed for secure client-server communication. It is primarily used in web and native applications to exchange an authorization code for an access token.

  1. User Authentication: The user authenticates with the authorization server.
  2. Authorization Code: The client app receives an authorization code via a redirect URI after the user has authenticated.
  3. Token Exchange: The client exchanges the authorization code for an access token by making a POST request to the authorization server.

This flow is secure because the access token is never exposed to the browser, and the authorization code is exchanged server-side.

Flow chart
POST /token HTTP/1.1
Host: auth.example.com
Content-Type: application/json
 
{
  "grant_type": "authorization_code",
  "code": "<authorization_code>",
  "client_id": "<client-id>",
  "client_secret": "<client-secret>",
  "redirect_uri": "https://example.com/callback"
}

2. Authorization Code Grant with PKCE

The Authorization Code Grant is very similar to the original Authorization Code Grant with one exception: To address the security vulnerabilities in public clients (like mobile apps or single-page apps), OAuth 2.0 introduced Proof Key for Code Exchange (PKCE). This adds an extra layer of security, ensuring that the client that initiates the request is the one that can exchange the authorization code for the access token.

  1. Code Verifier & Code Challenge: The client generates a random string (code verifier) and hashes it to create a code challenge.
  2. Authorization Request: The client sends the code challenge during the authorization request.
  3. Token Exchange: The client sends the code verifier along with the authorization code to exchange for an access token.
Flow chart
POST /token HTTP/1.1
Host: auth.example.com
Content-Type: application/json
 
{
  "grant_type": "authorization_code",
  "code": "<authorization_code>",
  "client_id": "<client-id>",
  "code_verifier": "<code_verifier>",
  "redirect_uri": "https://example.com/callback"
}
// Helper function to generate a code challenge from the verifier
async function generateCodeChallenge(verifier: string) {
  // Encodes the verifier
  const encoder = new TextEncoder()
  const data = encoder.encode(verifier)
 
  // Hashes the encoded verifier
  const hashBuffer = await crypto.subtle.digest("SHA-256", data)
  const hashArray = Array.from(new Uint8Array(hashBuffer))
 
  // Encodes the hash as base64
  const base64String = btoa(String.fromCharCode.apply(null, hashArray))
 
  // Converts the base64 string to a URL safe string
  return base64String.replace(/\+/g, "-").replace(/\//g, "_").replace(/=+$/, "")
}

3. Implicit Grant (deprecated)

The Implicit Grant was designed for client-side applications like Single Page Applications (SPAs). However, this grant type is now deprecated due to its security vulnerabilities. It exposes access tokens directly in the URL fragment, which could be intercepted by malicious actors.

  1. Client requests an access token directly from the authorization server.
  2. The access token is returned in the URL fragment, which is visible to the client and potentially exposed to malicious actors.

Because of the exposed access tokens in URL can lead to potential security risks, instead, Authorization Code Grant with PKCE is now the recommended flow for client-side apps.

Flow chart

4. Client Credentials Grant

The Client Credentials Grant is for machine-to-machine communication. In this flow, the client application authenticates with its own credentials (client ID and secret) to obtain an access token, typically for accessing its own resources or a third-party API.

  1. Client authenticates with the authorization server using its client ID and secret.
  2. Authorization server issues an access token to the client.
  3. Client uses the access token to access protected resources.
Flow chart
POST /token HTTP/1.1
Host: auth.example.com
Content-Type: application/json
 
{
  "grant_type": "client_credentials",
  "client_id": "<client-id>",
  "client_secret": "<client-secret>"
}

5. Extension Grant

The Extension Grant is a custom grant type used for special use cases that don't fit into standard OAuth 2.0 flows. For example, the Device Authorization Grant (RFC 8628) allows devices with limited input capabilities (like smart home devices) to request authorization through a secondary device, like a smartphone.

  1. Device requests authorization from the server.
  2. User completes the authorization on a separate device (e.g., smartphone).
  3. Device is issued an access token after user approval.
Flow chart

Conclusion

Learning about these different OAuth 2.0 authorization methods has been an eye-opener in understanding both security concerns and proper implementations for different scenarios. While the Authorization Code Grant with PKCE is the recommended choice for public apps due to its enhanced security, especially for mobile and single-page applications, other flows like Client Credentials Grant and Extension Grants are vital for machine-to-machine and custom use cases.

The Authorization Code Grant stands out as the most flexible and widely applicable, especially in situations where user interaction is needed. Its ability to securely exchange an authorization code for an access token without exposing sensitive credentials in the front-end has made it the standard for web-based authentication. The addition of PKCE ensures that even public clients, which cannot protect client secrets, can maintain a high level of security. This makes PKCE an essential feature in any modern web or mobile app that involves sensitive user data.

On the other hand, the Client Credentials Grant is fundamental in server-to-server communication, where no user is involved. It’s particularly useful for backend services that need to authenticate with APIs or microservices. By utilizing machine-to-machine communication, this grant type ensures that systems can securely interact without user intervention, enabling seamless automation in many cloud or enterprise-level architectures.

For use cases where standard grants do not suffice, the Extension Grants provide the flexibility needed to build custom authentication flows. This includes scenarios like the Device Authorization Grant, which is particularly beneficial for IoT devices and smart devices like wearables, TVs, and other appliances with limited input capabilities. Such grants show how OAuth 2.0 can be adapted to fit evolving technological needs and non-traditional client environments.

Understanding these flows is essential when designing secure, scalable, and flexible authentication systems. Each flow serves a specific use case, and leveraging the right grant type can dramatically reduce security risks while improving the user experience. In the context of a rapidly evolving digital landscape, OAuth 2.0 provides a robust and standardized approach to managing access across diverse systems and devices, making it the go-to framework for modern identity management.

Finally, the OAuth 2.0 framework continues to evolve with industry needs, and knowing when and how to use each flow helps developers and system architects stay ahead of security threats. Implementing the right authorization method not only protects user data but also helps maintain the integrity of the systems in which these methods are deployed.


By Marko Leinikka

Word count: 1089
5 min read