I got it into my head earlier this evening that maybe I couldn’t reach my files that should be registered in the PATH variable because it had been truncated, after all when I ran
ECHO %PATH%
I did get a truncated text. However that is probably just due to the output buffer being capped looking at this post about maximum length of environment variables.
By this point however, I had already begun building a script to try and shorten down my PATH variable, I mean, who would ever do that manually?……. I mean, who wouldn’t spend two hours writing a script to do it?……. I mean, yea, you could’ve used a regex and split it, done a 5 second ocular inspection, decided that it couldn’t be improved and left it at that but that wouldn’t be fun would it?……. ok. I got carried away.
So, anyway, I did some research, a lot of trial and error and the script I came up with not only removes any multiples of registered directories and missing ones in the PATH variable but also showcases some cool useful stuff you can do with a VBScript or command prompt, such as:
- Restarting current command prompt
Which is good for reloading environment variables
Simply:
START cmd /SEPARATE & EXIT
- Running an elevated command from within the script
- Grabbing output from another script
- Changing environment variables from within a script
- Checking whether or not you’re running in elevated mode
So the script looks like this and is ready to run with cscript or wscript from elevated or non elevated mode, the one thing I didn’t bother fixing in the end was to output the text from the elevated process to the first process if it’s restarted as elevated:
Dim application : Set application = CreateObject("Shell.Application")
Dim shell : Set shell = CreateObject("WScript.Shell")
Dim filesystem : Set filesystem = CreateObject("Scripting.FileSystemObject")
Dim winMgmt : Set winMgmt = GetObject("WinMGMTS://./Root/CIMv2")
Function Elevated()
Dim waitOnReturn : waitOnReturn = true
Dim windowStyle : windowStyle = 1
Dim execResult : Set execResult = shell.Exec("%comspec% /c whoami /groups | find ""S-1-16-12288""")
Do While execResult.Status = 0
WScript.Sleep 100
Loop
Dim output : output = execResult.StdOut.ReadAll
If InStr(output, "S-1-16-12288") Then
Elevated = true
Else
Elevated = false
End If
End Function
If Not Elevated() Then
WScript.Echo "Not running as elevated user, will restart with UAC control"
WScript.Echo "Will now run as elevated in another window, to get effects afterwards this console will need to be restarted."
WScript.Echo "To restart a command prompt use: START cmd /SEPARATE & EXIT"
application.ShellExecute "cscript.exe", WScript.ScriptFullName, "", "runas", 1
WScript.Quit
End If
Function TrimTrailingSlash(path)
If Right(path, 1) = Chr(92) Then ' Chr(92) = , used Chr to not mess up syntax highlighting
TrimTrailingSlash = Left(path, Len(path) - 1)
Else
TrimTrailingSlash = path
End If
End Function
Function InPath(totalPath, subPath)
Dim caseInsensitive : caseInsensitive = 1
InPath = InStr(1, totalPath, subPath & ";", caseInsensitive)
End Function
Function InPathExpanded(totalPath, subPath)
InPathExpanded = InPath(shell.ExpandEnvironmentStrings(totalPath), shell.ExpandEnvironmentStrings(subPath))
End Function
Dim sysEnv : Set sysEnv = shell.Environment("SYSTEM")
Dim pathEntries : pathEntries = Split(sysEnv("PATH"), ";")
Dim path, newPath, folderPath, itemsSaved
newPath = ""
itemsSaved = 0
For Each path in pathEntries
path = TrimTrailingSlash(path)
folderPath = shell.ExpandEnvironmentStrings(path)
If Not filesystem.FolderExists(folderPath) Then
WScript.Echo "Folder missing, removing from path: " & path
ElseIf InPath(newPath, path) Then
WScript.Echo "Folder exists in path multiple times, skipping: " & path
ElseIf InPathExpanded(newPath, path) Then
WScript.Echo "Folder exists in expanded path (no %...%) multiple times, skipping: " & folderPath
Else
newPath = newPath & path & ";"
itemsSaved = itemsSaved + 1
End If
Next
WScript.Echo ""
WScript.Echo "Output path = " & newPath
WScript.Echo ""
Dim optimized : optimized = UBound(pathEntries) - itemsSaved + 1
WScript.Echo "Saving " & itemsSaved & " items, optimized " & optimized & " items."
sysEnv("PATH") = newPath
WScript.Echo "All done! If running in a command prompt you will need to restart it for effects to kick in."
WScript.Echo "To restart a command prompt use: START cmd /SEPARATE & EXIT"
WScript.Sleep 2000
If nothing else, I hope it could at least serve as an example of some scripting techniques.
Edit (5 minutes later):
Forgot to credit the sources from which most of the above was combined, fixing the path here and running elevated here.