Click here to Skip to main content
Click here to Skip to main content

Scripting .NET applications with VBScript

, 11 Apr 2007
Rate this:
Please Sign up or sign in to vote.
Allows the use of user supplied or other external VBScript in an application.

Introduction

mScript is a .NET class that allows you to dynamically script portions of your code using VBScript. You can pass multiple variables to your script, do any necessary processing, and return multiple variables from the script.

Using mScriptable

After adding a reference to the mScriptable.dll assembly, you can use/import the namespace:

using mScriptable;

You can then begin by creating an instance of the mScript class found in the mScriptable namespace.

mScript script = new mScript()

Next, you need to supply the variables your script will need access to.

  script.addScriptInput("foo", "Hello");
  script.addScriptInput("bar", "World");
  script.addScriptInput("x", 100);
  script.addScriptInput("y", 13);

And also assign your script code to the script object.

  string myScriptCode = "...";
  script.setScript(myScriptCode);

Your script code must be valid VBScript. Any error in the script will be caught by the Windows Scripting Host and not the control. Currently, the return value from the Windows Scripting Host process is not being monitored to determine if a script completed successfully, so it's important to catch your own errors. Your VBScript can retrieve the values supplied to it using either a provided inpVal(varName) function, or an abbreviated wrapper function iv(varName). Values can be returned to the .NET caller using a provided return varName, varVal subroutine. A sample script might look like the following:

  foo = iv("foo")
  bar = iv("bar")
  helloWorld = foo & " " & bar & "!"
  return "hwString", helloWorld

  x = iv("x")
  y = iv("y")

  calc1 = x * y
  return "calc1", calc1

  if y = 0 then
    MsgBox "Zero divide attempted!"
    calc2 = 0
  else 
    calc2 = x / y
  end if

  return "calc2", calc2

You can execute your script code using the runScript() method of the mScript object. This method will return a Hashtable containing all of your script's return values.

Hashtable rValues = script.runScript();

Upon completion of the script, the runScript() method will return a Hashtable containing the script's return values. In the case of our example, your Hashtable would have the following:

Hash Key
(Variable Name)
Hash Value
(Variable Value)
hwString Hello World!
calc1 1300
calc2 7.692307...

Back in your .NET application, you can then retrieve these values using the Hashtable.

  string returned = "";
  foreach (string rVar in rValues.Keys) {
    returned += rVar + " = " + rValues[rVar] + "\r\n";
  }
  MessageBox.Show(returned);

That's pretty much all there is to it. The supplied demo project shows a working example of the class in use, allowing you to supply the inputs, modify the VBScript, execute, and then view the outputs.

How it works

mScriptable relies on the Windows Scripting Host for its VBScript functionality. As such, with each call to runScript(), you incur the overhead of starting a Windows Scripting Host process. The communication between the .NET component and the scripting host is fairly crude, but workable. For each run, a new file (called [timestamp].vbs) is created. This file includes your provided code as well as some header code that provides the basic variable value retrieval and value return functionality as well as file I/O. Each call your script makes to the return subroutine spools a tab delimited name/value pair out to another file called [timestamp].txt. When the script exits, the .NET module reads the values from this file and makes them available in a Hashtable. After the script completes and the values are retrieved, both the .vbs and .txt files are removed.

Update! (4/5/2007)

At user request, mScriptable has been modified so it can now run a user's standalone scripts. If you want to use a VBScript directly with WSH and also via a .NET application using mScriptable, you now can. The changes you'll need to make to your script are as follows:

  1. Anything that is an input to your script must get its value from a function named either inpVal() or iv().
  2. Any outputs your script returns must be returned using a subroutine called return().
  3. you must create dummy functions for the inpVal() and/or iv() as well as the return() subroutine.

To prevent duplicate declarations of functions/subroutines in the VBScript code, mScriptable will remove any user defined functions/subroutines named inpVal(), iv(), or return().

A sample VBScript that can run standalone as well as via mScriptable might look like the following:

  ' My function to allow script to run via WSH directly
  Function iv(myVariable) 
    Dim retVal
    
    Select Case myVariable
      Case "foo"
        retVal = "John"
      Case "bar"
        retVal = "Doe"
      Case "x"
        retVal = 9
      Case "y"
        retVal = 3
      Case Else
        retVal = ""
    End Select
    
    iv = retVal
  End Function
  
  Sub return(varName, varVal)
    ' this is just a dummy function
    MsgBox varName & " = " & varVal
  End Sub
  
  foo = iv("foo")
  bar = iv("bar")
  helloWorld = foo & " " & bar & "!"
  return "hwString", helloWorld

  x = iv("x")
  y = iv("y")

  calc1 = x * y
  return "calc1", calc1

  if y = 0 then
    MsgBox "Zero divide attempted!"
    calc2 = 0
  else 
    calc2 = x / y
  end if

  return "calc2", calc2

When executed via the WSH directly, this script would run as you would expect. When loaded and run via mScriptable, the iv() function and the return() subroutine will be removed and replaced with mScriptable's own code that supplies the script inputs.

License

This article, along with any associated source code and files, is licensed under The GNU General Public License (GPLv3)

About the Author

Don C. Smith
Web Developer
United States United States
I reside in Madison, WI and currently work as a web developer for a Madison based advertising agency.
 
Professionally, I currently spend most of my time working with PHP, MySQL, JavaScript, CSS and a host of other webish technologies.
 
In my spare time I'm an avid open source enthusiast and use Linux exclusively at home (currently Ubuntu) for my desktop and web server. I also have a firewall/router running Smoothwall and a file/media server running Ubuntu. I tinker with various projects using Perl and Mono (C#), and play around with Common Lisp, Scheme, and some other functional oddities here and there too.
 
If I could only use one language for the rest of my life, it would be Perl.

Comments and Discussions

 
GeneralTrouble building mscriptable PinmemberMark H Peterson30-Mar-07 15:31 
GeneralRe: Trouble building mscriptable PinmemberDon C. Smith2-Apr-07 4:27 
GeneralRe: Trouble building mscriptable PinmemberMark H Peterson2-Apr-07 11:26 
GeneralRe: Trouble building mscriptable PinmemberDon C. Smith5-Apr-07 5:01 
GeneralMultiline strings PinmemberG40017-Dec-06 11:34 
AnswerRe: Multiline strings PinmemberDon C. Smith17-Dec-06 11:44 
NewsRe: Multiline strings PinmemberDon C. Smith2-Jan-07 6:27 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Mobile
Web03 | 2.8.140709.1 | Last Updated 11 Apr 2007
Article Copyright 2006 by Don C. Smith
Everything else Copyright © CodeProject, 1999-2014
Terms of Service
Layout: fixed | fluid