LDAP Filter – Creating an LDAP Filter for Members of a Group

ldappowershell

I'm attempting to run an LDAP filter to return all users within a group. Pretty simple, and there are hundreds of Stack Overflow questions which already provide example queries. However the one I'm using is basic, and returns nothing when run in Powershell.

What I've Tried

Get-ADUser -LDAPFilter "(&(objectclass=user)(objectcategory=person)(memberOf=CN=MyGroup,OU=Users,DC=MyDomain,DC=com))"

I've also tried "CN=Users" instead of "OU=Users

Where "MyGroup" is located in the OU:

"MyDomain" (Forest) > "Users" (OU) > "MyGroup" (CN)

Any ideas what I'm doing wrong, and why none of the 100-200 members of the "MyGroup" are being returned?

Best Answer

The first thing I'd do is double check that the DN of the group you're trying to match is actually correct. I'd usually do something like this:

(Get-ADGroup MyGroup).distinguishedName

# optionally, save it to a variable
$groupDN = (Get-ADGroup MyGroup).distinguishedName

Get-ADUser will limit your results to user objects on its own, so you can leave out the objectclass/objectcategory pieces of the LDAP Filter and just include the memberOf part. You can use the DN variable we set earlier like this:

Get-ADUser -LDAPFilter "(memberOf=$groupDN)"

The important thing to note about this particular query is that it will only return users who are direct members of the group. It will not return nested members. So if one of the group's members is another group, that second group's members won't show up in the results without additional effort. You can get those nested members by tweaking the filter like this:

Get-ADUser -LDAPFilter "(memberOf:1.2.840.113556.1.4.1941:=$groupDN)"

That crazy dotted number in the middle is an OID called LDAP_MATCHING_RULE_IN_CHAIN. From the docs:

The LDAP_MATCHING_RULE_IN_CHAIN is a matching rule OID that is designed to provide a method to look up the ancestry of an object. Many applications using AD and AD LDS usually work with hierarchical data, which is ordered by parent-child relationships. Previously, applications performed transitive group expansion to figure out group membership, which used too much network bandwidth; applications needed to make multiple roundtrips to figure out if an object fell "in the chain" if a link is traversed through to the end.

The other reason your query might not return results is if the user you're running the query as doesn't have read access to some/all of the users for some reason.