Search code examples
oauth-2.0azure-active-directoryopenid-connectaccess-tokenazure-ad-b2c

When to use an Azure AD (B2C) access token for your own API


Our typical setup for projects is an SPA (https://api.project.app) and a backend API (https://project.app) running on the same domain.

Some of our clients want to use Azure AD (B2C) to sign in and we are developing a (Laravel/PHP) package to bring all of this functionality together.

We have struggled with some access token issues as described in this article, but were finally to able to receive an access token for our own API.

Our flow works like this:

  • User signs in by being redirected to the Azure authorization endpoint using OpenID
  • Returned auth code is exchanged for an access and ID token
  • The ID token is validated and a user is resolved (or created or redirected using the register flow in B2C)
  • The user is redirected to the SPA with the access_token to make authorized requests to the API

BUT we are not using any of the features that Azure access tokens offer (permissions, roles, custom scopes, ...), these are all managed in our app.

So, I guess my question is do we really need an access token from Azure to use against our own API which shares the same database and other resources with the client app?

It feels that we only need to authenticate the users and then could easily create a token using Laravel Passport or Sanctum?

It feels that I'm missing some conceptual knowledge about OAuth/OpenID, though, any help is appreciated!


Solution

  • In terms of concepts, the following roles are used in this architecture. Hopefully this gives you a sense of direction, though there is a learning curve to integrating a full solution:

    • An authorization server (AS) from RFC6749 issues access tokens to your APIs. It also enables many ways to authenticate users. It can also act as a central store of user identity related data.

    • An identity provider (IDP) gives you a way to sign users in externally. Other login methods are also possible when using OAuth and OIDC, including passwords, WebAuthn, use of mobile wallets etc.

    • Your applications and APIs only ever interact with, and receive tokens from, the AS. The AS manages all interaction with IDPs.

    The AS is the central component where clients are registeted. If a different app or set of users want to use a different IDP, then the AS would remain the same, and no security behaviour would change in clients or APIs.

    When a client initiates a login it runs a code flow against the AS. The AS can then run a second code flow against an IDP when needed.

    SHORTER TERM

    In theory an app could authenticate users using Azure AD as an IDP, then issue its own access tokens for APIs. Doing so is non standard in these areas though:

    • The app interacts directly with an IDP
    • The app is registered as an OAuth client in an IDP
    • The app acts as its own AS to issue tokens for APIs
    • The API needs to contact the app to get public keys when validating access tokens

    This will make it more complex to add new OAuth secured apps in future, or to integrate future authentication methods, that differ from Azure AD.

    In the longer term an authorization server can enable you to manage these aspects in the most extensible way, with the simplest application code.