.WSF: The Final Frontier

After this last lesson—which looks at the flexibility of Runtime tags—you’ll be ready to bravely face bold, new scripts.

Theory... The Final Chapter. Over the last several months, I’ve placed a larger-than-average focus on teaching you some very specific techniques. Sure, I’ve continued to strive to always show you practical ways to use this theory; but, nonetheless, I’m sure there were times when reading this column felt more like being in a classroom than a server room. That’s all about to change. Rest assured, you’ll be glad you learned what you did. This foundation of technical information is going to be vital as we move forward.

Starting with my next column, I’m going to begin a “script-centric” approach, leveraging—in one way or another—all of the techniques you’ve learned thus far. Rather than show you a technique and explain how to utilize it, I’ll be bringing you really cool, complete scripts that you’ll wonder how you ever lived without. Fear not. I’ll continue to explain new things as we encounter them, but I’ll rely on the fact that you’ve absorbed all of the knowledge of the preceding months. As I said, this begins in my next column. This month I’m going to finish discussing the really cool capabilities of .WSF scripts. Think of this as your last day of ground school before jumping into the plane and “getting down to business” by actually taking flight. Got your parachutes on? Let’s go!

He Ain’t Heavy... He’s my Theory
I’ve been discussing the various XML elements that are used in .WSF scripts to add power and flexibility. We’ll finish off this topic by discussing the last group of tags: the Runtime tags. This set of elements allows you to specify information pertaining to the correct usage of your scripts. You may remember that I’ve done this before. Back in my June 2000 column, “Garbage In, Data Out,” I talked about how to pass arguments into your scripts. This greatly increases the script’s flexibility by not requiring you to “hard-wire” everything into your code. In that column, I had to create code to manually display the proper usage. The Runtime tags do that for me.

Virtually every command-line tool allows you to ask for help. Even our old pal CSCRIPT.EXE will tell you how to use it when you ask properly. Figure 1 demonstrates this. As your scripts become more and more complex, proper usage guidelines become critical. This usage information is displayed either when the script is called with the “/?” argument or when specifically invoked by using the ShowUsage method of the WScript. Arguments object.

/? flag
Figure 1. Proper usage information is displayed when the ‘/?’ flag is used. (Click image to view larger version.)

Let’s look at the tags we use to add this runtime help to our scripts:

<runtime>—This element marks the beginning of the runtime usage section in your script. In .WSF files, usage information is established for each job; therefore, this element must be “inside” the <job> tag. Furthermore, each remaining runtime element must be “inside” the <runtime> tag.

Runtime tags
Figure 2. Use the <runtime> tags to display usage information. (Click image to view larger version.)

<description>—This element allows you to enter a short description of the functionality provided by the script. This text (including any special characters) is displayed at the beginning of the usage information.

<example>—You use the <example> tag exactly as you would the <description> tag. The only difference is that the text is displayed at the end of the usage information (where you would most likely include an example).

<named>—This element allows you to name the arguments you’ll pass to the script. This is really cool. Rather than passing arguments in a specific order, you can specify the name for each argument and extract it from the WScript.Arguments object at runtime. The elements of the <named> tag are as follows:

  • name specifies the name of the tag (i.e. the name that will be entered on the command line).
  • helpstring is displayed immediately after the name.
  • type, an optional element, specifies the type of value for the argument. The three types are String, Boolean and Simple. By default, all arguments are Simple.
  • required holds a Boolean value to indicate whether the argument is required. (Note: This doesn’t affect script execution. It only affects what is displayed during ShowUsage.)

<unnamed>—This element allows you to specify the usage for arguments that aren’t identified by a name when the script is invoked. Ironically, these unnamed elements must be named and must be entered on the command line in the correct order. Just like <named> arguments, <unnamed> arguments have name, helpstring and required elements, though required is handled differently. They also have a new element: many.

  • required can either be a Boolean value or an integer. If it’s an integer, it specifies the number of arguments required. Again, as with the <named> tag, required has no effect on the script functionality, only on what is displayed during ShowUsage.
  • many allows you to specify additional arguments beyond those that are required. This will become clear in the following examples.

Generally speaking, you should probably not mix named and unnamed arguments. Both are available to give you flexibility in how arguments are passed to your script. For what it’s worth, I like using named arguments exclusively. It’s more structured and leaves less room for error, and you know how I hate errors!

Unnamed tag
Figure 3. The <unnamed> tag allows you to specify multiple, optional arguments. (Click image to view larger version.)

<usage>—The <usage> tag is used to override all other runtime elements. If used, the text it contains is the only text displayed when ShowUsage is invoked.

My Brain Hurts!!
Are you thoroughly confused yet? Let’s look at how these tags are used in an actual script and see if I can’t clear the fog a bit.

<?xml version="1.0">
<job>
<comment>

MyComplicatedScriptWithArguments.wsf
This script demonstrates how the runtime tags are used to show the proper usage for passing arguments to the script.

</comment>

<runtime>
<description>

This script demonstrates how to use arguments.
</description>

<named
name=
"Arg1"
helpstring="This is the first argument"
type="string"
required="true"
/>

<named
name
="Arg2"
helpstring="This is the second argument."
type="string"
required="false"
/>
</runtime>

<script language="VBScript">
<![CDATA[
WScript.Arguments.ShowUsage

]]>
</script>
</job>

Figure 2 shows the output from this script. Because all our does is call the ShowUsage method, the output is the same regardless of whether we ask for help (“/?”) or run the script. You’ll also note that when I ran the script without the “/?” flag, I didn’t get an error, even though one of my arguments was required. Told you so!

Now let’s look at using unnamed arguments:

<?xml version="1.0">
<job>
<runtime>
<description>

This script demonstrates how to use unnamed arguments.
</description>

 

<named
name=
"Arg"
helpstring="This is the first argument"
many="true"
required="1"
/>

<example>
Example: MyComplicatedScriptWithArguments.wsf Argument 1
[Arg2... Arg3...]
</example>
</runtime>

<script language="VBScript">
<![CDATA[
WScript.Arguments.ShowUsage

]]>
</script>
</job>

As you can see in Figure 3, the Arg1 is shown as a required argument and Arg2 is shown as optional. I’ve also used the </example> tag to show how it’s displayed.

Before I wrap this up, let’s take a quick look at how you can retrieve these arguments in your scripts. Unnamed arguments are passed to the arguments collection in order. (Refer to my June 2000 column to see how you access these arguments.) Named arguments are retrieved by name. Add this code to the script using named arguments to assign the values to variables:

' AssignArguments.wsf
' ... insert script text from above

Dim strVar1, strVar2
strVar1=Wscript.Arguments.Named.Item("Arg1)
strVar2=Wscript.Arguments.Named.Item("Arg2)

' Rest of script here...

Homework

Your homework for this month is to go back to the beginning of this column (January 2000 issue) and re-familiarize yourself with all of the techniques we’ve learned to date. You’re going to need it!

About the Author

Chris Brooke, MCSE, is a contributing editor for Redmond magazine and director of enterprise technology for ComponentSource. He specializes in development, integration services and network/Internet administration. Send questions or your favorite scripts to [email protected].

Featured