Filtering the transitive group memberships of a user using Graph SDK

1.4k Views Asked by At

I am trying to use the MS Graph SDK (beta) for C# to get all the groups a user belongs to transitively with a filter to only get "security groups".

My code looks like this:

var upn = "[email protected]";
 
var request = await _graphClient.Users[upn].TransitiveMemberOf
    .Request()
    .Filter("securityEnabled eq true")
    .GetAsync();

When I run this code, I get an error that The specified filter to the reference property query is currently not supported. I know that the same API endpoint can be called successfully using Postman with the same filter so I assume I'm missing something in my C# code?

2

There are 2 best solutions below

0
On BEST ANSWER

Please use the below code for filtering the securityEnabled in c# using graph sdk

try
        {
            

            List<Option> requestOptions = new List<Option>();

            requestOptions.Add(new QueryOption("$count", "true"));

        

            var request = await graphClient.Users["[email protected]"].TransitiveMemberOf
                .Request(requestOptions).Header("ConsistencyLevel", "eventual")
                .Filter("securityEnabled eq true")
                .GetAsync();

            Console.WriteLine(JsonConvert.SerializeObject(request));
        }
        catch(Exception e)
        {
            Console.WriteLine(e.Message);
        }
1
On

Thanks to Sruthi's answer, I was able to get user transitive memberships. Obviously, this can often result in a huge list and the Graph API will only provide you a paginated response so you have to cycle through every page to get everything.

This is what the code looks like now:

public async Task<List<Group>> ListTransitiveGroupMembershipsOfUserAsync(string upn)
        {
            var requestOptions = new List<Option>
            {
                new QueryOption("$count", "true")
            };

            var directoryObjects = new List<DirectoryObject>();

            var request = await _graphClient.Users[upn].TransitiveMemberOf
                .Request(requestOptions).Header("ConsistencyLevel", "eventual")
                .Filter("securityEnabled eq true")
                .GetAsync();

            directoryObjects.AddRange(request.CurrentPage);

            while (request.NextPageRequest != null)
            {
                var currentHeaders = request.NextPageRequest.Headers;
                IUserTransitiveMemberOfCollectionWithReferencesPage newPage;

                if (!currentHeaders.Any())
                    request = await request.NextPageRequest.Header("ConsistencyLevel", "eventual").GetAsync();
                else
                    request = await request.NextPageRequest.GetAsync();

                directoryObjects.AddRange(request.CurrentPage);
            }

            return directoryObjects.Cast<Group>().ToList();
        }

Initially, my code failed when it tried to get the results for page 2 onwards because it kept appending eventual to the ConsistencyLevel header. So when sending the HTTP request for page 2, the header was like: ConsistencyLevel: eventual, eventual or ConsistencyLevel: eventual, eventual, eventual for page 3 and so on so forth.

To get around this, I added the little if (!currentHeaders.Any()) block to only add the ConsistencyLevel header if it doesn't already exist.

Hopefully that'll help anyone else who gets caught out by cycling through paginated responses!.