| Executive Summary:|
Using Windows Management Instrumentation (WMI), Windows Script Host (WSH), and a lot of creative coding, Alex K. Angelopoulos developed AddressBasedPrinter.vbs. This VBScript script determines which site a mobile user is in, then creates printer mappings for the appropriate printers at that site.
AddressBasedPrinter.vbs in Listing 1 performs many tasks to determine which site a mobile user is in and create mappings to the appropriate printers at that site. Here's a brief overview of how it works.
The script's first main task is to collect the TCP/IP-enabled Win32_NetworkAdapterConfiguration instances from the local computer. As callout A shows, for each configuration, it retrieves the IP addresses and subnet masks from the IPAddress and IPSubnet properties, respectively. After making sure these properties aren't empty, the script uses the NetworkID function in callout E to compute network IDs from the IP addresses and subnet masks. For example, if a computer has an IP address of 192.168.1.72 and a subnet mask of 255.255.255.0 associated with that address, the network ID for the computer—and all the other computers on the same network—will be 192.168.1.0. (For information about how this function works, see the web-exclusive Windows IT Pro article "Rem: How to Use WMI to Calculate a Computer's Network ID from Its IP Address and Network Mask." The script adds the IDs to the networkIDs dictionary as keys. Using the Scripting Runtime Library's Dictionary object is better than using an array because you don't know how many network IDs there will be. By storing them in a dictionary at this point, you avoid having to micromanage a resizable array. In the last line in callout A, the script extracts the networkIDs dictionary's keys and assigns them to the IDList array.
Next, the script creates another dictionary named Locations to hold the site names and network IDs specified in callout B. The code in callout C uses the Locations dictionary to determine which site the mobile user is in.
In callout C, the script makes sure that the mobile user isn't running a remote Terminal Services session. If Terminal Server is properly configured, mobile users won't run a standard logon script when they log on, but just in case, the script checks for the %SessionName% logon variable. This variable exists on all OSs from Windows 2000 Server forward that can support Terminal Services sessions. When a user is directly logged on to the console of a system that has Terminal Services support, this variable will exist and will contain the value Console. If a user has a legacy OS (which includes Windows 2000 Professional in this case), this variable shouldn't exist and checking its value will simply return %SessionName%. In either case, the script handles the printer mappings. However, if the user is running a nonconsole session (i.e., running a remote Terminal Services session), the script doesn't perform any matching and therefore won't accidentally set up printing to a remote location.
When the user is directly logged on to the console, the script checks to see if the network IDs in the Locations dictionary match the network IDs in the IDList array. When the script finds a match and that match is the first one found, it sets the SystemLocation variable to the corresponding site name, which it gets from the Locations dictionary. If SystemLocation has already been set because a previous match was found, the script sets MultipleMatches to True.
Next, AddressBasedPrinter.vbs checks the value in MultipleMatches. When the value is True, the script ends. This ensures that printers aren't mapped for multiple network locations in case of a configuration error. When the value is False, the script creates a Windows Script Host (WSH) WshNetwork object, which enables connections to network shares and printers, then runs the VBScript Select Case statement.
In the Select Case statement, the script looks for a match between the site in the SystemLocation variable and the sites in the Case clauses in callout D. When the script finds a match, it runs the code under that Case clause (i.e., the code that creates the printer mappings), then quits. When no matches are found, the Case Else clause runs. In this case, the script displays a message that notes there aren't any matching sites, then quits.