ADUserGroup.psm1

<#
.SYNOPSIS
This script fetches the Active Directory groups for all users in a given Organizational Unit (OU), optionally including users in sub-OUs.
 
.DESCRIPTION
The Get-ADUserGroupsFromOU function accepts an OU and a boolean indicating whether to recurse into sub-OUs as parameters. It fetches all users in the given OU (and, if specified, its sub-OUs) and then fetches the Active Directory groups that each user is a member of. It returns an array of custom objects. Each object contains the group's name and category, and the member's name and email address.
 
.PARAMETER OU
The distinguished name of the Organizational Unit. This parameter is required.
 
.PARAMETER Recurse
A boolean indicating whether to recurse into sub-OUs. This parameter is optional and defaults to true.
 
.EXAMPLE
PS C:\> Get-ADUserGroupsFromOU -OU "OU=Sales,DC=Contoso,DC=com" -Recurse $false
 
This will fetch all users in the "Sales" OU (but not its sub-OUs), then fetch the Active Directory groups for each user and return detailed information about each group and its members.
 
#>


function Get-ADUserGroupsFromOU {
    param(
        [string]$OU,
        [bool]$Recurse = $true
    )

    if($Recurse) {
        [string[]]$UserList = (get-aduser -filter * -SearchBase $OU -SearchScope Subtree).SamAccountName
    } else {
        [string[]]$UserList = (get-aduser -filter * -SearchBase $OU -SearchScope OneLevel).SamAccountName
    }    

    if($UserList.Count -gt 0) {
        Return Get-ADUserGroups $UserList
    } else {
        Return Write-Warning "No users from OU returned."
    }    
}

<#
.SYNOPSIS
This script fetches the Active Directory groups for a given user or set of users and returns detailed information about each group and its members, sorted by a specified attribute.
 
.DESCRIPTION
The Get-ADUserGroups function accepts an array of user names and a sort attribute as parameters. If no user names are provided, it will prompt for a user name.
It then fetches the Active Directory groups that each user is a member of and returns an array of custom objects. Each object contains the group's name and category, and the member's name and email address. The returned array is sorted by the specified attribute.
 
.PARAMETER User
An array of user names. If this parameter is not provided, the function will prompt for a user name.
 
.PARAMETER SortBy
A string representing the attribute to sort the returned array by. This parameter is optional. If not provided, the array will be sorted by the group's name.
 
.EXAMPLE
PS C:\> Get-ADUserGroups -SortBy "MemberName"
 
This will prompt for a user name, then fetch the Active Directory groups for that user, sort the results by the member's name, and return detailed information about each group and its members.
 
.EXAMPLE
PS C:\> "John Doe", "Jane Doe" | Get-ADUserGroups -SortBy "GroupName"
 
This will fetch the Active Directory groups for the users named "John Doe" and "Jane Doe", sort the results by the group's name, and return detailed information about each group and its members. In this example, the user names are provided as input to the function.
#>


function Get-ADUserGroups {
    param(
        [string[]]$User,
        [string[]]$SortBy = @("GroupName", "MemberName")
    )

    if($null -eq $User) {
        # Prompt for the user name if it's not provided as a parameter
        $User = Read-Host "Enter the user name"
    }

    if($User.Count -gt 0) {
        $UsersGroups = @()

        foreach($entry in $User) {

            # Initialize an empty array to hold the groups
            $UserGroups = @()

            # Fetch the Active Directory user that matches the provided name
            $UserSearch = Get-ADUser -Filter {anr -like $entry} -Properties samAccountName, EmailAddress

            foreach($UserSearchResult in $UserSearch) {

                # Fetch the Active Directory groups that the user is a member of
                $GroupsQuery = Get-ADPrincipalGroupMembership -Identity $UserSearchResult.samAccountName

                # For each group, create a new object with the group's name and category, and the user's name and email
                foreach ($group in $GroupsQuery) {
                    $UserGroup = New-Object -TypeName PSObject
                    Add-Member -InputObject $UserGroup -MemberType NoteProperty -Name GroupName -Value $group.name
                    Add-Member -InputObject $UserGroup -MemberType NoteProperty -Name GroupCategory -Value $group.GroupCategory
                    Add-Member -InputObject $UserGroup -MemberType NoteProperty -Name MemberName -Value $UserSearchResult.samAccountName
                    Add-Member -InputObject $UserGroup -MemberType NoteProperty -Name MemberEmail -Value $UserSearchResult.EmailAddress

                    # Add the new object to the array of groups
                    $UserGroups += $UserGroup
                }

            }

            $UsersGroups += $UserGroups
        }
    }

    # Return the array of groups
    return $UsersGroups | Sort-Object $SortBy
}