woensdag 9 mei 2012

Automated BizTalk Deployment



Introduction

At one of our customers, I set up a BizTalk environment with several applications, like applications for warehouse, subsidiary and customer interfaces. Some of these applications also use 2 separate servers, one in the internal network, and one in the DMZ network. These servers have completely different ports; for example. the DMZ server has ports connected to the outside world, which aren’t present on the internal server. Also, some applications are dependent on others, so deploying and undeploying has to be done in a specific order. To make this easy, I have set up a fully automatic BizTalk build and deployment setup. This is done by using PowerShell in combination with the BizTalk Deployment Framework. For my own reference, as well as for helping others set up an automated BizTalk deployment, I wrote this document. A basic understanding of BizTalk and PowerShell is needed to work with these examples. Special thanks go out to the blog of Randy Paulo.

BizTalk Software Factory

Although not necessary, the BizTalk Software Factory is a big help for creating BizTalk applications. When creating a new BizTalk solution with the BSF, it will create projects for all the different artifacts (pipelines, orchestrations, schema’s, etc.), as well as set up default BizTalk Deployment Framework items.

BizTalk Deployment Framework

The BizTalk Deployment Framework is a framework with which MSI’s can be created used for simple BizTalk deployments. The MSI’s include all the artifacts, as well as port bindings. By using place holders, the same binding file can be used for multiple environments, like development, test and production.
When you have created a new solution using the BTDF, you should start looking through your Deployment.btdfproj file and make changes where appropriate. Changes that should be made:
·         EnableSideBySide should be set to false if you do not want to run multiple instances of the application, leave this on true if you want to run multiple versions side by side.
·         Add <SkipIISReset>true</SkipIISReset> if you are not making use of IIS.
·         Add <ApplyXmlEscape>true</ApplyXmlEscape> if you want to have unescaped XML for better readability.
·         Add <RequireXmlPreprocessDirectives>false</RequireXmlPreprocessDirectives> so you do not need to have #ifdef around macros being substituted in PortBindingsMaster.xml and other XMLPreprocess'd files.
·         Set UseIsolatedAppDomain to false if the application does not need to run isolated.
·         If you do not want the receive locations to automatically start after deployment, for example to make sure everything was deployed correctly before starting to process the messages, add the following line:
<EnableAllReceiveLocationsOnDeploy>false</EnableAllReceiveLocationsOnDeploy>
Remove the <Transforms> and <Components> elements, we will be using another item group for this. After your <PropertyGroup Condition="'$(Configuration)' == 'Server'"> group, add the following (substitute or remove where needed):
<ItemGroup>
<Transforms Include="Company.Application.SubApplication1.Maps.dll">
<LocationPath>
..\Company.Application.SubApplication1.Maps\bin\$(Configuration)
</LocationPath>
</Transforms>
<Components Include ="Company.Application.SubApplication1.BusinessComponents.dll">
<LocationPath>
..\Company.Application.SubApplication1.BusinessComponents\bin\$(Configuration)
</LocationPath>
</Components>
<Components Include ="Company.Application.SubApplication1.PipelineComponents.dll">
<LocationPath>
..\Company.Application.SubApplication1.PipelineComponents\bin\$(Configuration)
</LocationPath>
</Components>
<Schemas Include ="Company.Application.SubApplication1.Schemas.dll">
<LocationPath>
..\Company.Application.SubApplication1.Schemas\bin\$(Configuration)
</LocationPath>
</Schemas>
<Orchestrations Include ="Company.Application.SubApplication1.Orchestrations.dll">
<LocationPath>
..\Company.Application.SubApplication1.Orchestrations\bin\$(Configuration)
</LocationPath>
</Orchestrations>
</ItemGroup>
Change <PortBindings>PortBindingsMaster.xml</PortBindings> to <PortBindings>PortBindings.xml</PortBindings>, so the PortBindingsMaster.xml file will be copied when deploying, and you can use the place holders for the different environments.
Change <FilesToXmlPreprocess> </FilesToXmlPreprocess> to <FilesToXmlPreprocess>PortBindings.xml</FilesToXmlPreprocess>, so the place holders will get the correct values when deployed.
·         Make sure to set a unique ProductID and ProductUpgradeCode.
·         If your application references other application (like an application with shared objects, or the BizTalk EDI application), add the following:
<ItemGroup>
<AppsToReference Include=" Company.Application.SharedObjects"/>
<AppsToReference Include="BizTalk EDI Application"/>
</ItemGroup>
Now to be able to automatically create the ports and receive locations, we will need a port bindings file. To create this, first deploy the application as you would normally do, and create all ports and such. Now export a bindings file. To make sure the bindings file can be used by the BTDF, run the following command from the commandline: ElementTunnel.exe /i:ExportedBindingsFile.xml /x:adapterXPaths.txt /o:PortBindingsMaster.xml /decode. ElementTunnel and adapterXPaths.txt can be found in the BTDF installation folder under Framework\DeployTools. When done, add the created PortBindingsMaster.xml to the BizTalk solution.
To be able to use this binding file in multiple environments, open the file and replace settings that can be different for the environments by placeholders. The placeholder should be in a format like ${PlaceHolderName}. You will probably want to do this for all addresses, but may also want to do this for timeouts, ports, usernames etc.
Once you have added all placeholders in the PortBindingsMaster.xml file, you can open the SettingsFileGenerator.xml file with Microsoft Excel, and add all the placeholders you just created to this file. If you do not see this file in your solution, just choose to add an existing file in your solution, and choose it from {Solution Folder}\Deployment\EnvironmentSettings. Here you can add the placeholders in the left most column, and add the respective values in the other columns. One important thing here is to make sure the Settings File Name is the same in all your SettingsFileGenerator files, otherwise our PowerShell script will have a problem later on.

PowerShell

For automating the building and deployment of your BizTalk applications, you will be using PowerShell scripts. First make sure PowerShell is enabled on your servers. We will need to adjust the execution policy to make sure we can run all necessary commands. Open a new PowerShell command line and execute the following command: Set-ExecutionPolicy Unrestricted. Next we will install the BizTalk PowerShell Provider so we can use PowerShell to work with BizTalk. Simply choose default settings for the installation.

Build script

We will start with a script that builds the BizTalk applications and copies the resulting installation files to a directory. You can also choose to copy the files to a shared folder, so they can be used by all your servers. We will also archive the older installations, so we can revert to a previous set of applications.
We start with creating a function that will build the project. This is done using MSBuild.
#
# This script is used to build the BizTalk solutions and create the MSI Installer packages.
# After this is done all necessary files will be copied to a location accessible to all BizTalk servers.
#

# Functions

#
# Function rebuilds a project in the given mode
# Project is the name of the project
#
function RebuildProject ( $project)
{
# Write to the prompt
Write-Host($mode + " " + $project)

# Set the directory of the project
$solutionDir = $baseDir + $project
# Set the solution file to be used
$solutionFile = $project + ".sln"

# Set options for the MSBuild process
$options = $verbosity + "/nologo /p:Configuration=" + $mode

# This will use MSBuild to clean the output directory of the solution
$clean = $msbuild + " " + $solutionFile + " " + $options + " /t:Clean"
# This will use MSBuild to build the solution
$build = $msbuild + " " + $solutionFile + " " + $options

# Go to the directory of the solution
cd $solutionDir

# Clean the solution output directory
Invoke-Expression $clean
# Build the solution
Invoke-Expression $build
}
The next function will create the MSI installers. This is done by using MSBuild in conjunction with the BizTalk Deployment Framework. After the installers have been created, they are being copied to a directory specified in your properties.
#
# Function builds the MSI installer
# Project is the name of the project
# DeploymentType can be used to create extra MSI packages for different deployment environments for the same application
# For example, a LAN and DMZ server with different ports for the same application
# The name of the BTDF project file should be something like Company.BizTalk.Test.Lan.Deployment.btdfproj
#
function BuildMsi ($project, $deploymentType)
{
# Check if a deployment type was provided
if($deploymentType -ne $null -and $deploymentType -ne "")
{
# If so, it should be proceeded by a dot
$deploymentType = "." + $deploymentType
}

# The directory of the deployment files
$solutionDir = $baseDir + $project + "\" + $project + ".Deployment"
# The directory where the installer will be built
$msiDir = $solutionDir + "\bin\" + $mode
# The location of the BTDF project file
$solutionFile = $solutionDir + "\" + $project + $deploymentType + ".Deployment.btdfproj"
# Options used by MSBuild
$options = " /nologo /t:Installer /p:Configuration=" + $mode
# Use MSBuild to build the installer
$build = $msbuild + " " + $solutionFile + " " + $options
# Build the installer
Invoke-Expression $build

# Copy the installer to the directory containing all installation files
Copy-Item ($msiDir + "\*.msi") $installersDir
}
Now we create a function that will copy any additional files we want to the same location as where the installers are being placed. In this case, we copy the PowerShell script that will be used to deploy the applications.
# Copy additional files to the directory containing all installation files
function CopyAdditionalFiles()
{
# Copy script used to do deployment
Copy-Item $serverDeployFile $installersDir
}
The last function we need to create is used to make a backup of the old installers. This way, you will always have the possibility to revert to a previous installation if something is incorrect.
# Create a backup of the current installers
function BackupInstallers()
{
# Get the currect date and time
$currentDateTime = (Get-Date -format s).Replace(":", "")
# Set the directory where we will want to store the backup
$backupDir = $installersDir + "\History\" + $currentDateTime
# Create backup directory
New-Item $backupDir -type directory
# Copy all the MSI and PowerShell files from the directory containing all installation files to the backup directory
Copy-Item ($installersDir + "\*.msi") $backupDir
Copy-Item ($installersDir + "\*.ps1") $backupDir
}
Now that we have created all functions, we will set the properties that are used in the script.
################################ Set your own properties here ##################################

# Parameters
# Base directory where all the related files can be found
$baseDir = "C:\Source\Company\"

# Build mode for building the BizTalk applications, can be Release or Debug
$mode = "Release"

# Directory where the finished MSI installers will be placed
$installersDir = "C:\Installers"

# Location of the PowerShell script used to do deployment on the servers
# Will be copied to the finished installers directory
$serverDeployFile = $baseDir + "Additional\Power shell\Deploy.ps1"

# Used applications
# Location of MSBuild
$msbuild = "C:\Windows\Microsoft.NET\Framework\v3.5\MSBuild.exe"

#
# The verbosity level posible values are:
# The available verbosity levels are q[uiet], m[inimal], n[ormal], d[etailed], and diag[nostic]
#
$verbosity = " /v:q "

################################ Done ##########################################################
Finally, we use all this to do the actual work. Start by creating a backup of your old installers.
# Do work
Write-Host "Backup old installers"

# Do Backup
BackupInstallers
Next we build the BizTalk applications. By doing this, we always make sure the applications are built in the correct order. Add a line for each of your applications.
Write-Host "Building the solutions"

################ Set your own projects here ###############

# Build solutions
RebuildProject "Company.BizTalk.CommonFiles"
RebuildProject "Company.BizTalk.Test1"
RebuildProject "Company.BizTalk.Test2"

######################### Done ############################
Now that the applications are built, we can create the MSI installers. For our customer, for some applications we wanted different versions for the LAN (internal) and DMZ servers, which is also being handled here.
Write-Host("Building MSI packages") -Fore DarkGreen

################ Set your own projects here ###############

# Create MSI installers
BuildMsi "Company.BizTalk.CommonFiles"
BuildMsi "Company.BizTalk.Test1"
BuildMsi "Company.BizTalk.Test2" "Lan"
BuildMsi "Company.BizTalk.Test2" "Dmz"

####################### Finished ##########################
When this has been done, we copy any additional files we may need to the output folder. When this is done, the application is finished, and will wait for the user to press a key before it exits. This is done so the user can check for any errors.

Write-Host("Copying additional files") -Fore DarkGreen

# Copy additional files
CopyAdditionalFiles

Write-Host("Press any key to exit...") -Fore White
$null = $host.UI.RawUI.ReadKey("NoEcho,IncludeKeyDown")

Deploy script

After copying the files we just created to the server where we want to do the deployment, we will want to automate this deployment as well. I created a script for this as well. We start with initializing the PowerShell provider, so we can use all the functions provided.
#
# Function initializes the PowerShell for BizTalk provider.
#
function InitPowerShellForBizTalk
{
# Check if the snap-in is allready loaded
if ( (Get-PSSnapin -Name BizTalkFactory.PowerShell.Extensions -ErrorAction SilentlyContinue) -eq $null )
{
# If not, add the snap-in
Write-Host "Initializing PowerShell provider" -ForegroundColor Cyan
Add-PSSnapIn BizTalkFactory.PowerShell.Extensions

# Set locations
Function Biztalk: { Set-Location Biztalk: }
Function Biztalk:\ { Set-Location Biztalk:\ }

# Set aliases
Set-Alias Enlist-SendPort Stop-SendPort
}
}
Now we create a function that is used to determine the path of the MSBuild application. I found that with MSBuild 4 we get an error if we want to deploy to the SSO as well, so we will need to use version 3.5. The error I got was as following:
The "UpdateSSOConfigItem" task failed unexpectedly.\r
System.ArgumentNullException: Value cannot be null.\r
Parameter name: s\r
at System.IO.StringReader..ctor(String s)\r
at SSOSettingsFileManager.SSOSettingsFileReader.Read(String affiliateApplication)\r
at DeploymentFramework.BuildTasks.UpdateSSOConfigItem.Execute()\r

The code for the method is as following:
#
# This script is used to build the BizTalk solutions and create the MSI Installer packages.
# After this is done all necessary files will be copied to a location accessible to all BizTalk servers.
#

# Functions

#
# Get the path of the MSBuild application
#
function GetMSBuildPath
{
# Check if the MSBuild executable can be found
if (Test-Path ( Join-Path $env:windir "Microsoft.NET\Framework\v3.5\MSBuild.exe" ))
{
# If so, set the executable to be used
$BTDFMSBuildPath = Join-Path $env:windir "Microsoft.NET\Framework\v3.5\MSBuild.exe"
Write-Host " Using MSBuild $dotNetVersion" -ForegroundColor DarkGray
return $BTDFMSBuildPath
}
else
{
Write-Error " MSBuild not found."
return ""
}
}
Using the BizTalk Deployment Framework, we don’t just deploy the applications, but we install them as well. However, before installing and deploying the new version, we have to undeploy and deinstall the old one first. This function is used to do just that.
#
# Function removes an application from the system
#
function RemoveApplication([string]$applicationName, [string]$versionNumber, [string]$guid)
{
# Write to prompt
Write-Host("")
Write-Host("Removing application " + $ApplicationName) -Fore Cyan
# Set the folder where the installation was installed
$applicationInstallFolder = $applicationInstallPath + "\" + $applicationName + "\" + $versionNumber
# Write to prompt
Write-Host("Undeploying application")
# The script to be executed for undeploying the application
$script =
{
#Assign MS Build Params
$BTDFMSBuildPath = GetMSBuildPath
$parms="DeployBizTalkMgmtDB=$BTDeployMgmtDB;Configuration=Server"
$logger="FileLogger,Microsoft.Build.Engine;logfile=`"" + ( Join-Path $applicationInstallFolder "DeployResults\DeployResults.txt" ) + "`""
$btdfFile="`"" + (Join-Path $applicationInstallFolder ("Deployment\" + $applicationName + ".Deployment.btdfproj")) + "`""
$args = "/p:{1} /target:Undeploy /l:{2} {0}" -f $btdfFile,$parms,$logger

# Write to prompt
Write-Host " Executing MSBuild from: $BTDFMSBuildPath" -ForegroundColor Cyan
Write-Host " ArgList: $args" -ForegroundColor DarkGray

# Get MSBuild return code
$exitCode = (Start-Process -FilePath $BTDFMSBuildPath -ArgumentList $args -Wait -Passthru).ExitCode
# Write to prompt
Write-Host " Exit Code: $exitCode"
Write-Host ""
Write-Host " Copying Log file."
# Copy to log file
$args = "Deployment\Framework\CopyDeployResults.msbuild /nologo"
Start-Process -FilePath $BTDFMSBuildPath -ArgumentList $args
# Check if MSBuild was succesful
if($exitCode -ne 0)
{
# If not, write to prompt
Write-Error " Error while calling MSBuild, Exit Code: $exitCode"
# Do not continue
return
}
}
# Execute the MSBuild command
Invoke-Command -scriptblock $script

# Write to prompt
Write-Host("Uninstalling application Company.BizTalk." + $applicationName)
# The script to be executed for uninstalling the application
$script =
{
# The MSI file for the application to be uninstalled
$msiFile = "Company.BizTalk." + $applicationName + "-" + $VersionNumber + ".msi"
# Uninstall arguments for the MSI file
$args = "/qn /x " + $guid
# Write to prompt
Write-Host " Uninstalling MSI File.." -ForegroundColor Cyan
Write-Host " MSI File: $msiFile" -ForegroundColor DarkGray
Write-Host " Args: $args" -ForegroundColor DarkGray

# Get the return code
$exitCode = (Start-Process -FilePath "msiexec.exe" -ArgumentList $args -Wait -Passthru).ExitCode
# Write to prompt
Write-Host " Exit Code: $exitCode"

# Check if uninstalling was succesful
if($exitCode -ne 0)
{
# If not, write to prompt
Write-Error "Uninstalling $msiFile failed!, Exit Code: $exitCode"
# Do not continue
return
}
# Write to prompt
Write-Host " Uninstalled MSI success.." -ForegroundColor Green
Write-Host ""
}
# Execute the uninstall command
Invoke-Command -scriptblock $script
# Write to prompt
Write-Host "Removing finished" -Fore DarkCyan
}
Now we will create the function that does the installation and deployment of the new version of the application.
#
# Function installs an application on the system
#
function InstallApplication([string]$applicationName, [string]$version, [string]$environment)
{
# The MSI file of the application to be installed
$msiFile = $applicationName + "-" + $version + ".msi"

# The location where the application should be installed
$applicationInstallFolder = $applicationInstallPath + "\" + $ApplicationName + "\" + $version

# The script to be executed for installing the application
$script =
{
# Arguments used for installing the application
$args = "-i $msiFile INSTALLDIR=`"$applicationInstallFolder`" /qn /norestart"
# Write to prompt
Write-Host " Installing MSI File.." -ForegroundColor Cyan
Write-Host " MSI File: $msiFile" -ForegroundColor DarkGray
Write-Host " Args: $args" -ForegroundColor DarkGray

# Get the exit code from the MSI installation
$exitCode = (Start-Process -FilePath "msiexec.exe" -ArgumentList $args -Wait -Passthru).ExitCode
# Write to prompt
Write-Host " Exit Code: $exitCode"

# Check if installing was succesful
if($exitCode -ne 0)
{
# If not, write to prompt
Write-Error "Uninstalling $msiFile failed!, Exit Code: $exitCode"
# Do not continue
return
}
# Write to prompt
Write-Host " Uninstalled MSI success.." -ForegroundColor Green
Write-Host ""
}
# Execute the install command
Invoke-Command -scriptblock $script

# The script to be executed for deploying the application
$script=
{
# Run environmentSettingsExporter, this one generates the xml file
# F.e. Exported_DevSettings.xml, Exported_TestSettings.xml etc..
$args = "`"" + (Join-Path $applicationInstallFolder "Deployment\environmentSettings\SettingsFileGenerator.xml") + "`"" + " Deployment\environmentSettings"
$exePath = ("`"" + (Join-Path $applicationInstallFolder "\Deployment\Framework\DeployTools\environmentSettingsExporter.exe") + "`"")
# Write to prompt
Write-Host " Generating environment Settings File.." -ForegroundColor Cyan
Write-Host " Location: $exePath" -ForegroundColor DarkGray
Write-Host " Args: $args" -ForegroundColor DarkGray

# Get the exit code
$exitCode = (Start-Process -FilePath $exePath -ArgumentList $args -Wait -PassThru).ExitCode
# Write to prompt
Write-Host " Exit Code: $exitCode"

# Check if exporting the environment settings was succesful
if($exitCode -ne 0)
{
# Write to prompt if this failed
Write-Error " Generating environment Settings File failed!, Exit Code: $exitCode"
# Do not continue
return
}
# Write to prompt
Write-Host " Generated environment Settings File. " -ForegroundColor Green
Write-Host ""
# Set the environment variables ENV_SETTINGS and BT_DEPLOY_MGMT_DB
$settingsFile = "Deployment\environmentSettings\Exported_{0}Settings.xml" -f $environment
$EnvSettings = Join-Path $applicationInstallFolder $settingsFile

# Write to prompt
Write-Host " Setting environment Variables" -ForegroundColor Cyan
Write-Host " ENV_SETTINGS = $EnvSettings" -ForegroundColor DarkGray;
# Set environment settings
Set-Item Env:\ENV_SETTINGS -Value $EnvSettings

# Write to prompt
Write-Host " BT_DEPLOY_MGMT_DB = $BTDeployMgmtDB" -ForegroundColor DarkGray;
# Set BT_DEPLOY_MGMT_DB
Set-Item Env:\BT_DEPLOY_MGMT_DB -Value $BTDeployMgmtDB

# Write to prompt
Write-Host " Setted environment Variables" -ForegroundColor Green
Write-Host ""

# Assign MSBuild parameters
$BTDFMSBuildPath = GetMSBuildPath
$parms="DeployBizTalkMgmtDB=$BTDeployMgmtDB;Configuration=Server;SkipUndeploy=$SkipUndeploy"
$logger="FileLogger,Microsoft.Build.Engine;logfile=`"" + ( Join-Path $applicationInstallFolder "DeployResults\DeployResults.txt" ) + "`""
$btdfFile="`"" + (Join-Path $applicationInstallFolder ("Deployment\" + $ApplicationName + ".Deployment.btdfproj")) + "`""
$args = "/p:{1} /l:{2} {0}" -f $btdfFile,$parms,$logger

# Write to prompt
Write-Host " Executing MSBuild from: $BTDFMSBuildPath" -ForegroundColor Cyan
Write-Host " ArgList: $args" -ForegroundColor DarkGray

# get MSBuild return code
$exitCode = (Start-Process -FilePath $BTDFMSBuildPath -ArgumentList $args -Wait -Passthru).ExitCode
# Write to prompt
Write-Host " Exit Code: $exitCode"
Write-Host ""
# Check if MSBuild was succesful
if($exitCode -ne 0)
{
# If not, write to prompt
Write-Error " Error while calling MSBuild, Exit Code: $exitCode"
# Do not continue
return
}

# Write to prompt
Write-Host " Copying Log file."
# Copy Log File
$args = "Deployment\Framework\CopyDeployResults.msbuild /nologo"
Start-Process -FilePath $BTDFMSBuildPath -ArgumentList $args
}

# Write to prompt
Write-Host " Running MS Build and deploying.." -ForegroundColor Cyan
# Execute the script
Invoke-Command -scriptblock $script
# Write to prompt
Write-Host " Deployed application" -ForegroundColor Green
}
Also we need a function used to add assemblies as resources to the BizTalk applications.
#
# Function adds an assembly resource to the provided BizTalk application
#
function AddAssemblyResource
{
param(
[Parameter(Position=0,Mandatory=$true,HelpMessage="An application name should be provided")]
[Alias("application")]
[string]$applicationName,
[Parameter(Position=1,Mandatory=$true,HelpMessage="Please provide a valid resource")]
[Alias("res")]
[string]$resource
)
# Add the resource to the application, overwriting if it allready exists
New-Item -Path BizTalk:\Applications\$applicationName\Resources\NameIgnored `
-ItemType System.BizTalk:Assembly `
-SourceLocation $resource `
-GacOnAdd `
-Overwrite}

Now that we have created all the functions, we will set the properties that are being used throughout the script.

################################ Set your own properties here ##################################

# Parameters
# Base path for application installs
[string]$applicationInstallPath = "C:\Program Files"

# The environment to which we want to deploy (f.e. production or test
[string]$deploymentEnvironment

# Boolean indicating if we want to deploy to the management database
[bool]$BTDeployMgmtDB=$true

# Boolean indicating if we want to skip undeploying when doing the deployment (can normally be set to true, since we do undeployment manually)
[bool]$SkipUndeploy=$true

################################ Done ##########################################################
Because we had the different types of servers, we want to be able to set on which server we are deploying. The next command reads the input of the user for this.
# Let the user select the type of deployment they want to do
function SelectDeploymentType
{
# Get input from the user
$dType = Read-Host -prompt ("What type of deployment do you want to do? LAN / DMZ / OTHER") -ForegroundColor Green
# Check what type of deployment the user selected
switch($dType)
{
"LAN"
{
return $dType
}
"DMZ"
{
return $dType
}
"OTHER"
{
return $dType
}
default
{
Write-Error " Please provide a valid deployment type!"
return SelectDeploymentType
}
}
}

We also want to let the user set the environment we are going to deploy to.
# Let the user select what type of environment they want to deploy to
function SelectDeploymentEnvironment
{
# Get input from the user
$dEnvironment = Read-Host -prompt ("What type of environment do you want to deploy to? DEV / TEST / ACCEPT / PROD") -ForegroundColor Green
# Check what type of environment the user selected
switch($dEnvironment)
{
"DEV"
{
$deploymentEnvironment = $dEnvironment
}
"TEST"
{
$deploymentEnvironment = $dEnvironment
}
"ACCEPT"
{
$deploymentEnvironment = $dEnvironment
}
"PROD"
{
$deploymentEnvironment = $dEnvironment
}
default
{
Write-Error " Please provide a valid environment!"
return SelectDeploymentEnvironment
}
}
}

Before we start the deployment, we initialize the BizTalk PowerShell provider.

# Initialize the PowerShell for BizTalk provider
InitPowerShellForBizTalk

Now we start undeploying and removing the applications. The applications that will be removed are determined by the server we are deploying to. Also, make sure you use the correct GUID’s here, it should be the ones you set in the BTDF project, as it is used to determine the application to be uninstalled.

# Get the type of deployment we want to do
$deploymentType = SelectDeploymentType

# Get the environment we want to deploy to
$deploymentEnvironment = SelectDeploymentEnvironment

# Write to prompt
Write-Host("Redeploying applications from Msi files...") -Fore DarkGreen

################ Set your own projects here ###############

# Uninstall the applications, make sure you use the GUID's you used in your BTDF project file
switch($deploymentType)
{
################ Set your own projects here ###############
"LAN"
{
RemoveApplication "Company.BizTalk.Test2.Lan" "1.0" "{850AF064-2DF2-4572-84FB-B6578565CC02}"
RemoveApplication "Company.BizTalk.Test1" "1.0" "{B60DF0FB-FDD6-4e9b-86A1-D37F777B4916}"
RemoveApplication "Company.BizTalk.Common" "1.0" "{DB073B98-310B-49C2-9128-1792900A2B62}"
}
"DMZ"
{
RemoveApplication "Company.BizTalk.Test2.Dmz" "1.0" "{850AF064-2DF2-4572-84FB-B6578565CC02}"
RemoveApplication "Company.BizTalk.Common" "1.0" "{DB073B98-310B-49C2-9128-1792900A2B62}"
}
"OTHER"
{
RemoveApplication "Company.BizTalk.Test2" "1.0" "{850AF064-2DF2-4572-84FB-B6578565CC02}"
RemoveApplication "Company.BizTalk.Test1" "1.0" "{B60DF0FB-FDD6-4e9b-86A1-D37F777B4916}"
RemoveApplication "Company.BizTalk.Common" "1.0" "{DB073B98-310B-49C2-9128-1792900A2B62}"
}
######################### Done ############################
}
Now we can install and deploy the new version of the applications, this is also done by checking which server we are deploying to.
# Install the application
switch($deploymentType)
{
################ Set your own projects here ###############
"LAN"
{
InstallApplication "Company.BizTalk.Common" "1.0" $deploymentEnvironment
InstallApplication "Company.BizTalk.Test1" "1.0" $deploymentEnvironment
InstallApplication "Company.BizTalk.Test2.Lan" "1.0" $deploymentEnvironment
}
"DMZ"
{
InstallApplication "Company.BizTalk.Common" "1.0" $deploymentEnvironment
InstallApplication "Company.BizTalk.Test2.Dmz" "1.0" $deploymentEnvironment

# In the DMZ, we also want to add the resource used for SFTP communication
AddAssemblyResource " Company.BizTalk.Common" "C:\Program Files\EldoS\BizCrypto.BizTalk\Assemblies\NET_20\BT2009\BizCrypto.BizTalk.DefaultPropertySchemas.dll"
}
"OTHER"
{
InstallApplication "Company.BizTalk.Common" "1.0" $deploymentEnvironment
InstallApplication "Company.BizTalk.Test1" "1.0" $deploymentEnvironment
InstallApplication "Company.BizTalk.Test2" "1.0" $deploymentEnvironment
}
######################### Done ############################
}
Now we are finished. Here we also wait for input from the user, so the output from the application can be reviewed.
# Do not close until the user presses a key
Write-Host("Press any key to exit...") -Fore White
$null = $host.UI.RawUI.ReadKey("NoEcho,IncludeKeyDown")

Geen opmerkingen:

Een reactie posten