Author Posts

January 1, 2012 at 12:00 am

by NMayberry at 2012-09-26 09:56:29

Hey All,

Is there a way to verify username and password against AD? I have some interactive scripts that I'm trying to head off errors with people possibly fat fingering their credentials.

Thanks,

Nathan Mayberry

by RichardSiddaway at 2012-09-26 11:16:11

You can verify username easily enough – password is a bit more tricky
if you look at a user object
$user = [adsi]"LDAP://CN=Richard,CN=Users,DC=Manticore,DC=org"
PS> $user | select p*

proxyAddresses : {SMTP:Richard@manticore.org}
pwdLastSet : {System.__ComObject}
primaryGroupID : {513}
protocolSettings : {HTTP§1§1§§§§§§, OWA§1}
Parent : LDAP://CN=Users,DC=Manticore,DC=org
Password :
Path : LDAP://CN=Richard,CN=Users,DC=Manticore,DC=org
Properties : {objectClass, cn, c, l...}

The password property isn't populated. The Microsoft & Quest cmdlets don't return the password

PS> $user.password -eq "test"
False

False will be returned even if you give the correct password.

When you log on your system data is sent to the domain controller – your password is used to derive a key that is used to encrypt the data. The password itself is not sent. AD uses its copy of your password to decrypt the data. As the data includes user name & time it can tell if the decryption worked.

The passwords aren't exposed.

You can verify the username – I don't think you can do password

by jonhtyler at 2012-09-26 11:48:37

I have done some quick tests in my environment with the System.DirectoryServices.AccountManagement.PrincipalContext class. It looks like a lot (see code below) but it is not really as bad as it might seem at first, and it does work in my little test snippet.

[reflection.assembly]::LoadWithPartialName("System.DirectoryServices.AccountManagement") | out-null
$pctx = new-object System.DirectoryServices.AccountManagement.PrincipalContext(
[System.DirectoryServices.AccountManagment.ContextType]::Domain,
"contoso.com", "dc=contoso,dc=com",
[System.DirectoryServices.AccountManagement.ContextOptions]::SimpleBind,
"CONTOSO\SomeServiceAccount", "Pa$$w0rd")
$pctx.ValidateCredentials("CONTOSO\jdoe", "t3stp4$$w0rd")

DISCLAIMER!!!
I DO NOT advocate coding clear-text credentials in production code. I have done so in this snippet for demonstration purposes ONLY!!! Use the above code in your production environment at your own risk.

Now that I have that out of the way, I did a quick & dirty test using the above code on my own system. It works. It is a starting point and it seems to do what you want. There are other options and ways to use this class as described in the MSDN documentation found here: http://msdn.microsoft.com/en-us/library/bb356158.aspx

To my knowledge, this simply does a check on the validation, however, it will not tell you if the password is expired, the account is locked out, or any other extended possibilities to describe why the credentials will not validate. In order to go to those depths, you will most likely want to write a series of other functions (or a self-contained .NET class) that will handle that heavy lifting. I don't know what your experience is in those areas. That being said, I believe this will suffice for your original question.

I hope this helps.

by NMayberry at 2012-10-16 11:36:07

Thanks for the help!