I solved a little problem for a customer the other day and I thought I’d share a little about it with you. It involves some VBScript user manipulation in Active Directory, and yes: there will be a code sample.
Let’s start with the problem. For whatever reason, some users were missing some home drive information and more than half of users were not configured for roaming profiles. It was determined that this should be corrected. An easy way, of course, would be to push a group policy out which would configure something like: \\servername\home\%username% for home directory paths and \\servername\profile\%username% for profile paths. Well, that would have been easy if that’s what the customer wanted to do, but it wasn’t. Instead, they have set up a rather nice DFS root share for home drives and profile paths broken down by, lets say, users’ last names. Sample paths for this would be \\dfsroot.com\home\%x\%username% where %x is the user’s first initial of the last name. This wouldn’t be so easy with a group policy. So for this, I wrote some code.
What I did was obtain a list of users who needed these properties set in display name format. This was done by extracting user information with CSVDE. The result would look something like this:
Johnson, William K.
Once I had this file (named users.txt), I could run my script
If you’ll notice, in this particular instance, the display name is Last, First. Many corporations configure their GAL this way, and I can understand why, although at Microsoft we use the reverse order of First Last.
What the script does is open a log file for writing, open the users.txt file for reading
Const ForWriting = 2 Const ForReading = 1 'Path for log logfilepath = "C:\TEMP\log.txt" 'Path for user list userfilepath = "C:\TEMP\users.txt" 'Base Paths baseHomePath = \\dfsroot.com\home\baseProfilePath = \\dfsroot.com\profile\ 'Setup input file Set objFSO = CreateObject("Scripting.FileSystemObject") Set objInputFile = objFSO.OpenTextFile(userfilepath, ForReading, True) 'Setup log file Set objFSO = CreateObject("Scripting.FileSystemObject") Set objAdLogTextFile = objFSO.OpenTextFile(logfilepath, ForWriting, True) 'Create Objects for LDAP Queries Set rootDSE = GetObject("LDAP://RootDSE") DomainContainer = rootDSE.Get("defaultNamingContext") Set conn = CreateObject("ADODB.Connection") conn.Provider = "ADSDSOObject" conn.Open "ADs Provider" 'Read in username from input file Do Until objInputFile.AtEndOfStream strDisplayName = objInputFile.Readline 'Find all users in AD using an LDAP query strLDAP = "<LDAP://" & DomainContainer & ">;(&(objectCategory=person)(objectClass=user)_
(anr=" & strDisplayName & "*));adspath;subtree" 'Get query results and output to file Set oComm = CreateObject("ADODB.Command") oComm.ActiveConnection = conn oComm.CommandText = strLDAP oComm.Properties("Sort on") = "displayName" oComm.Properties("Page size") = 15000 set rs = oComm.Execute If rs.recordcount = 0 then QueryResult = "User not found" objAdLogTextFile.WriteLine(FoundObject.Displayname & " | " & QueryResult) End If If rs.recordcount > 1 then QueryResult = "Resolved to more than one name" objAdLogTextFile.WriteLine(FoundObject.Displayname & " | " & QueryResult) End If If rs.recordcount = 1 then While Not rs.EOF Set FoundObject = GetObject (rs.Fields(0).Value) fullProfilePath = baseProfilePath & left(FoundObject.displayName,1) & "\" &_
FoundObject.sAMAccountName fullHomePath = baseHomePath & left(FoundObject.displayName,1) & "\" &_
FoundObject.sAMAccountName objAdLogTextFile.WriteLine(FoundObject.Displayname & " | " & fullHomePath &_
" | " & fullProfilePath) FoundObject.profilePath = fullProfilePath FoundObject.homeDirectory = fullHomePath FoundObject.homeDrive = "H:" FoundObject.SetInfo rs.MoveNext Wend End if Loop MsgBox "Processing complete!"
This code helped me to set the baseline for existing users. New would then need to be created with the proper home drive and profile path. A good way to automate this is with something like ILM to provision user accounts. ILM is good for quite a lot of things and maybe one day, I’ll have some tidbits to post about it.
Until next time, I hope this sample will help you get started on your own scripts for your directory.