A Practical Guide to leverage OAuth2 Authorization Flows

Hi there!

We have partners who would wish to use our API. In order to grant them access to our API, we would like to implement a flow similar to that of Google when you sign in from another app.

I’ve read the article OAuth2 Implicit Grant and SPA by Vittorio, the OAuth2 Authorization Framework, and the Authorization Flows section of the documentation but I am still unclear about how to implement it properly.

So to get started, here are a few questions that I couldn’t figure out from the documentation:

  1. Does the partner application need to have a client ID created through our Management Dashboard?
  2. How can I limit the scopes that the partner application has access to?
    2.1. Is there a way to do so on the Management Dashboard?
    2.2. Can I have a Rule that refuses certain scopes?
    2.3. How do I return such an error to the application?
    2.4. Can I use a Rule to grant different scopes than those requested?
  3. Is the auth-spa-js package a turnkey solution?
    3.1. Can my partners simply install this package on their SPAs, follow the steps, and then be able to leverage the Authorization Code with PKCE flow right away?
    3.2. How can they specify which OAuth2 scopes they want?
    3.3. Is this secure or I need to implement supplementary measures to protect my users’ auth?
    3.4. Can this solution allow to refresh the token? What are the conditions for the user to have to reauthenticate?
    3.5. If it is not a turnkey solution, how do I implement a secure flow to grant some permissions to an external application? Is there a sample repository I can reproduce?
    3.6. If this is a turnkey solution, why is it not the very first thing that we see in the Authorization Flows section?

Thanks a lot for your help!

Have a great day :slight_smile:

Cheers! :butterfly:

Hi there @philippegoarthurai and welcome to the Auth0 Community!

I apologize for the delay in response. Let me see if I can get some help with answering all of your questions :raised_hands:

Hi @philippegoarthurai
Let me try to answer your questions:

  1. Does the partner application need to have a client ID created through our Management Dashboard?

That is correct. If you want to provide open access to your APIs via OAuth2, you’ll have to have some kind of application registration offered to your partners, so that a client can be registered at your Auth0 dashboard. This can be as simple as a phone call or secure exchange of data, all the way to a “developer console” that you could offer to your partners, where they can register new clients. Your registration app would use Management API v2 to create clients on your Auth0 tenant.

Your partners will have to provide:

  • The application type (SPA/Native/Regular web app)
  • The callback URLs
  • The name for the app

In exchange, you’ll provide the client ID and the client secret (only for confidential clients, i.e. regular web apps or other server apps), as well as the domain to where they will send the /authorize request to get a token.
You might want to set your API as the default audience for the tenant. Also, the apps you create for your partners should be flagged as Third-Party Apps. Make sure to read the link to understand the limitations that third-party apps have, and how they work with domain connections. Also read Enable Third-Party Applications to understand changes that are needed in the hosted login page.

  1. How can I limit the scopes that the partner application has access to?
    2.1. Is there a way to do so on the Management Dashboard?
    2.2. Can I have a Rule that refuses certain scopes?
    2.3. How do I return such an error to the application?
    2.4. Can I use a Rule to grant different scopes than those requested?

For machine-to-machine apps (where your partner application would obtain a token directly using the client id/secret, without any user involvement), you can set the scopes allowed for the app directly in the dashboard.
For applications with interactive user authorization, you can use rules to restrict the scopes granted in a token.

In a rule, you can use accessToken.scope to alter the scopes returned in the access token (either limit or change them altogether).

function (user, context, callback) {
  var requestedScopes = (context.request.body.scope || context.request.query.scope || "").split(" ");

  // do your custom scope filtering based on context 
  // information, like `context.clientID`
  var filteredScopes = requestedScopes.filter(...);

  // add more scopes if you need to
  [..]
  
  context.accessToken.scope = filteredScopes;

  callback(null, user, context);
}

You can always return an error to the app using the form callback(new UnauthorizedError("Sorry, no token for you")). The error will get back to the app’s callback endpoint.
If you simply restrict scopes, the scopes granted will be listed as part of the response (client apps are supposed to check the scope part of the result to check the scopes actually granted).

  1. Is the auth-spa-js package a turnkey solution?

Yes. It’s an SDK to ease the OAuth2 dance of obtaining an access token to then call your API. Note that the SDK has a specific target: Single Page Apps running in the browser. If your partner is doing a native app or a regular web app, they should use any of our other SDKs/tutorials available.

3.1. Can my partners simply install this package on their SPAs, follow the steps, and then be able to leverage the Authorization Code with PKCE flow right away?

Yes

3.2. How can they specify which OAuth2 scopes they want?

Using the scope parameter in the authorization request. If they are using auth0-spa-js, that’s through the scope parameter in the options.

const auth0 = await createAuth0Client({
  domain: '<AUTH0_DOMAIN>',
  client_id: '<AUTH0_CLIENT_ID>',
  redirect_uri: '<MY_CALLBACK_URL>',
  scope: 'openid profile email read:timesheets'
});

3.3. Is this secure or I need to implement supplementary measures to protect my users’ auth?

Undertanding that “Secure” is not boolean (if you want it fully secure don’t use the internet :slight_smile: ), this is as secure as it gets using the OAuth2 protocol (which is the most secure protocol devised so far for delegated authorization). Implementors still need to be careful and follow OAuth2 and OIDC rules on validating responses and so on, but that is handled by the different SDKs.
Your users will only be prompted for credentials at your Auth0 domain, and the third-party app will only get a token, that will be valid only for what you approve in your rule’s logic.
Using rules you can also restrict the claims that apps get in the ID token, if necessary.

3.4. Can this solution allow to refresh the token? What are the conditions for the user to have to reauthenticate?

You can use the refresh token flow for native. SPAs rely, for now, on getTokenSilently (which opens a hidden iframe and attempts to get a token without user interaction) for a renewed token and can callback to other methods (like getTokenWithPopup) if getTokenSilently fails. Cross-domain will be always a concern for getTokenSilently with third-party apps, so with single page apps users might have to authenticate more often (or see the popup dialog). Regular web apps can benefit from the Auth0 session that the user will have, and native apps can use the refresh token flow.
You can configure the session duration in the tenant settings.

3.6. If this is a turnkey solution, why is it not the very first thing that we see in the Authorization Flows section?

Can you clarify which document you are referring to?

1 Like

This topic was automatically closed 15 days after the last reply. New replies are no longer allowed.