How can I get the azure AD roles in my Backend? - node.js

I am developing a backend in node express where I use the passport-azure-ad library to protect the routes of my api, is there any way to access the roles defined in Azure Ad for the application and validate them in the routes?

To achieve the above requirement you may need to follow the below workaround.
We can get our Azure AD log details by using MS GRAPH Programmatically
SAMPLE CODE:-
const options = {
authProvider,
};
const client = Client.init(options);
let directoryAudit = await client.api('/auditLogs/directoryAudits/{id}')
.get();
Also you can get roles which has assigned in Azure AD by using below MS GRAPH query in your code.
GET /users/{id | userPrincipalName}/appRoleAssignments
For complete setup please refer the below links:
MS DOC:- Call the Microsoft Graph API in a Node.js console app.
SO THREAD:- How to issue tokens from Azure AD in a Node.js App/API?

Related

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

Create Microsoft Azure AD application programmatically using Node.Js

We have a requirement where we want to create the Azure AD application automatically for enabling Microsoft Login.
Is there any way we can programmatically achieve the creation part as everywhere it is showing the GUI steps for registering an app in Azure AD.
Thanks in Advance.
You can register the application using this api
POST https://graph.microsoft.com/beta/applications
One of the following permissions is required to call this API
1) Delegated (work or school account):
Application.ReadWrite.All, Directory.ReadWrite.All,
Directory.AccessAsUser.All
2) Delegated (personal Microsoft account):
Application.ReadWrite.All
3) Application: Application.ReadWrite.OwnedBy, Application.ReadWrite.All,
Directory.ReadWrite.All
Example:
const options = {
authProvider,
};
const client = Client.init(options);
const application = {
displayName: 'Display name'
};
await client.api('/applications')
.version('beta')
.post(application);
For more details refer this document

I need to connect to Azure Media Services with user authentication

I'm writing a commandline tool to manipulate assets in Azure Media Services using the v3 AMS API. It should authenticate using the logged on user. As the Windows AD and Azure AD are synchronised, it should not need to pop up a login dialog box.
This document:
https://learn.microsoft.com/en-us/azure/media-services/latest/access-api-howto?tabs=portal
states that it's possible to use either user or service principal authentication to connect to AMS.
In this document:
https://learn.microsoft.com/en-us/azure/media-services/latest/configure-connect-dotnet-howto
there's an example of how to do service principal authentication but I can't find anything about user authentication. The code in the sample looks something like this:
var clientCredential = new ClientCredential(config.AadClientId, config.AadSecret);
var credentials = await ApplicationTokenProvider.LoginSilentAsync(config.AadTenantId, clientCredential, ActiveDirectoryServiceSettings.Azure);
var amsClient = new AzureMediaServicesClient(config.ArmEndpoint, credentials)
Note that all constructors of AzureMediaServicesClient take a ServiceClientCredentials object, so how can I authenticate using UserCredentials?
Azure Media Services Explorer does user based authentication (and SP auth). https://aka.ms/amse
Code for the user based authentication :
https://github.com/Azure/Azure-Media-Services-Explorer/blob/master/AMSExplorer/Program.cs#L779-L843

MS Graph API and DriveItem search not working with client credentials flow

I'm trying to call the search endpoint of the OneDrive API on a drive (i.e. https://graph.microsoft.com/v1.0/drives/{drive-id}/root/search(q='mysearchterm').
This works fine on the Graph Explorer, however, I'm not getting any search results with the client credentials flow on the same drive.
My app registration has all the required application permissions mentioned in the API documentation (Files.Read.All, Files.ReadWrite.All, Sites.Read.All, Sites.ReadWrite.All) and reading drives, driveitems, downloading drive items is all working fine. The one thing that is not working, is searching on drive items. I'm just getting an empty array back, no errors;
{"#odata.context":"https://graph.microsoft.com/v1.0/$metadata#Collection(driveItem)","value":[]}
I'm using adal-node with acquireTokenWithClientCredentials.
var adal = require("adal-node");
const TENANT = "{tenant-name-here}.onmicrosoft.com";
const CLIENT_ID = "{Application-id-here}";
const CLIENT_SECRET = "{Application-key-here}";
function getToken() {
return new Promise((resolve, reject) => {
const authContext = new adal.AuthenticationContext(
`https://login.microsoftonline.com/${TENANT}`
);
authContext.acquireTokenWithClientCredentials(
GRAPH_URL,
CLIENT_ID,
CLIENT_SECRET,
(err, tokenRes) => {
if (err) {
reject(err);
}
resolve(tokenRes.accessToken);
}
);
});
}
The drive I'm searching on is a SharePoint document library.
Some important tip: client credentials flow need to register the app in the Azure Management Portal but not Applicaation Registeration Portal. Graph Explorer is mostly based on the later one, so they have different backend code now is normal. Maybe they will do the same logic in furture.
We strongly recommend that you use Microsoft Graph instead of Azure AD Graph API to access Azure Active Directory resources. Our development efforts are now concentrated on Microsoft Graph and no further enhancements are planned for Azure AD Graph API. There are a very limited number of scenarios for which Azure AD Graph API might still be appropriate; for more information, see the Microsoft Graph or the Azure AD Graph blog post in the Office Dev Center.
adal-node is not the same as Graph, so you get result in the graph explorer but not the NodeJS product. We suggest you to use the latest Graph API.
Official docs: https://learn.microsoft.com/en-us/javascript/api/overview/azure/activedirectory?view=azure-node-latest

Azure AD OpenIDConnect + ASP.NET Core - Authenticate and Extra Permissions/Token?

I am using the following bits against my Azure AD to authenticate with ASP.NET Core.
https://azure.microsoft.com/en-us/resources/samples/active-directory-dotnet-webapp-openidconnect-aspnetcore/
https://github.com/Azure-Samples/active-directory-dotnet-webapp-openidconnect-aspnetcore
I have the basic login/auth working after creating an Azure AD app. User can login/logout.
My question is given this, what's the best way when a user Auth's to log to a DB? I thought about making the redirect URL to an endpoint, saving, then just redirecting back to "Home" but is that ideal?
Also, is it possible to retrieve a bearer token via this approach? Or does this require another type of call or extending "scope"? So that for example I could retrieve the authenticated users Manager.
https://graph.microsoft.com/v1.0/me/manager
My question is given this, what's the best way when a user Auth's to log to a DB? I thought about making the redirect URL to an endpoint, saving, then just redirecting back to "Home" but is that ideal?
This way only able to log those who already sign-in your app successfully. It is not able to log those users who are attempt to sign-in your app but enter the wrong password.
Azure AD already provide lots of report to gain visibility into the integrity and security of your organization’s directory.( refer here)
And if you are using the Azure AD Premium, you can review the sign-in activities via the Azure new portal below:
And if you want to store the sign-in activity in your web app, you can write the custom code after the token is verified. Here is the code for your reference:
// Configure the OWIN pipeline to use OpenID Connect auth.
app.UseOpenIdConnectAuthentication(new OpenIdConnectOptions
{
ClientId = Configuration["AzureAD:ClientId"],
Authority = String.Format(Configuration["AzureAd:AadInstance"], Configuration["AzureAd:Tenant"]),
ResponseType = OpenIdConnectResponseType.IdToken,
PostLogoutRedirectUri = Configuration["AzureAd:PostLogoutRedirectUri"],
Events = new OpenIdConnectEvents
{
OnRemoteFailure = OnAuthenticationFailed,
OnTokenValidated = context => {
//write the custom code to store users login-in
return Task.FromResult(0); }
},
});
Also, is it possible to retrieve a bearer token via this approach?
Yes. We can get the token after receive the authorization code. You can refer the code sample here to acquire the token from asp.net core app.

Resources