Managing BizTalk Groups with WMI

As some of you may know, Microsoft publishes an extensive documentation regarding the tasks one can perform against a BizTalk group, either throught a user interface, or through script and code. It’s called, quite ambitiously "Determining the Right Tool for your Task"!

This document is a set of matrices, grouped by relevant BizTalk artifacts they relate to. Each matrix consists in four columns and several lines, where each line lists a given potential operation you want to perform with BizTalk. The first two columns tell you what operation is available, if appropriate, through the use of the BizTalk Server Administration Console MMC Snap-In and the BizTalk Explorer user interface. More interestingly, the last two columns give you the same information when working through script and code and are of more interest to us.

If you read this list carefully, you’ll notice that certain kind of administrative tasks are only exposed from WMI. For instance, all the "Host tasks" group says in the "BizTalk Explorer Object Model" column is "None". For these tasks, you cannot rely on the neat object model exposed throught the Microsoft.BizTalk.ExplorerOM assembly.

Conversely, some operations are not available from WMI. This is why you need to use both models when working with BizTalk from code. Anyway, I don’t know about you, but I really don’t like working with WMI from C#. I find the resulting code unnecessary verbose and cumbersome. That is, until I discovered the Management Strongly Typed Class Generator command-line utility (aka MgmtClassGen).

This utility creates strongly-typed classes that alleviate the hard work usually associated with programming against WMI. For instance, take the traditional code necessary for creating a BizTalk host instance :

//Build the name of the HostInstance - name has to be in the below format 
string hostInstanceName = "Microsoft BizTalk Server" //Name of product
                  + " " + hostName        //Name of Host
                  + " " + svrName;         //Name of Server
         
//Create an instance of the ServerHost class using the System.Management namespace 
ObjectGetOptions svrHostOptions = new ObjectGetOptions();
ManagementClass svrHostClass = new ManagementClass("root\\MicrosoftBizTalkServer"
            , "MSBTS_ServerHost"
            , svrHostOptions);
ManagementObject svrHostObject = svrHostClass.CreateInstance();
 
//Set the properties of the ServerHost instance 
svrHostObject["ServerName"] = svrName;
svrHostObject["HostName"] = hostName;
            
//Invoke the Map method of the ServerHost instance 
svrHostObject.InvokeMethod("Map",null);
 
//Create an instance of the HostInstance class using the System.Management namespace 
ObjectGetOptions hostInstOptions = new ObjectGetOptions();
ManagementClass hostInstClass =
            new ManagementClass("root\\MicrosoftBizTalkServer"
                        , "MSBTS_HostInstance"
                        , hostInstOptions);
ManagementObject hostInstObject = hostInstClass.CreateInstance();
 
//Set the properties of the HostInstance class 
hostInstObject["Name"] = hostInstanceName;
 
//Build a parameter array 
object [] args = new object[2];
args[0] = uid;
args[1] = pwd;
            
//Invoke the Install method of the HostInstance 
hostInstObject.InvokeMethod("Install",args);

Contrast with this code, directly taken from our BizTalk PowerShell Provider:

                // map BizTalk Host

ServerHost host = ServerHost.CreateInstance();
host.LateBoundObject["ServerName"] = RunningServer;
host.LateBoundObject["HostName"] = HostName;
host.Map();

// add new BizTalk Host Instance

string name = "Microsoft BizTalk Server " + HostName + " " + RunningServer;

HostInstance hostInstance = HostInstance.CreateInstance();
hostInstance.LateBoundObject["Name"] = name;
hostInstance.Install(true, Credential.UserName, Credential.Password);

The difference speaks for itself, don’t you think ?

Sidebar

You can take advantage of Visual Studio’s builtin Prebuild event to generate the classes as part of the build process. For instance, the following line in the .csproj generates a strongly-typed GroupSetting class for managing the BizTalk group:

$(FrameworkSDKDir)bin\MgmtClassGen.exe" MSBTS_GroupSetting /n root\MicrosoftBizTalkServer /l cs /o Microsoft.BizTalk.Management /p "$(ProjectDir)\Management\GroupSetting.cs

This is the approach we’ve taken in the BizTalk Powershell provider. But there’s a catch: it does work only on a local BizTalk installation. Next time, we will see how to address this issue and work against a remote installation (Thanks to Randal for pointing this out).

This entry was posted in WMI. Bookmark the permalink.