How to check if email exists in B2C Microsoft Graph API: C# using $filter conditions against different issuer

Rishi Verma 126 Reputation points
2021-02-06T13:20:40.25+00:00

Below is the code I am using at the moment which works fine when I use with one filter condition(any of the below) at a time, but when i combine it with OR condition which is the actual requirement to validate if email already exists against any of the issuer, it throws error and doesn't work.

Is there any way we can concat multiple filter conditions and how to do that?

public async Task\

Microsoft Security Microsoft Entra Microsoft Entra ID
{count} vote

Accepted answer
  1. Rishi Verma 126 Reputation points
    2021-02-08T00:06:47.64+00:00

    Thanks @Dan Kershaw for responding and giving a try to my question. As it was an immediate requirement, all i could think of is to change the approach to achieve this. However I am not satisfied fully as I cant think why Filter would not offer an "OR" operation and just work an "AND" operation. Anyways, the below is a working scenario after code based change to get Users and then filter to match the condition. It is working fine now.

    Posted so that if it could help others in similar approach!!!!! :)

                      public async Task<bool> CheckUserByEmailId(string email, CancellationToken ct)  
                      {    
                        List<User> userResult1 = new List<User>();  
                        List<User> userResult2 = new List<User>();  
                         var graphClient = await GetGraphServiceClientAsync();  
                          var user1 = await graphClient.Users  
                             .Request()  
                     .Filter($"otherMails/any(id:id eq '{email}')")  
                     .Select(e => new  
                     {  
                         e.DisplayName,  
                         e.Id,            
                         e.Identities,  
                         e.PasswordPolicies,  
                         e.PasswordProfile,  
                         e.UserPrincipalName,  
                         e.OtherMails,  
                         e.LastPasswordChangeDateTime,  
                         e.Mail  
                     }  
                     )  
                     .GetAsync();  
    
                        var user2= await graphClient.Users  
                     .Request()  
                     .Filter($"identities/any(c:c/issuerAssignedId eq '{email}' and c/issuer eq '{this._adOptions.Issuer}')")  
                     .Select(e => new  
                     {  
                         e.DisplayName,  
                         e.Id,  
                         e.Identities,  
                         e.PasswordPolicies,  
                         e.PasswordProfile,  
                         e.UserPrincipalName,  
                         e.OtherMails,  
                         e.LastPasswordChangeDateTime,  
                         e.Mail } ).GetAsync();  
    
                         /*Above approach to first get two possible scenarios for user's to be of either federated(facebook   
                          or google issuer) or domain issuer*/  
    
                          /*Code based Filter to get Users based on Email condition*/  
    
                          if(user1.Count==0)  
                           {  
                               userResult1.AddRange(user2);  
                             }  
                              else  
                              userResult1.AddRange(user1);  
    
          // Get Issuer  
            var genIssuer = new List<List<string>>();  
            genIssuer = userResult1.Select(u => u.Identities  
                         .Select(u => u.Issuer).ToList()).ToList();  
            List<string> genIssuerList = new List<string>();  
            genIssuerList = genIssuer[0].ToArray().ToList();  
            string issuer = genIssuerList[0].ToString();  
    
            //Get All emails  
            var genIdentEmail = new List<List<string>>();  
            genIdentEmail = userResult1.Select(u => u.Identities  
                         .Select(u => u.IssuerAssignedId).ToList()).ToList();  
            List<string> genIdentEmailList = new List<string>();  
            genIdentEmailList = genIdentEmail[0].ToArray().ToList();  
            string identEmail = genIdentEmailList[0].ToString();  
            List<string> otherMails = new List<string>();  
            var other = userResult1.Select(e => e.OtherMails).ToList();  
            otherMails = other[0].ToArray().ToList();  
            string otherMail;  
             
            if (otherMails.Count==0)  
                otherMail = "na";              
            else otherMail = otherMails[0].ToString();  
    
    
          if (email==otherMail || email==identEmail)  
            {  
                return true;  
            }  
            else  
            {  
                return false;  
            }  
    

    }

    1 person found this answer helpful.

1 additional answer

Sort by: Most helpful
  1. Dan Kershaw 416 Reputation points Microsoft Employee
    2021-02-07T17:02:03.233+00:00

    This seems like a reasonable scenario and query pattern, but I also can't get this to work. I get:

    {
    "error": {
    "code": "Request_UnsupportedQuery",
    "message": "Complex query on property identities is not supported.",
    "innerError": {
    "date": "2021-02-07T16:52:50",
    "request-id": "5feeba47-b0de-4216-9e23-f580999f4a21",
    "client-request-id": "4e72d4c8-4c9c-a379-e93f-ed04ddbd6fc4"
    }
    }
    }

    Will need to ask the feature team to look at whether this can be supported.

    0 comments No comments

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.