Using Powershell to deploy BizTalk Server solutions

published in category technology on Oct 13, 2015

There are many ways to deploy BizTalk Server solutions. In this post I will show how to automate that process using Powershell scripts.

In my previous post I talked about methods for adding more control to the deployment process when using BizTalk. As I mentioned, there are various tools to ease the pain and the following is just one approach. But it is very flexible one and can be adapted to follow the process I described. I am by no means a powershell pro and it has been a nice learning path for me to get more comfortable with it while solving actual problems.

Starting point

There are some prerequisities for using the scripts I’m about to introduce:

  1. Your deployment packages need to be stored in certain folder structure: root_folder/integration_name/version/
  2. You need to have some tooling in central location (for example BTSTask)

Generic functions

I have one powershell script that contains generic functions for doing the actual heavy lifting. This way there is less copy-paste and the integration solution specific scripts can be kept as simple as possible. Fixing bugs and adding new logic can be also done by changing one script instead of tens of scripts.

The generic script contains two types of functions: ones for having dialog with the user and ones for excecuting the deployment tasks. If the deployment solution specific script is run without giving any command line parameters, then the user is asked to give those. That is the “normal” way of running the scripts. For “powerusers” there are parameters for giving the environment parameter and automatically deploying the latest version possible.

As an example here is one of the functions to get the idea what the general script contains:

    Function startOrchestration($orch)
      write-Host ""
      write-Host "|-------------------------------------------------------------------------------------------------------|"
      write-Host "| Starting orchestrations                                                                               |"
      write-Host "|-------------------------------------------------------------------------------------------------------|"
      write-Host ""
      write-Host "$orch"        
      write-Host ""
      $orch_param = "Name='$orch'"
        $orchestration = get-wmiobject MSBTS_Orchestration `
        -namespace 'root\MicrosoftBizTalkServer' `
        -filter $orch_param
        if ($orchestration)
          write-Host ""
          write-host -foregroundcolor "yellow" "Could not find orchestration $orch"
          write-Host ""
        write-host -foregroundcolor "red" "$_.Exception.Message"
        return $FALSE
      return $TRUE

This function starts given orchestration and prints some execution info also to the console. If orchestration is not found, an warning message is printed. The caller receives true/false depending of the result of the execution.

Calling this function takes only one line in the solution specific script:

    $ok = startOrchestration -orch "orch_name_goes_here"

I have created a gist containing the functions.

Solution specific scripts

Setting up solution specific scripts involves defining few parameters related to solution identification (names, folders, erc) + setting up the process itself. Takes about 5 minutes if the solution is not very complex. The script still contains some static parts that could probably be simplified or moved outside the solution specific script. Here is a tear down of an example script:

In the beginning there is a part where you define some names and folders:

    $integrationname = "Friendly name for your integration here. Shows in UI"
    $integrationfolder = "Folder name of the components related to this integration"
    $application = "BTS Application name for this integration"
    $destinationRoot="c:\ProgramFiles (x86)\Integrations\"

Destination root defines where deployment process stores the deployed binaries.

Next part that requires attention is setting up environment specific parameters, usually this involves bindings:

    If ($env -eq "DEV") {
      $bindings = "$deploymentpath\$integrationfolder\$version\Bindings\"

Before this stage, environment parameters is already set so you can have section for each of you environments.

The final part to modify is the actual process. This obviously varies from integration to integration, but by using the generic functions from the common script, also this part can be kept rather simple and readable. Here is an example of the whole script:

So what happens when the script is executed (without parameters)? Obviously it will fail as the contents of the example are rubbish, but the dialog still works:

First the info about the integration printed, name of the integration comes from the configuration of the script. After that user is asked for the environment and the version. Once that is done, user needs to give the final go before the actual deployment is started. This time it failed as I hadn’t set up the parameters for my host in the generic functions and an error is printed. But you probably got the idea.


I have described a simple CI-like process that can be used to add more control to the deployment process when using BizTalk Server. In addition to that, I have shown how you can set-up powershell scripts to support the described process. This approach still has more manual steps than I would like and relies on humans doing what they are supposed to do, so it is far from perfect. But if you are still managing your deployments without any fixed process and in “all manual” mode, I hopefully have given some ideas how to improve your situation.

As I don’t have commenting set up yet in the blog, I would be more than happy to hear what you think about this approach in twitter.

My name is Juha Ryhänen. I’m interested in everything related to productivity, remote work, automation and cool gadgets. This is my personal website where I write about the things I find interesting. Maybe you do too? [More]

+358 50 543 4543 | [email protected] | Twitter