3

I am already using B2C custom policy to let employees signin using external IdP, now I want to use my organization's Azure enterprise AD app as IdP. All employees are already registered using external IdP but external IdP subscription will expire soon, so I need to move them to Org's Azure AD IdP.

When registered user sign in using Azure enterprise AD app with same email Id, it should find the existing users based on email and associate the existing user's objectId with new Azure IdP. It should not create a new ObjectId for same email user for new IdP.

In my case it is creating new objectId for different policy and I don't want new objectId created for different IdP because then it will duplicate the user in database due to new object Id Instead I want the same object Id, can you please provide info how this can be achieved?

I followed this while updating my policy - Link user journey

 <TechnicalProfile Id="AAD-UserReadUsingEmailId-Link">
      <Metadata>
        <Item Key="Operation">Read</Item>
        <Item Key="RaiseErrorIfClaimsPrincipalDoesNotExist">false</Item>
      </Metadata>
      <IncludeInSso>false</IncludeInSso>
      <InputClaimsTransformations>
        <InputClaimsTransformation ReferenceId="CreateOtherMailsFromEmailFromADAccount" />
      </InputClaimsTransformations>
      <InputClaims>
         <InputClaim ClaimTypeReferenceId="email" PartnerClaimType="signInNames.emailAddress" Required="true" />
      </InputClaims>
      <PersistedClaims>
        <PersistedClaim ClaimTypeReferenceId="displayName" PartnerClaimType="displayName" />
        <PersistedClaim ClaimTypeReferenceId="objectId" />
        <PersistedClaim ClaimTypeReferenceId="otherMails" />
        
        <PersistedClaim ClaimTypeReferenceId="userPrincipalName" />
      </PersistedClaims>
      <OutputClaims>
        <OutputClaim ClaimTypeReferenceId="objectId" />
        <!-- Optional claims -->
        <OutputClaim ClaimTypeReferenceId="userPrincipalName" />
        <OutputClaim ClaimTypeReferenceId="displayName" />
        <OutputClaim ClaimTypeReferenceId="otherMails" />
      </OutputClaims>
      <IncludeTechnicalProfile ReferenceId="AAD-Common" />
    </TechnicalProfile>

but when I am searching with email I am getting below error in app insight log:

"Statebag": {
    "PROT": {
      "c": "2021-07-13T08:10:25.3600788Z",
      "k": "PROT",
      "v": "AAD Request to https://graph.windows.net/494db189-1a11-4de4-a4d0-7ba7003b4fbd/users?api-version=1.6-integrationOnly&%24filter=logonIdentifiers%2fany(x%3ax%2fvalue+eq+%27Prashant.Kumar%40gmail.com%27) using method GET as request body is malformed.\r\nResponse: \n{\"odata.metadata\":\"https://graph.windows.net/494db189-1a11-4de4-a4d0-7ba7003b4fbd/$metadata#directoryObjects\",\"value\":[]}\r\n",
      "p": false
    }

Why its giving malformed request, am I doing something wrong in policy file? any suggestions?

  • Did you manage to fix it ? I am getting the same error now. It was working until yesterday but now none of the users can login. – Venkata Dorisala Dec 10 '21 at 23:21
  • @Venky Sorry for late reply. I just saw your comment. No, ultimately we had to migrate all users manually and remove all duplicate users from DB. It was long and painful activity. Initially we had a call with Microsoft support and they also could not help us so we went ahead with manual way. – Prashant Kumar Dec 08 '22 at 12:22
  • I am having the same problem. bump? – Karl Merecido Jul 06 '23 at 21:09

2 Answers2

0

I had the same error when tried to setup account linking. And figured out I forgot to register extension attribute 'haspassword'.

Check prerequsities: https://github.com/azure-ad-b2c/samples/blob/master/policies/auto-account-linking/readme.md#prerequisites

Prerequsities contain link how to define custom attribute: https://learn.microsoft.com/en-us/azure/active-directory-b2c/user-flow-custom-attributes?pivots=b2c-custom-policy#modify-your-custom-policy-to-add-the-applicationobjectid

In short:

  1. create new custom attribute in your AD B2C tenant
  2. your AD B2C tenant has built-in app 'b2c-extensions-app' (you will see it in App registrations) - use 'Application (client) ID' and 'Object ID' of this app in 'AAD-Common' technical profile.
<!-- 
<ClaimsProviders> -->
  <ClaimsProvider>
    <DisplayName>Azure Active Directory</DisplayName>
    <TechnicalProfiles>
      <TechnicalProfile Id="AAD-Common">
        <Metadata>
          <!--Insert b2c-extensions-app application ID here, for example: 11111111-1111-1111-1111-111111111111-->  
          <Item Key="ClientId"></Item>
          <!--Insert b2c-extensions-app application ObjectId here, for example: 22222222-2222-2222-2222-222222222222-->
          <Item Key="ApplicationObjectId"></Item>
        </Metadata>
      </TechnicalProfile>
    </TechnicalProfiles> 
  </ClaimsProvider>
<!-- 
</ClaimsProviders> -->
-1

Although your request URL seems to be well-formatted as per Azure AD Graph API requirements, there is -integrationOnly value appended to the {api-version} which can only be one of the following values:

  • "beta"
  • "1.6"
  • "1.5"
  • "2013/11/08"
  • "2013/04/05"

which invalidates the request URL. Remove it and try again.

One other possible cause is spaces in the URL. Spaces in the query string should be URL-encoded before sending a request.

For example, your query string,

https://graph.windows.net/494db189-1a11-4de4-a4d0-7ba7003b4fbd/users?$filter=logonIdentifiers/any(x:x/value eq 'Prashant.Kumar@gmail.com')&api-version=1.6

should be URL encoded as:

https://graph.windows.net/494db189-1a11-4de4-a4d0-7ba7003b4fbd/users?$filter=logonIdentifiers/any(x:x/value%20eq%20'Prashant.Kumar%40gmail.com')&api-version=1.6

Although this is already done as in your error message, it is worth noting since it is mentioned at the bottom of the Azure AD Graph API Supported queries, filters, and paging options page.

Finally, as a side note, Microsoft recommends that you migrate your apps to the Microsoft Graph API since Azure AD Graph is deprecated but won't be retired until the end of year 2022.

Read more about Graph API Version {api-version}

ViajanDee
  • 654
  • 4
  • 15
  • This does not answer the question, the ADB2C policy creates the request to the API, and there is no control over that generated URL – Armand Jul 28 '22 at 05:39
  • I'm aiming with my answer to troubleshoot and see if it works with the public API. IntegrationOnly is Microsoft's backend API and if returned an error while the public one doesn't, there is a way around it. So, if a GET request to the public API (1.6) worked you will have to add a custom attribute declaring it as an extension instead of using the built-in ones. That's one way to control your request. URL-encoding, Microsoft argues you to handle this correctly, refer to the links provided. As a courtesy, genuine answer attempts shouldn't be marked not useful respecting people's time and effort. – ViajanDee Jul 28 '22 at 07:56