TeamBuild 2010: UpdateAssemblyInfo activity sample

TeamBuild 2010: UpdateAssemblyInfo activity sample

As promized her is a sample of how i’m using the UpdateAssemblyInfo activity i’ve published on codeplex.

First let’s describe what we want:

  1. Increment the build number of my AssemblyFileVersion automatically for all the projects in a solution when doing a build. The major and minor versions of the AssemblyVersion and AssemblyFileVersion must not change and the revision number must be 0.
  2. Don’t modify the solution sources in TFS and let the developers do what they want.
  3. The BuildNumber of my build must contains the AssemblyFileVersion so that my build name, label and drop location are easily identifiable.
  4. Don’t modify the version numbers when doing a gated checkin or a private build.
  5. Be able to launch a build and specify to skip versionning.

Before updating our build template i’ll start by configuring my solution to make easier the versionning of all the projects. Let’s add a GlobalAssemblyInfo.cs (or .vb if you use VB.Net) file to the solution as a solution item:

image

This file will contains all assembly level attributes that we want to share between all our projects:

using System.Reflection;

[assembly: AssemblyDescription("Sample project for UpdateAssemblyInfo activity.")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("Qetza")]
[assembly: AssemblyProduct("UpdateAssemblyInfoSample")]
[assembly: AssemblyCopyright("Copyright © Guillaume Rouchon 2010")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

In this cas we share all attributes describing the assembly with the exception of the title (AssemblyTitle) and of course we share the AssemblyVersion and AssemblyFileVersion attributes. All we have to do now is add this file as a link in our projects:

image

It’s important to add this file as link so that the file is not duplicated! Now we need to modify the AssemblyInfo.cs files to remove the extra attributes. Our solution is now ready.

It’s time to customize our build template:

  1. Create a Workflow/ActivityLibrary project.
  2. Update the targeted framework to .Net Framework 4.
  3. Add the following references:
    • In C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\IDE\PrivateAssemblies
      • Microsoft.TeamFoundation.Build.Workflow.dll
      • Microsoft.TeamFoundation.TestImpact.BuildIntegration.dll
    • In C:\Windows\assembly\GAC_MSIL\Microsoft.TeamFoundation.TestImpact.Client\10.0.0.0__b03f5f7f11d50a3a
      • Microsoft.TeamFoundation.TestImpact.Client.dll
    • Qetza.TeamFoundation.Build.UpdateAssemblyInfo.dll
    • Microsoft.TeamFoundation.Build.Client.dll
    • Microsoft.TeamFoundation.VersionControl.Client.dll
    • Microsoft.TeamFoundation.WorkItemTracking.Client.dll
    • System.Drawing.
  4. Delete the default activity.
  5. Add a copy of DefaultTemplate.xaml to the project.

We are now ready to customize this file and add versionning support. Let’s see how we can meet the requirements specified at the start of this post:

  1. Requirement 1 explains how the version number must be updated. To meet this requirement we’ll pass the following parameters to the UpdateAssemblyInfo activity:
    • AssemblyVersionFormat : “$(current).$(current).0.0″
    • AssemblyFileVersionFormat : “$(current).$(current).$(increment).0″
  2. Our build number must be incremented at each build, we’ll need to store the last used number. Our requirement 2 gives a constraint, we cannot use the GlobalAssemblyInfo file from the solution because we must not modify the source code in TFS. The simplest method is store a copie of the GlobalAssemblyInfo file which we will use only for the build. Since TeamBuild 2010 doesn’t provides a Checkin activity, we’ll use a network share. Don’t forget to give read and write access to the file for the account you’re using for TeamBuild.
  3. Requirement 3 will force where we will add our customization. We will need to update our version numbers before setting the BuildNumber so that the build name, label and drop location uses the computed version.
  4. For meeting requirement 4, we will use a InvokeForReason activity configured with Triggered.
  5. We will add If activity based on a workflow argument to meet requirement 5.

Before updating the workflow let’s define some arguments that will be accessible will defining a build definition:

  • AssemblyVersionFormat : the format used to update the assembly version.
  • AssemblyFileVersionFormat : the format used to update the file version.
  • AssemblyInfoFilePattern : the pattern used to search files to update.

image

We’ll also need some variables:

  • UpdateAssemblyInfo : a boolean to indicate whether or not we will do versionning. It’s value will be based on the AssemblyInfoFilePattern value, if it’s empty no versionning will occure.
  • AssemblyInfoFiles : to store the names of the files to update.
  • MaxAssemblyVersion : to store the maximum assembly version after update.
  • MaxAssemblyFileVersion : to store the maximum file version after update.

image

We’ll now add the following workflow:

  • If UpdateAssemblyInfo
    • Then
      • InvokeForReason Triggered
        • FindMatchingFile AssemblyInfoFilePattern
        • UpdateAssemblyInfo
        • Assign BuildNumberFormat = “$(BuildDefinitionName)_v” + MaxAssemblyFileVersion

This workflow will be added before the “Update Drop Location” sequence:

image

With this workflow we have updated our GlobalAssemblyInfo file and have customized the BuildNumber and therefore the build name, the label and the drop location. But we still need to modify our build template, when compiling we’re still using the file from the source controller. We must add some activities in the BuildAgent part to replace the GlobalAssemblyInfo file of the solution with our updated one after getting the source and before compiling:

  • If UpdateAssemblyInfo
    • Then
      • InvokeForReason Triggered
        • CopyDirecgtory Path.GetDirectoryName(AssemblyInfoFilePattern) to SourcesDirectory

This workflow must be added before the “If CreateLabel”:

image

Our build template is now customized to use the UpdateAssemblyInfo activity to automatically update our version numbers.

Let’s enhanced this template by providing metadata to add descriptions to our arguments and group them in a “Versionning” category, this can be done by modifying the Metadata argument as follow:

image

Our template is now finished, we must now put everthing in TFS:

  • Add the template by replacing the existing DefaultTemplate.xaml template or add it under a new name.
  • Add the Qetza.TeamFoundation.Build.UpdateAssemblyInfo.dll assembly in TFS so that the build process can have access to it. (for example in a “BuildProcessTemplate/CustomActivities” folder under source control).
  • Update the build controller to indicates where custom assemblies are in TFS:

image

Last, we need to create a build definition on a project and queue a new build. When queuing a build, it’s possible to override default values (for example to force new major or minor version when building the first code of a new version):

image

And here’s the result:

image
It’s now time for you to establish some versionning policy and integrate them in TeamBuild 2010!

Carpe Diem.

You can find the solution i used for this post at the following url http://blog.qetza.net/wp-content/uploads/2010/08/UpdateAssemblyInfo_v1.0.1.0_Sample.zip.

Leave a Reply

  

  

  


5 − = four