Microsoft Graph API token validation failure

18,484

Solution 1

The issue is that you're using the id_token instead of the access token:

let tokenid= sessionStorage.getItem('msal.idtoken');

becomes something like:

let tokenid= sessionStorage.getItem('msal.token'); // or msal.accesstoken

Update(per Phillipe's comment)

You need to select the scopes that you want to target in your application. So, it looks like you want the user profile, so you'll want to add the consentScopes property to specify which scopes your app will use:

MsalModule.forRoot({
  clientID: "Tenant ID",
  authority: "https://login.microsoftonline.com/common/",
  redirectUri: "http://localhost:4200/",
  validateAuthority : true,
  popUp: true,
  consentScopes: ["user.read"]
}),

Solution 2

According to the same sample you can also attach an HttpInterceptor that will automatically attach the access token to each (external) HTTP call.

By reading through the documentation I found the following information.

consentScopes: Allows the client to express the desired scopes that should be consented. Scopes can be from multiple resources/endpoints. Passing scope here will only consent it and no access token will be acquired till the time client actually calls the API. This is optional if you are using MSAL for only login (Authentication).

That suggests that using the HttpInterceptor doesn't only attach the access token, but also retrieves it. The token that you're seeing is probably just a token for your application, but isn't a valid token for the Graph API.

Internally it uses getCachedTokenInternal(scopes: Array<string>, user: User) to get a new access token for specific scopes code found here. I'm not sure if you can use this method as well to get a new token for that resource. I would just use the interceptor.

You could try to copy the access token and see how it looks like on jwt.ms (a Microsoft provided JWT token viewer) or jwt.io.

Any tokens valid for Graph should have the Audience of https://graph.microsoft.com, so if you inspect the token (in jwt.ms) it should at least have this value.

"aud": "https://graph.microsoft.com",
Share:
18,484
infodev
Author by

infodev

Updated on June 15, 2022

Comments

  • infodev
    infodev almost 2 years

    I would use Microsoft Graph API in my Angular Web application.

    First I make connexion using msal library When I try log in with my profil I get this error

    I have configured my app as the mentionned in the official git sample

    MsalModule.forRoot({
      clientID: "Tenant ID",
      authority: "https://login.microsoftonline.com/common/",
      redirectUri: "http://localhost:4200/",
      validateAuthority : true,
      popUp: true
    }),
    

    Authetification is working and I get the token.

    Then when I'm in home page I make a second request to Microsoft Graph API to get user information using that token.

    getProfile() {
      let header= new Headers();
      let tokenid= sessionStorage.getItem('msal.idtoken'); 
      header.set('Authorization', 'Bearer ' + tokenid)
      let url ="https://graph.microsoft.com/v1.0/me/"
      return this.http.get(url,{headers:header});
    }
    

    }

    I get an 401 Unauthorized error with a response :

    {
      "error": {
        "code": "InvalidAuthenticationToken",
        "message": "Access token validation failure.",
        "innerError": {
          "request-id": "xxxxxx",
          "date": "2018-10-09T22:58:41"
        }
      }
    }
    

    I don't know why MG API is not accepting my token, Am I using wrong authority url ?

    UPDATE: I have understood that actually I get id_token which is different from access token. How can I get Access token from MSAL library to make MS GRAPH API calls ?:

  • Daniel Dobalian
    Daniel Dobalian over 5 years
    This is your problem. Need to use the access token.
  • Philippe Signoret
    Philippe Signoret over 5 years
    It shouldn't be, the access token should be a token intended for Microsoft Graph, and the ID token should be a token intended for your app.
  • infodev
    infodev over 5 years
    So the msal authentification library that uses Azure AD 2.0 (docs.microsoft.com/en-us/azure/active-directory/develop/…) don't provide a access token to MS Graph API ?
  • Philippe Signoret
    Philippe Signoret over 5 years
    It does, but you have to ask it to, by setting the consetScopes.
  • FelixJongleur42
    FelixJongleur42 over 4 years
    But what if aud=graph.microsoft.com is the only value? That does not seem suffiicent in order to make Graph happy when accessing SharePoint resources (though the client is authorized in the app registration). Struggling to find examples where some actual scopes are specified for ConfidentialClientApplication.acquireToken()
  • Stephan
    Stephan over 4 years
    You cannot have a confidential client in anguler, because you cannot keep the secret (or the access token) hidden from the user.
  • PeterOeClausen
    PeterOeClausen over 3 years
    What do I do if aud does not have "graph.microsoft.com" in it? I also have a backend API, and that's what is listed. What do I need to add in order to have "graph.microsoft.com" listed as aud?
  • Stephan
    Stephan over 3 years
    If the aud ot the token isn't the desired value you are probably using the idenity token and not the access token.