Search code examples
powershellactive-directory

Powershell Expression gives no results


I have created an expression that should return the OU canonical name. A small outline:

@(Search-ADAccount -LockedOut -UsersOnly) | Select-Object Name,SamAccountName,@{Name="OU";Expression={((Get-ADOrganizationalUnit -Identity $($_."DistinguishedName")).CanonicalName)}}

However, this expression returns an empty OU column, the other 2 columns are filled.

My question is what is wrong with this expression? Any feedback is appreciated.

With kind regards, TheStingPilot


Solution

  • The issue with your code is that you're trying to feed Get-ADOrganizationalUnit a user's DistinguishedName instead of an OU's DistinguishedName which is not valid.

    It's also worth mentioning, you're missing -Properties CanonicalName on Get-ADOrganizationalUnit.

    Try this instead:

    $exp = { ($_.DistinguishedName.Split(',', 2)[1] | Get-ADOrganizationalUnit -Properties CanonicalName).CanonicalName }
    Search-ADAccount -LockedOut -UsersOnly |
        Select-Object Name, SamAccountName, @{ N = "OU"; E = $exp }
    

    Now, this syntax using calculated properties with Select-Object above is really hard to read but also very inefficient, it is querying the OUs per every user and there is a very high chance that the same OU will be queried more than once. What I would recommend instead is to cache the OUs in a hashtable with key = the OU DN and value = the OU CanonicalName.

    This is much better:

    $cache = @{}
    Search-ADAccount -LockedOut -UsersOnly | ForEach-Object {
        $ouDN = $_.DistinguishedName.Split(',', 2)[1]
    
        if (-not $cache.ContainsKey($ouDN)) {
            $ou = $ouDN | Get-ADOrganizationalUnit -Properties CanonicalName
            $cache[$ouDN] = $ou.CanonicalName
        }
    
        [PSCustomObject]@{
            Name           = $_.Name
            SamAccountName = $_.SamAccountName
            OU             = $cache[$ouDN]
        }
    }