Find Active Directory User Info with the PowerShell Provider

Find Active Directory User Info with the PowerShell Provider

  • Comments 9
  • Likes

Summary: Microsoft Scripting Guy, Ed Wilson, talks about how to use the Windows PowerShell provider to find user information in Active Directory.

Hey, Scripting Guy! Question Hey, Scripting Guy! I often need to find information in Active Directory, but I do not like having to write LDAP queries. To me, it is soooo last century—I mean, Fred Flintstone used to write LDAP queries. I love the way that...

—CH

Hey, Scripting Guy! Answer Hello CH,

Microsoft Scripting Guy, Ed Wilson, is here. CH, I know what you mean. I loved my first computer, but I have no desire to go back to using the CPM operating system. Luckily, with the Active Directory module provider, I have direct access to an AD: drive. This makes it easy to use Windows PowerShell to explore. Because of the Active Directory module provider, and the way that Windows PowerShell providers work, I need no special Active Directory Domain Services (AD DS) knowledge. In fact, I can use the same commands that I would use if I was exploring the file system, the registry, the environmental variables, or even the variable drive. Windows PowerShell abstracts the underlying data and permits me to use a file system analogy to work with the data.

Note   This is the second in a series of blogs about working with the Active Directory module provider. You should definitely read Playing with the AD: Drive for Fun and Profit prior to reading today’s blog because I am going to build on everything that went before.

Filtering by using the Where-Object cmdlet

The cool thing about the AD: drive is the ability to use standard Windows PowerShell cmdlets to find and to filter the AD DS data. In the example that follows, I import the Active Directory module, create a Windows PowerShell drive that exposes Charlotte organizational unit (OU) information, and filter out only the users from the OU. The commands is shown here (ipmo is an alias for Import-Module, sl is an alias for Set-Location, dir is an alias for Get-Childitem, and ? is an alias for Where-Object).

ipmo activedirectory

New-PSDrive -PSProvider activedirectory -Name charlotte -Root "AD:\ou=Charlotte,DC=Iammred,DC=net"

sl charlotte:

dir

dir | ? objectclass -eq user

The commands and the output associated with the commands are shown in the image that follows.

Image of command output

Finding a specific user

To find a specific user, I again use Where-Object. I have a couple of choices to use when filtering for the contact. I can use the Name property or the DistinguishedName property. Because the Name property is shorter and requires less typing, I use that one as shown here.

PS charlotte:\> dir | ? name -match 'ed wilson'

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 CN=ed wilson,OU=Charlotte,DC=iammred,DC...

If I would like to directly access the user object instead of filtering to find the user object, I need to use the DistinguishedName attribute. But it is not as bad as it might sound. This is because the DistinguishedName property becomes the path to the object.

I discovered this when I tried to use Get-Item to access the user object. Normally, a property such as Name would what I would expect to use to find an object. In fact, that is what I did in my Where-Object command–I filtered on a value for the Name attribute. When I use the name of the user in my Get-Item command to retrieve a user, an error message appears. This command and the message are shown here.

PS charlotte:\> Get-Item 'ed wilson'

Get-Item : Cannot find path 'charlotte:\ed wilson' because it does not exist.

At line:1 char:1

+ Get-Item 'ed wilson'

+ ~~~~~~~~~~~~~~~~~~~~

    + CategoryInfo          : ObjectNotFound: (charlotte:\ed wilson:String) [Get-Item], ItemNotFoundException

    + FullyQualifiedErrorId : PathNotFound,Microsoft.PowerShell.Commands.GetItemCommand

Note that the error message is ObjectNotFound, and the FullyQualifiedErrorId is PathNotFound. Therefore, Get-Item is attempting to look for a path to an object and is not finding it. In fact, whenever I use Get-Item, I must specify a path to the object. For example, if I want to retrieve a log file, I specify the path. This is shown here.

PS C:\> Get-Item C:\fso\20110314.log

If I am already in the C:\fso folder, a period can be used to take the place of the C:\fso portion of the path—but still, I must specify a path. This is shown here.

PS C:\fso> get-item .\20110314.log

If I think of OU=Charlotte, DC=Iammred, and DC=NET as folders (or directories), the file system analogy works. The DistinguishedName attribute is the full path to the object. Therefore, if I am in the OU=Charlotte folder, I only need to specify the last portion of the DistinguishedName attribute. This technique is shown here.

PS charlotte:\> Get-Item .\'cn=ed wilson'

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 cn=ed wilson,ou=Charlotte,DC=Iammred,DC...

Luckily, the Active Directory module provider does not require the .\—therefore, I can drop it as shown in this example.

PS charlotte:\> Get-Item 'cn=ed wilson'

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 cn=ed wilson,ou=Charlotte,DC=Iammred,DC...

Filtering directly by using Get-Item

Because the Get-Item cmdlet supports the use of the Filter parameter, I can easily create a filter to find a specific user. All I need to do is to specify a value for the Name attribute and use a wildcard character for the path. This technique is shown here when I am on the Charlotte Windows PowerShell drive.

PS charlotte:\> Get-Item -Filter "name=ed wilson" -Path *

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 CN=ed wilson,ou=Charlotte,DC=Iammred,DC...

The cool thing is that I can even filter for properties not normally returned. So for example, I can find users who have a city value of Charlotte (the lowercase L is the LDAP attribute). This technique is shown here.

PS charlotte:\> Get-Item -Filter "l=charlotte" -Path *

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 CN=ed wilson,ou=Charlotte,DC=Iammred,DC...

Teresa Wilson        user                 CN=Teresa Wilson,ou=Charlotte,DC=Iammre...

Performing a recursive search by using Get-ChildItem

Perhaps I want to search for users that have a city value of Charlotte, but I do not know in which OU they reside. To do this, I can use the Get-ChildItem cmdlet and use the Recurse parameter.

PS AD:\dc=iammred,dc=net> Get-ChildItem -Filter "l=charlotte" -Path * -Recurse

 

Name                 ObjectClass          DistinguishedName

----                 -----------          -----------------

ed wilson            user                 CN=ed wilson,OU=Charlotte,dc=iammred,dc...

Teresa Wilson        user                 CN=Teresa Wilson,OU=Charlotte,dc=iammre...

MyNewUser            user                 CN=MyNewUser,OU=MyTestOU,dc=iammred,dc=net

CH, that is all there is to using the Active Directory module provider in Windows PowerShell to find user information. Active Directory Week will continue tomorrow when I will talk about finding and modifying user information.

I invite you to follow me on Twitter and Facebook. If you have any questions, send email to me at scripter@microsoft.com, or post your questions on the Official Scripting Guys Forum. See you tomorrow. Until then, peace.

Ed Wilson, Microsoft Scripting Guy 

Your comment has been posted.   Close
Thank you, your comment requires moderation so it may take a while to appear.   Close
Leave a Comment
  • Good info.

  • That is useful, but how would I get just the OU a user is in so I can pipe it to elsewhere in a script?

    I am trying to make a script that places new users in the same OU as their manager, but I can't figure out how to get that info -_-

  • how to check if I can enumerate an AD object property, usually if I don't access no error code is generated

  • Lars Panzerbjørn: try this

    $User="SamTheMan"

    $Dom="Company.com"

    $root=[ADSI]"LDAP://$Dom/DC=Company,DC=com"

    $search = [System.DirectoryServices.DirectorySearcher]$root

    $search.Filter = "(SAMACCOUNTNAME=$User)"

    $result1 = $search.FindOne()  

    $useADSI= [adsi]$result1.path

    $UserDN=[string]$useADSI.distinguishedName

    $USERCN=[string]$useADSI.cn

    $thestring=[string]"CN=$USERCN,"

    $arr= $UserDN -split $thestring

    $OU=$arr[1]

  • @samtheman

    Instead of using older and more error proneVBScript methods try using PowerShell native techniques.  Thisis easier andmuch more powerful.

    $accountid="SamTheMan"

    $searcher=[adsisearcher]"(samaccountname=$accountid)"

    $user = ($searcher.FindOne()).GetDirectoryEntry()

    $UserDN=$user.distinguishedName[0]

    $USERCN=$user.cn[0]

    $ou=$User.Parent

  • @Lars

    The OU of any object is the "parent" property.  Of course it may also be a "container" or a "folder" or an object.  FOr most users it is an OU unless they are in "User" which is not an OU.

  • Also:

    $user.PSBase.Parent

    $user.Parent

  • for more info about manipulating AD objects try this

    $ADSIObject.PSBase | gm

  • Please provide script ti list whole active users list in Active diractory