Hey, Scripting Guy! I’ve been playing around with Windows PowerShell, and I find it interesting. However, I have a problem. I’d like to use PowerShell as a quick way to get information about an Active Directory user account, but I can’t figure out how to bind to a user account. Any suggestions?
Hey, BW. As we noted a few days ago, Windows PowerShell is still in beta; although the technology works (and works well), there are still some features missing. Unfortunately, one of those features happens to be a cmdlet that makes it easy to bind to and work with Active Directory objects (similar to what the Get-WMIObject cmdlet does for WMI). When that cmdlet is available, working with Active Directory will be a breeze; until then, well, we’re afraid you’re out of luck. See you later, BW; we’re going outside to enjoy the sunshine.
Um, we’re back. The Scripting Editor has … suggested … that we actually try to help you with your problem instead of just brushing you off and heading outside. Fine; we’ll see if we can figure out a way to use Windows PowerShell to bind to an Active Directory user account. But we’d like to state, for the record, that we’re only doing this because we’re scared of the Scripting Editor. (We’re still amazed that no one has ever dropped a house on her, if you know what we mean.)
Editor’s Note: The Scripting Editor would normally edit out something like that, but she’s decided instead to introduce the Scripting Guys to some flying monkeys. (She thought of sending them some poppies, but they already spend most of their day sleeping.)
If you’ve written VBScript scripts that access Active Directory you’ve probably used code similar to this:
Set objUser = GetObject _ ("LDAP://cn=kenmyer, ou=Finance, dc=fabrikam, dc=com")
What’s wrong with that line of code? Nothing; it works just fine, provided you’re using VBScript. If you’re using Windows PowerShell, however, it’s a different story; that’s because Windows PowerShell doesn’t have a cmdlet analogous to the GetObject method. If you need to use GetObject to connect to something, well, that’s a problem.
So does that mean we are out of luck? Not quite. One of the cool things about Windows PowerShell is that it provides direct access to the .NET Framework. The Scripting Guy who writes this column isn’t exactly an expert on the .NET Framework, but he does know one thing: the DirectoryServices.DirectoryEntry class enables you to bind to an object in Active Directory. Can we use this .NET Framework class to get information about the Ken Myer user account? We’re about to find out.
Right after we step outside for a moment. Don’t tell you-know-who, OK? (Although that probably won’t matter; no doubt her flying monkeys will tattle on us anyway.)
Editor’s Note: Never fear, the monkeys have brought the Scripting Guys back to their offices to finish this.
Now, where were we? Oh, that’s right: something about using Windows PowerShell to bind to an Active Directory user account. Hey, all you had to do was ask:
New-Object DirectoryServices.DirectoryEntry "LDAP://cn=kenmyer, ou=Finance, dc=fabrikam, dc=com"
As you can see, this is actually a pretty neat little trick: what we do is call the New-Object cmdlet followed by the type of .NET object we want to create (DirectoryServices.DirectoryEntry). And then we follow that by specifying the ADsPath of the object we want to bind to. It’s that easy.
Incidentally, you can also use the New-Object cmdlet to access COM objects. That can get a tiny bit complicated, so we won’t discuss the whys and wherefores today. But, just to whet your appetite a little, here’s a command that starts up a visible instance of Microsoft Excel (note the use of the -com parameter):
$A = New-Object -com Excel.Application; $A.Visible = $True
By default the Active Directory command we showed you a moment ago returns only the user’s distinguished name. (Which isn’t as useful as it might sound; after all, seeing as how the distinguished name is part of the ADsPath we already know the user’s distinguished name.) But that’s OK; after we bind to the user account we can then use the Select-Object cmdlet to pick out the properties we’re interested in. Did you say you wanted to know the user’s Name and telephoneNumber? Okey-doke:
New-Object DirectoryServices.DirectoryEntry "LDAP://cn=kenmyer, ou=Finance, dc=fabrikam, dc=com" | Select-Object name, telephoneNumber
Now you want to get back all the properties and their values? Then just use the wildcard character (the asterisk) when calling Select-Object:
New-Object DirectoryServices.DirectoryEntry "LDAP://cn=kenmyer, ou=Finance, dc=fabrikam, dc=com" | Select-Object *
Not bad for a workaround, is it?
Ah, that’s a good question: how can you determine, in advance, which properties are available for this user account? Here’s a hint for you: bind to the object, then pass the object to the Get-Member cmdlet, which then reports back all the object properties and methods.
Here’s an even better hint; just do this:
New-Object DirectoryServices.DirectoryEntry "LDAP://cn=kenmyer, ou=Finance, dc=fabrikam, dc=com" `
We should note that all we’ve done today is answer a very specific question: how can you bind to, and get back information from, an Active Directory user account? No doubt you have other questions about using Windows PowerShell to work with Active Directory (e.g., how can I create/delete/modify a user account?). To be honest, we don’t have the answers to many of those questions; we’re pretty new to Windows PowerShell ourselves. But as we begin to find the answers you’ll be the first to know. Promise.
And now we are going outside. After all, in Seattle the sun is like a solar eclipse or a pay raise: if you’re lucky, you might get to see it once in your life. We’ve given up on the pay raise, but we have no intention on missing the sunshine.