Azure AD B2C : User credential validation against custom user store - azure-ad-b2c

Can Azure AD B2C pass the "UserName/Email and Password" entered by end user to a third party trusted application for credentials validation and get the claims for the user on successful credentials validation by the App?
This scenario arises because, some of my users are in Azure AD B2C and some of the users are maintained in the custom user store and can't be moved to Azure AD B2C due to business reasons. Yet i want to provide same sign-in experience for both users.

The Wingtip sample contains an example of this integration.
See the "ClassicAccount" claims provider for reference.
This claims provider, which is implemented by a REST API, is integrated in to the sign-in user journey to sign users in using logins that are external to the Azure AD B2C directory.
Code for the REST API can be found in the same repository.

Related

What approaches are available for allowing Azure AD B2C users to GET and POST data to a M365 environment via Graph API?

Per the docs, there is no 'out of the box' way to enable Azure AD B2C users to interact with the M365 environment associated with the Azure AD tenant that was used to create the Azure AD B2C tenant.
Azure AD B2C can't be used to authenticate users for Microsoft 365.
Source:
Can I use Azure AD B2C to provide social login (Facebook and Google+) into Microsoft 365?
But I still need to be able to provide this functionality, i.e GET and POST requests to M365 via the Graph API.
To be clear, this is what I have achieved so far:
Azure AD B2C users can login
Azure AD users can login and interact with their own M365 environment via Graph API
(to enable this, I added the Azure AD tenant as an identity provider, per this article)
What I have not yet been able to figure out is:
How can the Azure AD B2C users interact with the M365 environment associated with the Azure AD tenant?
(that created the Azure AD B2C tenant)
To illustrate a use case for this requirement:
Company_A wants to enable external contractors to be able to submit compliance documents to them
They set up Azure AD B2C and create accounts for their external contractors
They set up a Node.js/Express web app on Azure
External contractors can now login to a web app and view forms designed to submit data and attachments
How can those forms send data and attachments to a Document Library in Company_A's M365 environment?
I have been pondering this issue for a while and can't conceptualise a mental or technical model of how this can be achieved.
Google searching related phrases doesn't produce any relevant content.
I am hoping someone will have the knowledge and experience to be able to say:
You will need to follow THIS paradigm which is documented HERE and involves doing THIS
Edit:
I am reading articles like these:
Get access without a user
which talks about scenarios where:
apps that have a signed-in user present may also need to call Microsoft Graph under their own identity
and contemplating adding Application Permissions (as opposed to Delegated Permissions) to my Azure AD B2C application registration.
Just to test the idea, I have added Sites.ReadWrite.All as an Application Permission and granted Admin Consent for that permission. How would I define this scope (Sites.ReadWrite.All) to be associated with the 'home' Azure AD tenant (as opposed to the Azure AD B2C tenant)? I am using msal-node which has a method named getAuthCodeURL() where you pass through the scopes required. I am assuming if I just added Sites.ReadWrite.All it would default to being applied to the Azure AD B2C tenant, rather than the desired Azure AD tenant?
M365 doesn’t exist in an Azure AD B2C tenant, you cannot apply a license for Office there. This simply isn’t possible.
For Graph API, you cannot use B2C issued tokens to call it. You must use underlying AAD Tokens to access it. Your server would need to perform Azure AD client credentials flow against the Azure AD endpoint of your AAD B2C tenant and ask for a token to Graph API. https://learn.microsoft.com/en-us/azure/active-directory/develop/v2-oauth2-client-creds-grant-flow
Microsoft service scopes only apply to the underlying Azure AD endpoints of your AAD B2C tenant. They won’t mean anything at the AAD B2C login endpoints. Hence, the differentiation is made by the endpoint used.
An Azure AD B2C tenant has both endpoints:
AAD: login.microsoftonline.com/tenantId
B2C: b2clogin.com/tenantId
Since M365 env does not exist for B2C tenants, the MS Graph API is only useful to R/W user data. But, for this, you could just use the B2C user flows to R/W user profile data, and return user profile data into the B2C token, so you don’t have go call MS Graph API. This is actually the intended usage pattern.

Azure B2C Signup For External Provider and Sign In for Local Provider

This is extension to this question that I have already asked.
Authenticate Azure AD User Using Azure B2C
Now with suggested solution over there, I can add Azure Ad as an OpenId provider.
Only problem is that, I have to sign in / sign up flow for this. I only want to use Sign In flow as requirement is that user will preconfigured into Azure B2C and only those user allow to access application so sign up needs to disable. This work for local account but external AD if user is not created in B2C as part of Sign up process then it will not work.
Is there any specific way that Sign up only for external AD.

Error 70001 trying to sign in as Azure AD B2C user with custom Identity Experience Framework policy

We have a Web App secured with Azure AD B2C using custom Identity Experience Framework policies to allow users to register and sign in with social identities (Microsoft, Google, Facebook), or with an identity from another federated Azure AD instance, or with 'local' Email / Password accounts.
All the social accounts and the Federated AD work correctly. Sign up and sign in with Email/Password was working correctly, but we are now experiencing an error. We haven't knowingly made any changes to our Email/Password configuration since this was last known to be working, so we're not sure how this has happened.
The issue is: Sign Up with a new Email Address works correctly, and after the process completes, the user is correctly logged-in, and their account appears in the directory. If the user signs out, however, then any attempt to sign back in again fails:
(Email address shown is not the actual one. Error has been repeated by multiple users with new and old email/password combinations.)
Digging into the portal, the underlying error is revealed as:
70001 The application named X was not found in the tenant named Y. This can happen if the application has not been installed by the administrator of the tenant or consented to by any user in the tenant. You might have sent your authentication request to the wrong tenant.
This error appears sometimes to be related to a failure to grant permissions to an application in the portal. We have tried removing and reinstating all permissions, and re-granting permissions. This has not solved the issue.
Does anyone know what could be causing this issue, and in particular why sign up / sign in works correctly, but returning sign in does not?
UPDATE:
Just to confirm that we have the IEF and Proxy IEF apps configured in the AD directory:
And we have the login-NonInteractive technical profile configured in TrustFrameworkExtensions.xml:
Having wired up Application Insights (following these instructions https://learn.microsoft.com/en-us/azure/active-directory-b2c/active-directory-b2c-troubleshoot-custom), we're able to get to this more detailed error:
AADSTS70001: Application with identifier
'ProxyIdentityExperienceFrameworkAppID' was not found in the directory
weapageengine.onmicrosoft.com
The only place 'ProxyIdentityExperienceFrameworkAppID' appears in any of our custom policies is shown in the XML snipped above, but this seems correct as per the documentation here: https://github.com/Azure-Samples/active-directory-b2c-custom-policy-starterpack/blob/3b4898fec3bf0014b320beffa6eb52ad68eb6111/SocialAndLocalAccounts/TrustFrameworkExtensions.xml#L38 - unless we are meant to update those 'DefaultValue' attributes as well?
Resolution:
As per the answer below, it is necessary to update both the Metadata and the default values with the relevant app ids. Worth noting that in the GitHub sample https://github.com/Azure-Samples/active-directory-b2c-custom-policy-starterpack/blob/3b4898fec3bf0014b320beffa6eb52ad68eb6111/SocialAndLocalAccounts/TrustFrameworkExtensions.xml#L38 the boilerplate values are differently cased, leading to our missing one in a replace-all:
The local account sign-in authenticates the end user against the Azure AD B2C directory and then reads the user object from it.
The local account sign-up and the social account sign-in do not authenticate the end user against the Azure AD B2C directory. The local account sign-up writes the user object to it. The social account sign-in delegates authentication to the social identity provider and then either writes the user object to the Azure AD B2C directory if the user object does not exist or reads the user object from the Azure AD B2C directory if the user object does exist.
To enable authentication of the end user by the local account sign-in against the Azure AD B2C directory, you must add the Identity Experience Framework applications to the Azure AD B2C directory and then configure these IEF applications with the login-NonInteractive technical profile.
The local account sign-up and the social account sign-in do not require these applications.

Multiple accounts created with same Facebook login in Azure AD B2C

I am seeing duplicate accounts being created using the same Facebook login on Azure AD B2C. My understanding has always been that using the combined sign-up/sign-in policy, if a user taps a social provider, Azure AD B2C will sign them back in using the same Azure AD B2C account if they created it using Facebook rather than creating a new one.
In this case however, I have three examples where 2 Azure AD B2C accounts exist with the same email address, created by the user using Facebook as the authentication mechanism. They share the same name and profile photo but have different Azure AD AD object id's.
There is a known outstanding Facebook issue around expired tokens which was acknowledged by Microsoft and is logged on UserVoice here after a paid developer support issue was logged on the Azure portal: Fix the faulty Facebook integration and more transparency please!
I have logged this here under the request from Azure Support on Twitter:
https://twitter.com/AzureSupport/status/949258937915895809
Please assist - we are very concerned about these issues with regards B2C's integration with a very popular social provider!
Millions of end users use facebook to register and login to apps secured by Azure AD B2C.
If you are sure that the same facebook user(same user id) registered into the b2c app, then it may be possible that you used different facebook Application IDs. In which case you would have different facebook ids presented to b2c, resulting in 2 different Azure AD B2C user accounts.
Alternatively, it is possible that a single facebook user with email joe#email.com registerd into b2c using their facebook login and later selected "local account" and created a local user (non facebook) using the same email joe#email.com. These would appear as 2 different users.

API authentication for Azure AD B2C users?

Is there a back-end API available to programatically authenticate the external user against the Azure AD B2C instance by passing in the user credentials from within a MVC web application (without showing the login page) as we do from a Native Client like console application?
Authentication through a back-api that accepts user credentials is achieved through the OAuth Resource Owner Password Grant.
Azure AD B2C does not support the "Resource Owner Password Grant" yet.
You can support this feature ask and get updates on its progress by voting for it in the Azure AD B2C feedback forum: Add support for Resource Owner Password Credentials flow in Azure AD B2C.

Resources