powershellloopsforeachactive-directory-groupmembers

List all Sub-Groups (members) of Groups in Active Directory - Powershell


I'd like to get help to create simple script. All it has to do is list sub-groups of groups, it shouldn't be even recursive and formatting for now is not that important.

I created script, but all it does, it writes lines with GROUP=$group but not sub-groups. It should write:

GROUP=$group 
subgroup 
subgroup 
GROUP=$group 
subgroup

...and so on.

Get-ADGroup -filter * -properties GroupCategory | FORMAT-Table -property name -hidetableheaders | Out-File -FilePath "D:\groups_list.txt"
$sourcepath = "D:\groups_list.txt"
$path = "D:\groups.txt"
foreach ($group in get-content $sourcepath) {
Out-File -FilePath $path -InputObject "GROUP= $group" -Append
Get-ADGroupMember $group | FORMAT-Table -property name -hidetableheaders | Out-File -FilePath $path -Append
}

If I do script without loop then everything is fine so I think there is some problem in loop which I don't know how to fix.

$group = "DEPARTMENT_Finance"
Out-File -FilePath $path -InputObject "GROUP= $group" -Append
Get-ADGroupMember $group | FORMAT-Table -property name -hidetableheaders | Out-File -FilePath $path -Append

Where is the mistake in the loop?


Solution

  • To add on to what @TheMadTechnician says, you should be using select (or select-object) instead of Format-Table in both the Get-ADGroup pipeline and the Get-AdGroupMember pipeline. When you are writing the list of groups to file, Format-Table inludes tons of whitespace at the end of each line. It is formatting a table, so even though you are only using a single column, that column will be as wide as the longest group name, using whitespace as filler to keep columns nice and orderly.

    Essentially, when you are reading the list of groups back in, instead of getting "DEPARTMENT_Finance" you are getting "DEPARTMENT_Finance "

    Get-AdGroupMember doesn't know to trim the whitespace.

    Do something like this:

    Get-ADGroup -filter * -properties GroupCategory | Select-Object -ExpandProperty name | Out-File -FilePath "D:\groups_list.txt"
    $sourcepath = "D:\groups_list.txt"
    $path = "D:\groups.txt"
    foreach ($group in get-content $sourcepath) {
        Out-File -FilePath $path -InputObject "GROUP= $group" -Append
        Get-ADGroupMember $group | Select-Object -ExpandProperty name | Out-File -FilePath $path -Append
    }
    

    Since you said you want to only list sub-groups, you might want to add a Where-Object to the Get-AdGroupMember pipeline to limit the output to only group objects, like so:

    Get-ADGroupMember $group | Where-Object objectClass -eq "group" | Select-Object -ExpandProperty name | Out-File -FilePath $path -Append