Powershell error...

Duchemin, Dominique 2,006 Reputation points
2021-05-02T20:59:29.61+00:00

Hello,

I am trying to use the powershell script from https://social.technet.microsoft.com/Forums/windows/en-US/be8f23bb-ab2d-486c-b6c0-e35bb312ed06/get-a-list-of-all-local-admins-on-computers-in-a-specific-ou-in-adds

Blockquote

Import-Module ActiveDirectory
$Searcher = New-Object DirectoryServices.DirectorySearcher([ADSI]"")
$Searcher.SearchRoot = 'LDAP://OU=Servers,DC=ad'
$Searcher.Filter = "(objectClass=computer)
"$Computers = ($Searcher.Findall())

$Results = @()
md C:\All_Local_Admins

Foreach ($Computer in $Computers){
$Path=$Computer.Path
$Name=([ADSI]"$Path").Name
write-host $Name
$members =[ADSI]"WinNT://$Name/Administrators"
$members = @($members.psbase.Invoke("Members"))
$members | foreach {
$LocalAdmins = $.GetType().InvokeMember("Name", 'GetProperty', $null, $, $null) # Create a new object for the purpose of exporting as a CSV
$pubObject = new-object PSObject
$pubObject | add-member -membertype NoteProperty -name "Server" -Value $Name
$pubObject | add-member -membertype NoteProperty -name "Administrators" -Value $LocalAdmins

Append this iteration of our for loop to our results array.

$Results += $pubObject
}
}

$Results | Export-Csv -Path "C:\All_Local_Admins\ServerLocalAdmins.csv" -NoTypeInformation
$Results = $Null

Blockquote

but I am getting an error:

Blockquote

VOPCCOP002
Exception calling "Invoke" with "2" argument(s): "The network path was not found.
"
At line:15 char:2

  • $members = @($members.psbase.Invoke("Members"))
  • ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  • CategoryInfo : NotSpecified: (:) [], MethodInvocationException
  • FullyQualifiedErrorId : DotNetMethodException

The following exception occurred while retrieving member "GetType": "The network path was not found.
"
At line:17 char:3

  • $LocalAdmins = $_.GetType().InvokeMember("Name", 'GetProperty ...
  • ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  • CategoryInfo : NotSpecified: (:) [], ExtendedTypeSystemException
  • FullyQualifiedErrorId : CatchFromBaseGetMember

Blockquote

Any idea?
Thanks,
Dom

Windows for business Windows Server User experience PowerShell
0 comments No comments
{count} votes

10 answers

Sort by: Most helpful
  1. Anonymous
    2021-05-03T05:58:06.953+00:00

    Hi,

    You can add try/catch blocks to check which computer is not found.

    try{  
        $members = @($members.psbase.Invoke("Members"))  
    }  
    catch{  
        write-host "$name is not found"  
    }  
    

    Since the type of $name is System.DirectoryServices.PropertyValueCollection, it cannot be stored in a csv file. You can convert it to string like this.

    [string]$Name=([ADSI]"$Path").Name  
    

    Best Regards,
    Ian Xue

    ============================================

    If the Answer is helpful, please click "Accept Answer" and upvote it.
    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.

    1 person found this answer helpful.
    0 comments No comments

  2. Anonymous
    2021-05-04T08:20:07.73+00:00

    Hi,

    The try/catch blocks can be added to the line $members = @($members.psbase.Invoke("Members")). To get the users in the nested groups you can use a recursive function like below

    function GetGroupUser{  
        param(  
            [Parameter(Mandatory=$true)]$group  
        )  
        Get-ADGroupMember -Identity $group | ForEach-Object {  
            if($_.objectClass -eq "group"){  
                GetGroupUser $_  
            }  
            else{  
                $_  
            }  
        }  
    }  
      
    $Searcher = New-Object DirectoryServices.DirectorySearcher([ADSI]"")  
    $Searcher.SearchRoot = 'LDAP://CN=Computers,DC=contoso,DC=com'  
    $Searcher.Filter = "(objectClass=computer)"  
    $Computers = ($Searcher.Findall())  
      
    $Results = @()  
    md C:\All_Local_Admins  
      
    Foreach ($Computer in $Computers){  
        $Path=$Computer.Path  
        [string]$Name=([ADSI]"$Path").Name  
        write-host $Name  
        $members =[ADSI]"WinNT://$Name/Administrators"  
        try{  
            $members = @($members.psbase.Invoke("Members"))  
        }  
        catch{  
            Write-Host "$name is not found"  
        }  
        $members | foreach {  
            $LocalAdmins = $_.GetType().InvokeMember("Name", 'GetProperty', $null, $_, $null)    # Create a new object for the purpose of exporting as a CSV  
            $Class = $_.GetType().InvokeMember("Class", 'GetProperty', $null, $_, $null)  
            $pubObject = new-object PSObject  
            $pubObject | add-member -membertype NoteProperty -name "Server" -Value $Name  
            $pubObject | add-member -membertype NoteProperty -name "Administrators" -Value $LocalAdmins  
            $pubObject | add-Member -membertype NoteProperty -name "Class" -Value $Class  
      
            # Find out if this is a user or group object  
            if ($Class -like "User"){  
                $Type = "User"  
                $DisplayName = Get-ADUser -Identity $LocalAdmins | Select -ExpandProperty Name  
                $pubObject | add-Member -membertype NoteProperty -name "Display Name" -Value $DisplayName  
            }  
            else {  
                $Type = "Group"  
                $DisplayName = GetGroupUser $LocalAdmins | Select -ExpandProperty name  
                $pubObject | add-Member -membertype NoteProperty -name "Display Name" -Value $DisplayName  
            }  
              
            # Append this iteration of our for loop to our results array.  
            $Results += $pubObject  
        }  
    }  
    

    Best Regards,
    Ian Xue

    ============================================

    If the Answer is helpful, please click "Accept Answer" and upvote it.
    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.

    1 person found this answer helpful.
    0 comments No comments

  3. Anonymous
    2021-05-05T09:17:36.1+00:00

    Hi,

    You can check if it's a local account like this.

    function GetGroupUser{  
        param(  
            [Parameter(Mandatory=$true)]$group  
        )  
        Get-ADGroupMember -Identity $group | ForEach-Object {  
            if($_.objectClass -eq "group"){  
                GetGroupUser $_  
            }  
            else{  
                $_  
            }  
        }  
    }  
      
    $Searcher = New-Object DirectoryServices.DirectorySearcher([ADSI]"")  
    $Searcher.SearchRoot = 'LDAP://CN=Computers,DC=contoso,DC=com'  
    $Searcher.Filter = "(objectClass=computer)"  
    $Computers = ($Searcher.Findall())  
      
    $Results = @()  
    md C:\All_Local_Admins  
      
    Foreach ($Computer in $Computers){  
        $Path=$Computer.Path  
        [string]$Name=([ADSI]"$Path").Name  
        write-host $Name  
        $members =[ADSI]"WinNT://$Name/Administrators"  
        try{  
            $members = @($members.psbase.Invoke("Members"))  
        }  
        catch{  
            Write-Host "$name is not found"  
        }  
        $members | foreach {  
            $LocalAdmins = $_.GetType().InvokeMember("Name", 'GetProperty', $null, $_, $null)    # Create a new object for the purpose of exporting as a CSV  
            $Class = $_.GetType().InvokeMember("Class", 'GetProperty', $null, $_, $null)  
            $pubObject = new-object PSObject  
            $pubObject | add-member -membertype NoteProperty -name "Server" -Value $Name  
            $pubObject | add-member -membertype NoteProperty -name "Administrators" -Value $LocalAdmins  
            $pubObject | add-Member -membertype NoteProperty -name "Class" -Value $Class  
      
            # Find out if this is a user or group object  
            if ($Class -like "User"){  
                $Type = "User"  
                $aduser = Get-ADuser -Filter {name -eq $LocalAdmins}  
                if($aduser){  
                    $DisplayName = $aduser.Name  
                }  
                else{  
                    $DisplayName = "Local Account $LocalAdmins"  
                }  
                $pubObject | add-Member -membertype NoteProperty -name "Display Name" -Value $DisplayName  
            }  
            else {  
                $Type = "Group"  
                $DisplayName = GetGroupUser $LocalAdmins | Select -ExpandProperty name  
                $pubObject | add-Member -membertype NoteProperty -name "Display Name" -Value $DisplayName  
            }  
              
            # Append this iteration of our for loop to our results array.  
            $Results += $pubObject  
        }  
    }  
    

    For the AD issue you can start a new thread with the tag "windows-active-directory". Sorry I'm no expert in AD.

    Best Regards,
    Ian Xue

    ============================================

    If the Answer is helpful, please click "Accept Answer" and upvote it.
    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.

    1 person found this answer helpful.
    0 comments No comments

  4. Anonymous
    2021-05-07T04:09:31.677+00:00

    Hi,

    Please check the sequence of the groups called in the recursive function. Are there any duplicated ones?

    function GetGroupUser{  
        param(  
            [Parameter(Mandatory=$true)]$group  
        )  
        Get-ADGroupMember -Identity $group | ForEach-Object {  
            if($_.objectClass -eq "group"){  
                Write-Host $_  
                GetGroupUser $_  
            }  
            else{  
                $_  
            }  
        }  
    }  
    

    Best Regards,
    Ian Xue

    ============================================

    If the Answer is helpful, please click "Accept Answer" and upvote it.
    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.

    1 person found this answer helpful.
    0 comments No comments

  5. Duchemin, Dominique 2,006 Reputation points
    2021-05-03T00:27:12.71+00:00

    Hello,

    Now even with the error which is skipping a lot of machines I have some results:

    Blockquote

    "Server","Administrators"
    "System.DirectoryServices.PropertyValueCollection","Administrator"
    "System.DirectoryServices.PropertyValueCollection","Administrator"
    "System.DirectoryServices.PropertyValueCollection","Domain Admins"
    "System.DirectoryServices.PropertyValueCollection","MCCS Server Staff Admin"
    "System.DirectoryServices.PropertyValueCollection","MITS Server Service Accounts"
    "System.DirectoryServices.PropertyValueCollection","svcentrfax"
    "System.DirectoryServices.PropertyValueCollection","ISS Mobility "
    "System.DirectoryServices.PropertyValueCollection","Administrator"
    "System.DirectoryServices.PropertyValueCollection","MITS Server "
    "System.DirectoryServices.PropertyValueCollection","MCCS Server "
    "System.DirectoryServices.PropertyValueCollection","ISS Admins"
    "System.DirectoryServices.PropertyValueCollection","Domain Admins

    Blockquote

    As you can see I do not get the server name!!! ... why?
    Also I would like to get the user accounts and not the group name (MITS Server) contains several accounts it is what I will need..

    Thanks,
    DOm

    0 comments No comments

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.