powershellforeachpowershell-remotingget-aduser

Variable not defined when trying to list a group of AD user from a CSV using Get-ADUser -Filter {displayName


I am using the below code to try and pull out a list of last logon times for a group of users contained in a CSV file. I have a test domain at home and the script below works fine. However, when I try it on my work prod AD I get the following error.

Get-ADUser: Variable: 'dname' found in expression: $dname is not defined.

This is the script I have put together.

$list = Import-Csv -Path "C:\data\PowerShell\UserInfo.csv"

ForEach ($user in $list) {
    $dname = $user.Displayname
    Get-ADUser -Filter {displayName -eq $dname} -Properties lastLogon | Select-Object Name, SamAccountName, @{Name="LastLogon"; Expression={[DateTime]::FromFileTime($_.lastLogon)}} | Export-CSV -Path "C:\data\PowerShell\user_last_login.csv" -append -NoTypeInformation
    }

Solution

  • tl;dr

    For the reasons explained in the next section, your Get-ADUser proxy command[1] doesn't see your local variables inside a -Filter argument. Therefore, use string interpolation instead, so as to directly incorporate the variable value into the -Filter argument (note the need to use embedded double-quoting (`")around the expanded value):

    Get-ADUser -Filter "displayName -eq `"$dname`"" -Properties lastLogon
    

    As an aside:


    Background information: The limitations of implicit remoting:

    Your symptom implies that your Active Directory commands are provided via implicit remoting, where a local proxy module is used to relay calls to a remote machine behind the scenes using PowerShell's remoting feature (the proxy modules are typically created with the Export-PSSession cmdlet; this article provides an introduction to implicit remoting).

    In a nutshell, the proxy module contains proxy commands of the same name as their remote counterparts, implemented as PowerShell functions that relay the calls to their remote counterparts.[1]

    While this proxying mostly works as intended, it has side effects:


    [1] Given that Get-ADUser is normally a binary cmdlet, an easy way to test if a given Get-ADUser command is a proxy command is to use (Get-Command Get-ADUser).CommandType -eq 'Function'.