Reputation: 65
I need help figuring out the logic for looping through Active Directory security groups to find all members of any nested groups using Get-ADGroupMember. If I use the recursive switch on that cmdlet, it doesn't capture the name of the nested group, just the members. I need to capture everything. I feel like this needs to be done using a while or do/while.
This section of code gets me most of the way there. However, I can't figure out how to prevent it from running the Get-AdGroupMember inside of the while if the objectclass is User. I'm testing with 4 AD groups called "testgroup1", "testgroup2", "testgroup3" and "testgroup4". Testgropus 1,2 and 3 each have a single user as a member. Testgroup2 is a member of Testgroup1. Testgroup3 is a member of Testgroup2. Testgroup4 is a member of Testgroup 3 and it also has 4 users as members.
$groups = Get-ADGroupMember 'testgroup1'
$allGroups =$null
While($groups){
$allGroups += $groups.SamAccountName
$groups = $groups.SamAccountName | Get-ADGroupMember
}
$allGroups
Upvotes: 2
Views: 2600
Reputation: 65
We solved this issue by creating a function that gets the members of an AD group and adds only users to an array. If the object class returns as a group it calls the same function again on that new group and then adds users under it to the same array. Code is below.
function Get-MBusers {
Param (
$Group,
$adserver
)
$users=@()
$members = Get-Adgroup -Identity $Group -Server $adserver -Properties members | Select-Object -ExpandProperty Members | Where-Object {$_ -notmatch "ForeignSecurityPrincipals"} | ForEach-Object {Get-ADObject $_ -Server $adserver}
foreach ($member in $members) {
Write-Debug "$($member.Name)"
$type = Get-ADObject $member -server $ADServer -Properties samAccountname
if ($type.ObjectClass -eq 'user') {
$users += Get-Aduser $type.samaccountname -Server $ADServer
}
# If it's a group
if ($type.ObjectClass -eq 'group') {
Write-Debug "Breaking out group $($type.Name)"
$users += Get-MBUsers $member $adserver
}
}
return $users
}
Upvotes: 1