简体   繁体   中英

Securing REST API Calls in SPAs using MSAL.js with Azure Active Directory - How to Pass Authentication Token to Bearer Strategy

I am creating a SPA using React and Express. I am trying to include authentication using MSAL.js and have looked at Microsoft's tutorials for SPA . I've been able to implement this with React using @msal-react. While this does perform authentication, it does not protect the REST API from access by unauthenticated users.

I found the Active Directory Javascript Nodejs Web API that seems to provide a means for protecting the REST API using Passport and the Bearer strategy, but the links showing how to couple this with the client-side seem to be broken.

I'm not sure how to connect the authentication that is occurring on the client side with REST API. As I understand it, the authentication token has to be passed, but I am not sure how to pass that.

The server-side sample code has:

// API endpoint exposed
app.get("/api",
    passport.authenticate('oauth-bearer', {session: false}),
    (req, res) => {
        console.log('Validated claims: ', req.authInfo);

        // Service relies on the name claim.  
        res.status(200).json({
            'name': req.authInfo['name'],
            'issued-by': req.authInfo['iss'],
            'issued-for': req.authInfo['aud'],
            'scope': req.authInfo['scp']
        });
    }
);

What I tried to do on the client side was to get the account information:

import {
  useAccount,
  useMsal
} from "@azure/msal-react";

...

const { accounts } = useMsal();
const account = useAccount(accounts[0] || {});

From looking at account after authenticating, I thought account.idTokenClaims might have what is necessary, but have had no luck.

I am stuck because I am not sure if I have a fundamental misunderstanding of how the Bearer strategy works, if I am using MSAL or Passport (or both) incorrectly, or if this is a configuration issue. I appreciate the help!

When calling your protected REST API, you need to present an access token obtained by the client application (on behalf of the signed-in user). So the ID token won't do here -it's only meant for your client application as a proof of successful user authentication. (ideally, your client and service apps should be separate, each represented by an Azure AD app registration).

After authentication, you need to obtain an access token, by using one of the acquireToken* methods. You pass a token request object to that method. Here you need to specify what resources and permissions you are requesting an access token for. The access token that would work with calling your REST API shouldn't/won't work with other APIs.

The tutorial article you linked points to a sample using implicit flow . I would recommend using the more secure auth code flow .

This tutorial should cover your need. Check this section in particular.

ps for a React client app, see this .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM