I am currently trying to get Microsoft authentification running on ASP.NET Core. Basically I want to login on the frontend(React) and use my custom API.
A call might look like
https://example.com/API/returnHelloWorld
Now in React Im using @azure/msal-browser
for the login.
By using a button I am calling instance.loginRedirect(loginRequest)
which works and I am able login.
After that I call
const request = {
scopes: ["User.Read"],
account: accounts[0]
};
instance.acquireTokenSilent(request).then(response => {
console.log(response.accessToken);
}
where I get the token inside the console, but when checking it on jwt.io, I get an invalid signature error.
My authConfig.js:
import { LogLevel } from "@azure/msal-browser";
export const msalConfig = {
auth: {
clientId: "c0000d4e-0000-0000-0000-425000032721",
authority: "https://login.microsoftonline.com/eace0000-0000-0000-0000-6dced0000bc/oauth2/v2.0/token",
redirectUri: "https://example.com/signin-oidc",
},
cache: {
cacheLocation: "sessionStorage",
storeAuthStateInCookie: false,
},
system: {
loggerOptions: {
loggerCallback: (level, message, containsPii) => {
if (containsPii) {
return;
}
switch (level) {
case LogLevel.Error:
console.error(message);
return;
case LogLevel.Info:
console.info(message);
return;
case LogLevel.Verbose:
console.debug(message);
return;
case LogLevel.Warning:
console.warn(message);
return;
default:
return;
}
}
}
}
};
export const loginRequest = {
scopes: ["api://c0000d4e-0000-0000-0000-425000032721/.default"]
};
export const graphConfig = {
graphMeEndpoint: "https://graph.microsoft.com/v1.0/me"
};
Now I gave up on generating a valid token using react for now, mabye someone has an Idea what I have to do to fix this.
To ASP.NET Core
Inside the Program.cs I added
builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
.AddMicrosoftIdentityWebApi(options =>
{
builder.Configuration.Bind("AzureAd", options);
options.Events = new JwtBearerEvents();
}, options => { builder.Configuration.Bind("AzureAd", options); });
to use AzureAD / Microsoft for the authentication.
Inside the appsettings.json
"AzureAd": {
"Instance": "https://example.com/",
"Domain": "local.example.com",
"TenantId": "eace0000-0000-0000-0000-6dced0000bc",
"ClientId": "c0000d4e-0000-0000-0000-425000032721",
"Scopes": ".default", // also tried api://clientid/.default
"CallbackPath": "/signin-oidc"
}
Because I wanted to know if atleast ASP.NET Core does what it was supposed to do I generated a new Key using:
curl -X POST https://login.microsoftonline.com/eace0000-0000-0000-0000-6dced0000bc/oauth2/v2.0/token -H "Content-Type: application/x-www-form-urlencoded" -d "client_id=c0000d4e-0000-0000-0000-425000032721" -d scope=api://c0000d4e-0000-0000-0000-425000032721/.default" -d "client_secret=jtS0000SC000lorem0000000DjULkm00001aS9" -d "grant_type=client_credentials"
This gave me a key with a valid signature, but when calling (after adding the [Authorize] to the controller)
https://example.com/API/returnHelloWorld
with the token , I just get "Bearer error="invalid_token"".
Does anyone know how to get this running, or has an example which I may look at?
First of all the "invalid signature" error when validating the token on jwt.io is expected when you don't provide the public keys used by Microsoft identity platform. For validation in your server-side code, you should use libraries that can automatically retrieve Microsoft's public keys. You don't need to manually verify these tokens on jwt.io unless you also provide the public keys from Microsoft's well-known URL (https://login.microsoftonline.com/{tenant}/v2.0/.well-known/openid-configuration
).
Your authority
URL in msalConfig
seems incorrect. The authority
URL typically ends with your tenant ID or 'organizations', not /oauth2/v2.0/token
.
authority: "https://login.microsoftonline.com/eace0000-0000-0000-0000-6dced0000bc",
appsettings.json:
"AzureAd": {
"Instance": "https://login.microsoftonline.com/",
"Domain": "local.example.com",
"TenantId": "eace0000-0000-0000-0000-6dced0000bc",
"ClientId": "c0000d4e-0000-0000-0000-425000032721",
"Audience": "api://c0000d4e-0000-0000-0000-425000032721",
"CallbackPath": "/signin-oidc"
}
Your loginRequest
scopes are trying to use a .default
scope on your client application ID (api://c0000d4e-.../.default
). This scope is usually correct for acquiring tokens meant for APIs, make sure that the API is configured to this scope.
For more detail you could refer to this document: