Why: At the schools I work for, we routinely need to log in as a particular user account that exists solely for online testing (why we have this account is a long explanation...just accept that it's needed). In the past what we've had to do is log into every machine as that user and let our startup scripts handle setting up autologin and restarting the computer so that the system is ready for the online testing software we're required to run.
How: We name our computers like this: campus-room-ws__ with the last two characters being a workstation number. This way we can script for large numbers of computers at once while having the granularity to easily work with individual stations. This script basically asks for the campus-room prefix, and a range of workstation numbers. It then issue a delayed shutdown command and then registry modifications to enable autologin (the registry mods come second because we've had problems with the computer overwriting autologin registry values when shutdown is run)
Here's the code:
edit: okay, the code tags don't seem to work the same here as they do in other forums. I pasted this from NOTEPAD and it's still not behaving.
<html>
<head>
<title>Online Testing Lab Deployment</title>
<HTA:APPLICATION
APPLICATION="JBKB tutorial"
SCROLL=No
SINGLEINSTANCE=YES
>
</head>
<script language="VBScript">
Sub Window_onLoad
window.resizeTo 350,250
End Sub
Sub DeployScript
Set WSHShell = CreateObject("WScript.Shell")
strLoginUser = "cota"
intCount = StopWS.Value - StartWS.Value
if intCount < 1 Then
MsgBox "Invalid Workstation Range"
document.execCommand("Refresh")
End If
For i=StartWS.Value To StopWS.Value Step 1
if i<10 Then
strComputer= LabName.Value & "-ws0" & i
Else
strComputer= LabName.Value & "-ws" & i
End If
Set objWMIService = GetObject("winmgmts:\\.\root\CIMV2")
Set colItems = objWMIService.ExecQuery("SELECT * FROM Win32_PingStatus WHERE Address = '" & strComputer & "'")
For Each objItem in colItems
If objItem.StatusCode = 0 Then
'
WSHShell.Run "shutdown -f -r -t 30 -m \\" & strComputer
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v DefaultUserName /f /d " & strLoginUser
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v AutoAdminLogon /f /d 1"
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v DefaultPassword /f"
Else
MsgBox strComputer & " did not respond to ping."
End If
Next
Next
End Sub
Sub RevertScript
Set WSHShell = CreateObject("WScript.Shell")
strLoginUser = RevertUser.Value
intCount = StopWS.Value - StartWS.Value
if intCount < 1 Then
MsgBox "Invalid Workstation Range"
document.execCommand("Refresh")
End If
For i=StartWS.Value To StopWS.Value Step 1
if i<10 Then
strComputer= LabName.Value & "-ws0" & i
Else
strComputer= LabName.Value & "-ws" & i
End If
Set objWMIService = GetObject("winmgmts:\\.\root\CIMV2")
Set colItems = objWMIService.ExecQuery("SELECT * FROM Win32_PingStatus WHERE Address = '" & strComputer & "'")
For Each objItem in colItems
If objItem.StatusCode = 0 Then
Set FSO=CreateObject("Scripting.FileSYstemObject")
strINIfile="\\" & strComputer & "\c$\windows\testnav.bat.ini"
If FSO.FileExists(strINIfile) Then
FSO.DeleteFile strINIfile
End If
WSHShell.Run "shutdown -f -r -t 30 -m \\" & strComputer
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v DefaultUserName /f /d " & strLoginUser
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v AutoAdminLogon /f /d 0"
WSHShell.Run "reg add ""\\" & strComputer & "\HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon"" /v DefaultPassword /f"
Else
MsgBox strComputer & " did not respond to ping."
End If
Next
Next
End Sub
Sub CancelScript
Self.Close()
End Sub
</script>
<body>
<table>
<tr>
<td align="right">
Lab name (ex. CHS-A1)
</td>
<td>
<input type="text" name="LabName" tabindex=1 />
</td>
</tr>
<tr>
<td align="right">
Start on workstation #
</td>
<td>
<input type="text" name="StartWS" tabindex=2 />
</td>
</tr>
<tr>
<td align="right">
Stop on workstation #
</td>
<td>
<input type="text" name="StopWS" tabindex=3 />
</td>
</tr>
<tr align="right">
<td>
<input class="button" type="button" value="Cancel" onClick="CancelScript" tabindex=5 />
</trd>
<td>
<input class="button" type="button" value="Deploy" onClick="DeployScript" tabindex=4 />
</td>
</tr>
</table>
<br />
Revert using the following user name:<br />
<input type="text" name="RevertUser" value="your_username_here" tabindex=6 />
<input class="button" type="button" value="Revert to Normal" onClick="RevertScript" tabindex=7 />
</body>
</html> Yes, there is a fair bit of replication between the apply and revert code. There was just enough difference between the two that I felt the need to keep them separate.
I found it easier to making changes to the remote registries and shut down the PCs using shell commands as the VBScript for this was convoluted and I found the shell far easier to make work consistently.
This particular script doesn't let you specify the autologin user because we always use the same account. It would be a simple thing to have it use the same text field as the revert script (and would probably make it easier to reuse some of the code)
Comments and suggestions on further improving this are always welcome. I'm new to this :)
<message edited by Kravis on Friday, April 09, 2010 4:14 AM>