How to implement On behalf of flow in Azure Ad? - azure

Net core application. I have three applications registered in azure ad.
React SPA application
Web API Gateway application
Protected API application
Whenever user logs into SPA application, Redirecting to Azure AD with implicit flow to get access token.
I have received access token as below and used to access apis from gateway layer
{
"aud": "7851c317b-87e7-4cb3-95f0-37cb52b6f873",
"family_name": "alex",
"given_name": "fernandes",
"hasgroups": "true",
"roles": [
"Admin"
]
}
In the above token aud is client id of the spa application and other few details I added but not all the details.
Now I want to call Protected API application from Web API Gateway application
I am trying with sample http request in postman as below.
Request - https://login.microsoftonline.com/45fgh-f30d-4596-gt67-7045b338485a/oauth2/v2.0/token
Body
{
"grant_type": "urn:ietf:params:oauth:grant-type:jwt-bearer"
"client_id": "" //unknown client id of SPA or API GateWay or Protected API
"client_secret": "" //unknown client id of SPA or API GateWay or Protected API
"assertion": "Above token"
"scope":"" //unknown
"requested_token_use" : "on_behalf_of"
}
Along with above confusions, just wondering Is there any configurations required in azure ad in order to generate token for Protected API. One more thing is the token generated to access Protected API does that token have user details and role details same as above token generated by SPA?
Can someone help me in configuring On behalf of flow? I am struggling here to get this done. Any help would be appreciated. Thank you

As the following diagram shows, Client App means React SPA application, Web API 1 means Web API Gateway application, and Web API 2 means Protected API application. For more details, see this blog.
Steps of On-Behalf-Of flow:
Add API permission of Web API Gateway application to SPA application.
GET https://login.microsoftonline.com/{tenant}/oauth2/v2.0/authorize
?scope={permission for Web API Gateway application like api://1108f6-xxxxxxx-9f622/test} openid
&redirect_uri={redirect_uri of SPA application}
&nonce=123
&client_id={client-id of SPA application}
&response_type=id_token token
Add API permission of Protected API application to Web API Gateway application.
It calls Microsoft Graph API in the official document, so the scope is 'user.read' in this step.
POST https://login.microsoftonline.com/{tenant}/oauth2/v2.0/token
grant_type=urn:ietf:params:oauth:grant-type:jwt-bearer
&client_id={client_id of Web API Gateway application}
&client_secret={client_secret}
&assertion={access token from previous step}
&scope={permission for Protected API application}
&requested_token_use=on_behalf_of
Call Protected API application with the access token

Related

Azure Function App (Backend) 401 Error when accessing from Azure App Service Frontend

we have a problem and i dont see anything which i can do for now. I've already followed for example this article but i does not work for now: Azure Function App as Backend
Azure AD Authentication is configured in our Azure Function App and with postman i can connect with a bearer token to the function app.
Function App Authentication is configured with error 401 for apis
I can see in the browser that there is always this error when we open the frontend app. There is no access to the Azure AD secured backend function app from the frontend: Failed to load resource: the server responded with a status of 401 (Unauthorized)
i exposed the api from the app registration of the backend function app and gave them invoke delegated rights to the frontend app registration like in the blog article. CORS is configured too.
App Reg Invoke Config
is there anything i can do? We login to our Frontend App Service with Azure AD credentials and this token should give access to the backend service function app too so there is nothing unprotected in the public internet. But frontend get always this 401 error.
I tried to reproduce the scenario from my end :
When you decode the bearer token ,
Check issuer url and audience received
Also if issuer url has v2 endpoint ,Make sure the accessTokenAcceptedVersion is set to 2 other wise null or 1
Manifest:
{
"id": "4axxxxxxx039",
"acceptMappedClaims": null,
"accessTokenAcceptedVersion": 2,
...
}
Try including function app url https://kafnapprepo.azurewebsites.net
in allowed audiences. Along with the clientId of the app and AppId uri
and make sure the permissions are granted admin consent.

Azure B2C client credentials flow throws invalid_grant AADB2C90085

I followed this resource: https://icareb2cdev.b2clogin.com/icareb2cdev.onmicrosoft.com/B2C_1A_DEMO_CLIENTCREDENTIALSFLOW/oauth2/v2.0/token
Azure B2C App registrations:
Protected web api
Expose an api
App ID URI = https://{my tenant name}.onmicrosoft.com/{protected web api client id}/.default
Daemon console app
API Permissions
API = protected web api
Permission = access_as_application
Type = Application
Admin consent requested = Yes
I acquire a token using the OAuth client credentials flow:
POST https://{my tenant name}.b2clogin.com/{my tenant name}.onmicrosoft.com/{a basic user flow SUSI policy}/oauth2/v2.0/token
scope=https://icareb2cdev.onmicrosoft.com/{protected web api client id}/.default&
grant_type=client_credentials&
client_id={daemon console app client id}&
client_secret={daemon console app client secret}
Error response:
{
"error": "invalid_grant",
"error_description": "AADB2C90085: The service has encountered an internal error. Please reauthenticate and try again.\r\nCorrelation ID: REDACTED\r\nTimestamp: REDACTED\r\n"
}
I ran into the same issue, please double check your Manifest and make sure that "signInAudience": "AzureADandPersonalMicrosoftAccount" and not your organization only. Do also ensure you followed the steps same as other answer.

Getting Error AADB2C99067 when trying to request access token from Azure B2C

I have an Azure AD B2C tenant setup with an Angular app on the front-end using Authorization Code Flow with PKCE and a back-end api. Everything is working fine. I now have a need to allow the user to access certain pages on the front-end anonymously. I would prefer to still protect the apis these pages will call using the same access token.
I have followed the article here to set up Client Credentials flow. I am able to get an access token successfully using Postman and use it to call my back-end apis fine. However, when I try to do the same from the Angular app, I get the following error:
{"error":"invalid_request","error_description":"AADB2C99067: Public Client XXXXX-XXXXXX is not supported for Client Credentials Grant Flow\r\nCorrelation ID: 2b3346ef-1828-4900-b890-06cdb8e0bb52\r\nTimestamp: 2022-07-28 04:12:21Z\r\n"}
Below is the code snippet I am using in Angular to retrieve the access token.
const urlencoded = new URLSearchParams();
urlencoded.set('grant_type', 'client_credentials');
urlencoded.set('client_id', '<clientid>');
urlencoded.set('client_secret', '<clientsecret>');
urlencoded.set('scope', '<scope>');
const httpOptions = {
headers: new HttpHeaders({ 'Content-Type': 'application/x-www-form-urlencoded' }),
};
const url = 'https://<b2ctenant>.b2clogin.com/<b2ctenant>.onmicrosoft.com/<customPolicy>/oauth2/v2.0/token';
return this.httpClient.post(url, urlencoded, httpOptions);
Any ideas what could be missing?
Thanks!
Though azureadb2c supports client_credential flow.One may not use them with SPA apps.
This scenario is not supported by MSAL.js. Client credential flow/ grant type will not work in SPAs(Angular) because browsers cannot securely keep client secrets.
As they may end up in the browser, visible to everyone and to attackers that load them.
Note:As the application's own credentials itself are being used, they must be kept safe - never publish that credential in your source
code
If you are using it for web app , please make sure to select the platform as web or change the reply url type to be web.
"replyUrlsWithType": [
{
"url": "https......",
"type": "Web"
},
]
Please refer :
Configure authentication in a sample Angular SPA by using Azure
Active Directory B2C | Microsoft Docs
OAuth 2.0 client credentials flow on the Microsoft identity platform- Microsoft Entra | Microsoft Docs

Azure AD Token based Authentication for WebAPI

We have developed Web API in .net Core 2.1 without authentication.
But now we are trying to add the Azure AD token based authentication.
we have registered app in azure AD and we did necessary changes in startup.cs file. and added authorize tag
When we test the API in postman we generated token we are getting Microsoft login page in Html format as result.
when we crosscheck the API in browser, its asking domain user name and password by providing the user name password we are getting the result.
Its seems some configuration or setting missing in Azure AD setup or code.
Can anyone help on this. other wise anyone share the steps for token based authentication implementation for API.
If you already have the api , you should firstly register an app in Azure Portal .
In your api application , you can follow the below steps :
Install the package Microsoft.AspNetCore.Authentication.AzureAD.UI
Register the Azure AD Bearer authentication service in ConfigureServices function :
services.AddAuthentication(AzureADDefaults.BearerAuthenticationScheme)
.AddAzureADBearer(options => Configuration.Bind("AzureAd", options));
In appsettings.json , set the correct api configuration from Azure Portal :
"AzureAd": {
"Instance": "https://login.microsoftonline.com/",
"Domain": "YourDomain.onmicrosoft.com",
"TenantId": "cb1c3f2e-a2dd-4fde-bf8f-f75ab18b21ac",
"ClientId": "83bf146d-4948-4596-a4b3-b7b2e68ac3e0"
},
Tenant ID ,domain name and API's ClientId could be find in Azure Portal .Then you can add Authorize attribute on protected controllers/actions . If you have multiple authentication schema , you can authorize with a specific scheme .
You client app will uses the OpenID Connect middleware and the ADAL/MSAL to obtain a JWT bearer token for the signed-in user using the OAuth 2.0 protocol. The bearer token is passed to the web API, which validates the token and authorizes the user using the JWT bearer authentication middleware.

How do I authorize a service to call an API using Azure Active Directory?

I have a service that gets an access token from Azure AD. I have an API that I would like to accept that token as authorization.
My service code to call the API is
HttpClient client = new HttpClient()
{
BaseAddress = new Uri("https://localhost:44372/")
};
HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, client.BaseAddress + "api/todolist");
request.Headers.Authorization = new System.Net.Http.Headers.AuthenticationHeaderValue("Bearer", accessToken);
HttpResponseMessage response = await client.SendAsync(request);
The response I get back is a 401 - Unauthorized.
I have a feeling that the issue is in the API ConfigureServices function; specifically (this was taken from an example, so I don't really know what it means yet):
services.Configure<JwtBearerOptions>(AzureADDefaults.JwtBearerAuthenticationScheme, options =>
{
options.TokenValidationParameters.RoleClaimType = "roles";
});
I'm new to Azure and authentication in general so I don't know what options are available or appropriate. I also am not sure how to set up the applications in Azure to allow this. I have the application id of the service set up as an Authorized client application of the API; it is also listed int the knownClientApplications in the API manifest.
There are just so many knobs to turn, I have no idea where to go from here. If anyone can let me know some things to try, that would be outstanding.
Thanks
Here is a code sample on how to call a web API in an ASP.NET Core web app using Azure AD:
https://learn.microsoft.com/en-us/samples/azure-samples/active-directory-dotnet-webapp-webapi-openidconnect-aspnetcore/calling-a-web-api-in-an-aspnet-core-web-application-using-azure-ad/
This sample contains a web API running on ASP.NET Core 2.0 protected by Azure AD. The web API is accessed by an ASP.NET Core 2.0 web application on behalf of the signed-in user. The ASP.NET Web application uses the OpenID Connect middleware and the Active Directory Authentication Library (ADAL.NET) to obtain a JWT bearer token for the signed-in user using the OAuth 2.0 protocol. The bearer token is passed to the web API, which validates the token and authorizes the user using the JWT bearer authentication middleware.

Resources