Public/Get-sysLocalGroupMember.ps1
<#
.SYNOPSIS This function grabs local groups along with their members (if any) from local or remote computers. .DESCRIPTION This function uses Win32_Group and Win32_GroupUser to grab local groups and their members form local and remote computers. .EXAMPLE PS C:\> Get-sysLocalGroupMember -GroupName "Remote Desktop Users","RDS Remote Access Servers" GroupName Member ComputerName --------- ------ ------------ Remote Desktop Users {Everyone, mrpig} DC01 RDS Remote Access Servers DC01 This examples grabs the group and members of 2 groups specified with the GroupName parameter from the local computer. .EXAMPLE PS C:\>Get-sysLocalGroupMember -IncludeGroupsWithMembersOnly GroupName Member --------- ------ Pre-Windows 2000 Compatible Access {Authenticated Users} Windows Authorization Access Group {ENTERPRISE DOMAIN CONTROLLERS} Administrators {Administrator, Enterprise Admins, Domain Admins} Users {INTERACTIVE, Authenticated Users, Domain Users} Guests {Guest, Domain Guests} Remote Desktop Users {Everyone, mrpig} IIS_IUSRS {IUSR} Denied RODC Password Replication Group {krbtgt, Domain Controllers, Schema Admins, Enterprise Admins, Cert Publisher... This example grabs all groups from the local computer if they have any members and ignores the one's with no members. .EXAMPLE PS C:\>Get-sysLocalGroupMember -ComputerName $ENV:COMPUTERNAME,pancake-3 -Protocol Dcom -GroupName "Remote Desktop Users" -OutVariable groups GroupName Member ComputerName --------- ------ ------------ Remote Desktop Users {Everyone, mrpig} DC01 Remote Desktop Users {mrpig, mrpig} pancake-3 PS C:\>$groups[1].Member Name Domain MemberType ---- ------ ---------- mrpig CLEVELAND UserAccount mrpig PANCAKE-3 UserAccount This example grabs members of the "Remote Desktop Users" group from both dc01 and pancake-3 and uses the Dcom protocol since pancake-3 does not have WsMan enabled. It then stores the results into the groups variable. The second command expands the Member property of pancake-3 LocalGroup object to get more info about each group member. .INPUTS Inputs (if any) .OUTPUTS [SysAdminTools.LocalGroupMember] .NOTES GroupName has tab completetion, but it only grabs the local groups from the local computer and not remote ones, but generally they should be the same. #> function Get-sysLocalGroupMember{ [CmdletBinding()] param( [Parameter(ValueFromPipelineByPropertyName,ValueFromPipeline)] [string[]]$ComputerName = $ENV:COMPUTERNAME, [ArgumentCompleter({ param($commandName, $parameterName, $wordToComplete, $commandAst, $fakeBoundParameter) Get-CimInstance -ClassName Win32_Group -Filter "LocalAccount=True AND Name LIKE `"%$WordToComplete%`"" | where Name -notin $fakeBoundParameter.GroupName | foreach { $ToolTip = $_ | Format-List Name,Description,Caption | Out-String [System.Management.Automation.CompletionResult]::new("`"$($_.Name)`"","$($_.Name)","ParameterValue",$ToolTip) } })] [Parameter(ValueFromPipeline)] [string[]]$GroupName, [switch]$IncludeGroupsWithMembersOnly, [Parameter()] [ValidateSet("WsMan", "Dcom")] [string]$Protocol = "WsMan" ) Begin{ if ($PSBoundParameters.ContainsKey("GroupName")){ $GroupNameFilter = "AND (Name=`"$($GroupName[0])`"" foreach ($name in ($GroupName | select -Skip 1)){ $GroupNameFilter += " OR Name=`"$name`"" } $GroupNameFilter += ")" } } #Begin Process{ foreach ($computer in $ComputerName){ try{ $Session = New-CimConnection -ComputerName $computer -Protocol $Protocol -ErrorAction Stop $Groups = Get-CimInstance -CimSession $Session -ClassName Win32_Group -Filter "LocalAccount=True $GroupNameFilter" foreach ($group in $Groups){ $GroupComponent = Get-CimInstance -CimSession $Session -ClassName Win32_GroupUser -Filter "GroupComponent=""Win32_Group.Domain='$computer',Name='$($group.Name)'""" if ($IncludeGroupsWithMembersOnly){ if ($GroupComponent -eq $null){ continue } } $Members = foreach ($member in $GroupComponent){ [PSCustomObject]@{ PSTypeName = "SysAdminTools.LocalGroupMember" Name = $member.PartComponent.Name Domain = $member.PartComponent.Domain MemberType = $member.PartComponent.cimclass.cimclassname.split('_')[1] } } [PSCustomObject]@{ PSTypeName = "SysAdminTools.LocalGroup" ComputerName = $computer GroupName = $group.Name Member = $Members Description = $group.Description Domain = $group.Domain Caption = $group.Caption SID = $group.SID SIDType = $group.SIDType LocalAccount = $group.LocalAccount Status = $group.Status } } $Session | Remove-CimSession } catch{ if ($Session){ $Session | Remove-CimSession } $PSCmdlet.WriteError($_) } } #foreach computer } #Process } |