So you’ve just finished creating a lovely shiny new web application. As you’re putting on your jacket, you think ‘Ah! I should quickly create an MSI installer…will only take a few minutes’…you sit back down, and remember the latest company directive that stated that Visual Studio Setup projects should not be used anymore…
No big deal…WIX 3.5 has been released, and is integrated into Visual Studio 2010…easy…
Reality check: no, it’s not quite as easy as you may be used to…so take off your jacket, hang it up, and crack open a can of sugar-free Red Bull before you start playing with WIX.
Don’t get me wrong: WIX is the way to go, but at this point in time if you want to create an installer for a web application you have a lot more work to do than for more traditional applications.
Step 1: Adjusting the Setup Project
So in this example, we have an ASP .NET 4 web application, and have created a WIX installer called MySetup. We then add a project reference to MyWebApp, and adjust that reference to specify we want to harvest the files:


We then make a minor adjustment to the Project.wxs file to specify MyCompany:
Product.wxs
<?xml version="1.0" encoding="UTF-8"?>
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
<Product Id="d5b59d53-5fbb-4dd4-a2ac-1e97d70710b3" Name="MySetup"
Language="1033"
Version="1.0.0.0" Manufacturer="MyCompany"
UpgradeCode="c72f2c40-88b1-4a8f-8800-1796cf0dbafe">
<Package InstallerVersion="200" Compressed="yes" />
<Media Id="1" Cabinet="media1.cab" EmbedCab="yes" />
<Directory Id="TARGETDIR" Name="SourceDir">
<Directory Id="ProgramFilesFolder">
<Directory Id="INSTALLLOCATION" Name="MySetup">
</Directory>
</Directory>
</Directory>
<Feature Id="ProductFeature" Title="MySetup" Level="1">
<ComponentGroupRef Id="Product.Generated" />
</Feature>
</Product>
</Wix>
We can then build, and run the generated MSI. However, at this point we have not put any UI in place, so we end up with our web application installed under Program Files in a folder called MySetup…not ideal, but we’ll get to that later.
If you take a look at the files that have been installed, you will quickly notice a problem: there is no bin folder, and the content of the bin folder has all been put into the root folder:

Clearly wrong. The solution is to adjust the project reference and edit the installer project as explained by Travis Illig in his post How to Consume MSDeploy Staged Web Site Output in a WIX Installer. After making this adjustments, we now end up with the following result:

Excellent. Thanks Travis! 
Step 2: Implementing Localisation
You may ask ‘why?’. Well, aside from the argument about broadening the reach of your product to support other cultures, we can make use of localisation to centralise our text in one place rather than having it spread across various files. This not only makes maintenance easier, but also makes reuse a whole lot easier.
So add a new WiX Localization File to your project and name it for the main language you are supporting (in my case English.wxl). We then fill it in with some text we can immediately make use of:
English.wxl
<?xml version="1.0" encoding="utf-8"?>
<WixLocalization Culture="en-us"
xmlns="http://schemas.microsoft.com/wix/2006/localization">
<String Id="LANG">1033</String>
<String Id="Comments">MyWebApp Comments</String>
<String Id="Description">MyWebApp Description</String>
<String Id="Keywords">MyWebApp</String>
<String Id="ProductName">MyWebApp</String>
<String Id="CompanyName">MyCompany</String>
</WixLocalization>
And adjust our Product.wxs to use the resource entries:
Product.wxs
<?xml version="1.0" encoding="UTF-8"?>
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
<Product Id="d5b59d53-5fbb-4dd4-a2ac-1e97d70710b3"
UpgradeCode="c72f2c40-88b1-4a8f-8800-1796cf0dbafe"
Version="1.0.0.0"
Name="!(loc.ProductName)"
Language="!(loc.LANG)"
Manufacturer="!(loc.CompanyName)">
<Package InstallerVersion="200" Compressed="yes"
Languages="!(loc.LANG)"
Manufacturer="!(loc.CompanyName)" Comments="!(loc.Comments)"
Description="!(loc.Description)" Keywords="!(loc.Keywords)"/>
<Media Id="1" Cabinet="media1.cab" EmbedCab="yes" />
<Directory Id="TARGETDIR" Name="SourceDir">
<Directory Id="ProgramFilesFolder">
<Directory Id="INSTALLLOCATION" Name="!(loc.ProductName)">
</Directory>
</Directory>
</Directory>
<Feature Id="ProductFeature" Title="!(loc.ProductName)" Level="1">
<ComponentGroupRef Id="MyWebApp_Project" />
<ComponentGroupRef Id="Product.Generated" />
</Feature>
</Product>
</Wix>
You can see how copy-and-paste followed by adjustment is a whole lot easier thanks to localisation, and also avoids string duplication (e.g. ProductName is used multiple times).
In the next post( s) , we’ll look at checking conditions, providing an interface and dealing with IIS.
Print | posted on Sunday, 20 February 2011 12:23 PM