It's All (nearly) in the Script
This column appeared in the April 2000 edition of EXE.
It reviews the key features of the VBScript dialect of Visual Basic, and then
examines its usage in the Windows Scripting Host.
I must admit to feeling very fortunate about being the regular
columnist for Visual Basic. Not only is Visual Basic the most widely adopted of
Microsofts developer tools but the core language itself crops up in
several places, most notably in Visual Basic for Applications; a technology
which thirdparties can licence for their own products. This month however
I would like to involve another guise of the language: Visual Basic Scripting
Edition, also known as VBScript. The language itself is a cut down version of
Visual Basic, but the bulk of the constructs are still available and,
importantly, it still offers access to ActiveX components. Ill briefly
discuss what differences exist, but frankly this is more a matter of detailing
what features are missing. Ill then move on to discuss the Windows
Scripting Host tool, which supports the VBScript language (among others).
VBScript
VBScript is, to all intents and purposes, the same language
that we use with the fullblown Visual Basic development tool. Various
aspects of the language have, however, been lightened up in order to reduce the
implementation overhead. Visually, the most noticeable difference is in the
area of declaring variables, in that everything is a variant. Although variants
store subtypes of data, such as date, string, integer, long, object, and so on,
the actual variable definition is always of this one type. Therefore a variable
will always be just declared by name, such as
Dim LoopCount
rather than
Dim LoopCount As Long
Of course its not even necessary to make this
declaration; if you skip the Option Explicit statement at the top of the script
then all variables declarations will be implied by their appearance within the
actual code. Other major exclusions from VBScript are:
-
The Debug object.
-
The collection and clipboard objects.
-
The Declare statement (for declaring DLLs).
-
All traditional Visual Basic file I/O (but you can use FileSystemObjects
instead).
-
All financial functions.
-
Most of the error handling constructs (On Error Resume, Resume Next, On Error
Goto, the undocumented Erl value).
-
Conditional compilation constants (#Const, #If .. Then .. #Else)
One familiar feature that the most recent implementation of
VBScript (version 5) does provide is that of classes, which are declared as
shown in listing 1.
Option Explicit
Const Pi = 3.14159
Class AreaCalc
Public Function GetArea(Radius)
GetArea = Pi * Radius * Radius
End Function
End Class
Dim Result
Dim o
Set o = New AreaCalc
Result = o.GetArea(25)
WScript.Echo "The area of this circle is " & Result
Set o = Nothing
Listing 1: VBScript class declaration example
Visual Basic recognises files with a cls extension to contain
a class, but because a VBScript component is often encapsulated within a single
physical file a new syntax is introduced in the form of
Class..End Class. I understand that the Visual
Basic development team are apparently considering implementing this syntax into
Visual Basic in order to comply with the fact that VBScript is supposed to be a
subset of the fullfeatured language.
Windows Scripting Host (WSH)
For those software developers who were using PCs before the
Windows environment really got going there will no doubt be fond memories (er,
or not) of MSDOS batch files; the precursor to scripting. Once the
Windows environment became more established there were two approaches to
writing routines for administration tasks: continuing to use batch files (with
the BAT or CMD extension) or, at the other end of the scale, using
fullblown development tools such as Visual Basic to provide EXE
applications.
The WSH is a utility that incorporates the best of both
worlds. As the name implies it is a facility designed to run scripts, and as an
added bonus it is languageindependent too. For the purposes of this
discussion we will continue to make use of VBScript, but its worth noting
here that it can also host other languages such as Jscript and, if you have the
relevant thirdparty technologies, Perl, Python, and Rexx. The major
improvement over batch files however is the support for ActiveX technology,
which of course opens up the language to interfacing with a wide range of
software components. Furthermore it also brings its own object model to the
party, which we will take a look at in a moment.
VBScript files are conventionally given a vbs extension and
JScript files are denoted by js. The Windows namespace is familiar with these
extensions and so associates them with wscript.exe; the Windowsbased
version of the WSH runtime program. Therefore, for example,
doubleclicking a file with a vbs extension will cause the WSH program to
load up and then run the script within the file. To illustrate the most
fundamental illustration of this in timehonoured fashion, if you type
MsgBox "Hello world"
into a blank file, save it as hello.vbs, and then
doubleclick the resulting file from the Windows Explorer you will see the
expected dialog box. No need for a development environment, compiler, or
associated installation of runtime files! Aside from the Windowsbased
wscript.exe there is also a Win32 consolebased version, in this case
called cscript.exe.
When a WSH script is executed an internal object model called
WScript is automatically instantiated and made available. Apart from providing
root level properties such as the name and path of the current script and the
current WSH version number it also exposes a method called Echo which is
actually more appropriate than the MsgBox example I cited above. If there is
any chance that the script will be run in console mode then you should always
use WScript.Echo instead of MsgBox because it will display a standard line of
text within the console window if it is being run in this mode, but if it is
being run in Windows mode (i.e. via wscript.exe) then a standard message box
will be displayed instead.
The root object is also the path to a couple of subordinate
objects that provide access to the network and shell areas of Windows itself.
For example, you can create an instance of the Network object in the usual way,
i.e.:
Set oNetwork = CreateObject("WScript.Network")
and you can then obtain or set information as required, such
as
WScript.Echo oNetwork.ComputerName
The scope of the facilities made available by this object is
perhaps illustrated by the AddWindowsPrinterConnection method which will allow
you to dynamically add a new printer connection to Windows. Similarly, the
underlying shell object allows to you create desktop shortcuts, obtain and
expand environment strings, write data to the event log, read from and write to
the registry, and run other processes. For example, to obtain the actual full
path to the current users desktop area, you would first obtain a reference to a
Shell object and then call the SpecialFolders function:
Dim oShell
Dim sPath
Set oShell = CreateObject("WScript.Shell")
sPath = oShell.SpecialFolders("Desktop")
WSH 2.0
The initial version 1.0 of WSH was introduced with Windows 98
and also with the Windows NT 4 Option Pack. Windows 2000 introduces version
2.0, although the application logo message that is displayed by cscript.exe
when you are in a console window would have you believe that you are using
version 5.1. This confusion aside, WSH 2.0 includes a lot of new features that
certainly improve upon the previous version.
The most fundamental change to the specification is the
addition of an XMLbased file type that has the extension .wsf (short for
Windows Script File). Didnt I say last month that we would be seeing a
lot of XML this year? The incorporation of the XML language provides a new
framework for the script file, allowing for a greater scope of definition of
each logical entity within the file. Although vbs and js files are still
supported for backwardcompatibility, a wsf file incorporates the new
concepts of Jobs and Packages. A Job element is the logical grouping of a
series of tasks into a single batch; this is pretty much equivalent to a single
vbs file. A job can consist of multiple blocks of code which are each
identified by the XML <script> tag. By virtue of the language attribute
of this tag it is also quite easy to mix different languages within the same
job. A set of jobs is referred to as a Package, which is really just a means of
identifying the scope of the jobs within the wsf file. If there is more than
one job within a wsf file then it is necessary to embed them all within a pair
of <package> tags, otherwise the presence of this tag is optional.
Listing 2 illustrates the overall flow that exists within a wsf file that
includes multiple jobs.
<package>
<job id="job1">
<script language="VBScript">
WScript.Echo "Running
a VBScript item..."
</script>
</job>
<job
id="job2">
<script language="JScript">
WScript.Echo("Running
a JScript item...");
</script>
</job>
</package>
Listing 2: .wsf file using jobs and multiple languages
By default only the first job in a file is executed, but there
is a command line option for both of the hosting applications that allow you to
specify which of the jobs should be run the //Job:xxxx option. Therefore
if you run the script in listing 2 by doubleclicking from the Windows
Explorer you will only see the first message Running a VBScript
item
. However, if you open the Run dialog from the Windows Start
menu and specify something like
Wscript.exe c:\somedir\myjobs.wsf //Job:job2
Then you will instead see the Running a JScript
item
message.
One inevitable improvement is the addition of support for
include files. As with other languages this allows for libraries of common code
to be maintained and called as necessary, but because this referencing of other
files is dependent upon the XML tag it is only available to wsf files. The
actual reference is achieved by modifying the <script> tag to include an
src reference to an external file, as in
<script language="VBScript"
src="mylib.vbs"/>
As a quick aside, note the use of the trailing slash in the
above definition. This is an XML shortcut convention called the empty element
tag that denotes the closing of the section opened by the preceding
< character.
The power that the WSH gives to developers and administrators
alike is a major improvement upon the previous batch file concept, and WSH 2.0
in Windows 2000 significantly strengthens the technology even further. For
administrators and network support staff the additional inclusion of Windows
Management Instrumentation (see separate panel for overview) which is
callable from wsf scripts because of its ActiveX interface provides a
rich collection of key system information. Developers too will appreciate its
power both for writing components for formal systems development, but also for
writing their own quick support/configuration jobs. Further information on this
technology can be obtained from the Microsoft site at
http://msdn.microsoft.com/scripting. For the serious enthusiast there is
also a book called Windows Script Host Programmers Reference written by
Dino Esposito (Wrox Press, ISBN 1861002653).
The article also included a sidebar outlining the
basics of Windows Management Instrumentation (WMI)
WMI is the specific Microsoft implementation of an emerging
industry standard known as WebBased Enterprise Management (WBEM). The
concept is that management information about a computer installation can be
accessed in a uniform manner. Examples of such information are memory usage,
installed applications, hardware specifications, and so on. A WMI programming
interface allows developers to write programs that retrieve information about,
or manipulate as appropriate, the various aspects of a computer installation
using a SQL statements. Logical areas of functionality are implemented as
providers, of which a core set are supplied by the WMI SDK. For example the
event log provider allows an application to receive notification of Windows
events, and also provides access to the event log data itself. Thirdparty
companies can provide their own providers for their own products.
WMI is supported on Windows NT4 service pack 4 and above
(including Windows 2000), and Windows 95 SR2 and Windows 98.