How to insert an assembly version number into a WiX script at build time

Things have been quiet on this blog regarding Team Foundation Server… this isn’t from lack of interest, merely that the server is doing a great job taking care of itself and thereby leaving me to get on with other pleasures… such as documentation of project process.

Well, there was one thing, but I was somewhat ashamed to show it. It seems like when anyone creates a cool Powershell script in 5 lines of code, there will be some RegEx ninja who will jump in and splice it into 1.5 lines.

Well, first the scenario. We are using AssemblyInfoTask in the build project. Each time a build is kicked off, this task will go check out an AssemblyInfo.cs file of your choosing, and increment the assembly version number inside it. If the build is ultimately successful, it will then check this file back into source control with the new version.

The problem was that I had a WiX project that built the MSI, and there was no automatic way to pick up this assembly value and put it in as a variable.

Well, there is a way to get it in there.. you run a Powershell script during the build process, and update the WiX file whilst it is being built.

1 : you need to get a MSBuild task that can invoke Powershell.. I used this one.

6 : Add the following Powerscript file to the file system on your build machine. I called it ReplaceVersion.ps1, but you can name and place it where you want

#######################
# This function will extract assembly version from an AssemblyInfo.cs file
# and replace the value x.x.x.x in the destination file with this value
#######################
function replaceVersions([string]$assemblyFile, [string]$fileToFix)
{
# Get the whole line where ‘AssemblyFileInfo exists
$version = (select-string -pattern “AssemblyFileVersion” $assemblyFile) -replace ‘\”‘,”;

# Find the beginning of the version number
$beginIndex = ($version.IndexOf(“(“) + 1);

(Question: I thought to source control this.. but how much of a risk is that?? A developer could put any code they wanted inside it, and it would get called as part of the build process. That said, your build process should be running as a standard user anyhow)

I’m not really happy with this script, so if anyone wants to make it shorter, then feel free to let me know for the good of the community 🙂

_______________________________________________________

UPDATE: 27/09/2007

Already a couple of comments saying that this is a long hard way to do it… and you are right!

What I am looking for is:

Build my assemblies with TFS build

Update the minor version number of the assemblies

Get this assembly number used as a variable inside WiX 3.0

It doesn’t have to be Powershell.. if there is a simple setting in WiX that will allow me to do this then let me know!

_______________________________________________________

UPDATE: 31/10/2007

Morten Lyhr has an alternative solution, which I’m happy to advertise as an alternative.

He describes my solution as ‘clumsy’, and I guess everyone is entitled to their opinion 🙂

However I strongly disagree: once you have my powershell script on the system then there is not a great deal of configuration to do inside of the .proj file. His solution requires A LOT of hacking the project file, which I’m sure will cause major headaches down the road.

Because of this, I suggest mine is in fact more ‘elegant’.

What would be better, if I ever get the time, is just create an MSBuild task to handle this all in one stepI’m thinking just to create a new MSBuild task that can do all this in one step…

No, I’ve not done this. We’ve not moved to TFS; our build process is SVN/NAnt-based. We have a custom NAnt task that sets a property from the last-committed-revision for a particular branch, which we can then use in other tasks, including updating AssemblyInfo.cs, Version.rc or whatever.

I wanted to refute Christopher’s assertion that “WiX can’t catch up to InstallShield”, since WiX’s -dPRODUCTVERSION is equivalent to InstallShield’s -y, unless there’s some complexity I’m missing.