views:

948

answers:

2

We have TFS 2008 our build set up to checkout all AssemblyInfo.cs files in the project, update them with AssemblyInfoTask, and then either undo the checkout or checkin depending on whether the build passed or not. Unfortunately, when two builds are queued close together this results in a Partially completed build as the AssemblyInfo.cs files seem to be checked out at an earlier version to the previous checkin.

In order to get around this I thought that I could use the "Get" task to force the AssemblyInfo.cs files to the latest version before updating them, but this appears to have no effect. Any ideas?

<Target Name="AfterGet" Condition="'$(IsDesktopBuild)'!='true'">
<Message Text="SolutionRoot = $(SolutionRoot)" />
<Message Text="OutDir = $(OutDir)" />
<!-- Set the AssemblyInfoFiles items dynamically -->
<CreateItem Include="$(SolutionRoot)\Main\Source\InputApplicationSln\**\$(AssemblyInfoSpec)">
  <Output ItemName="AssemblyInfoFiles" TaskParameter="Include" />
</CreateItem>

<Message Text="$(AssemblyInfoFiles)" />

<!-- When builds are queued up successively, it is possible for the next build to be set up before the AssemblyInfoSpec is checked in so we need to force 
    the latest these versions of these files to be got before a checkout -->
<Get Condition=" '$(SkipGet)'!='true' " TeamFoundationServerUrl="$(TeamFoundationServerUrl)" Workspace="$(WorkspaceName)" Filespec="$(AssemblyInfoSpec)"  Recursive="$(RecursiveGet)" Force="$(ForceGet)" />

<Exec WorkingDirectory="$(SolutionRoot)\Main\Source\InputApplicationSln"
    Command="$(TF) checkout /recursive $(AssemblyInfoSpec)"/>

+1  A: 

Does your build re-write the AssemblyInfo files and then check them back in? Or do you just modify the AssemblyInfo files locally. Personally I prefer the latter approach - as documented over at the TFSBuild recipies site:

http://tfsbuild.com/AssemblyVersioning%20.ashx

I've never actually sat down and checked but I was wondering if you checked in the AssemblyInfo files then could the following be happening which might be causing your problems...

  1. Request a build, current changeset = 42
  2. Build 1 for changeset 42 starts running
  3. Request a build, current changeset = 42 (still)
  4. Build 2 for changeset 42 queued
  5. Build 1 checks in new assemblyinfo files, current changeset = 43
  6. Build 1 completes
  7. Build 2 for changeset 42 starts, dows a get of changeset 42 meaning AssemblyInfo files are the fold ones.

As I say, not exactly sure when the changeset number is determined for the build - at the time of queuing or at the time of running. It would make more sense for it to be at the time of queueing though.

Martin Woodward
You're right, we check out, modify and then, once the build has succeeded, check in again. This is to make sure that the modified AssemblyInfo.cs matches our modified build number and to help if we need to rebuild a previous version. I'm assuming the second get command isn't the way to go?
Damien Ryan
A: 

Changing:

<Get Condition=" '$(SkipGet)'!='true' " TeamFoundationServerUrl="$(TeamFoundationServerUrl)" Workspace="$(WorkspaceName)" Filespec="$(AssemblyInfoSpec)"  Recursive="$(RecursiveGet)" Force="$(ForceGet)" />

To:

<Get Condition=" '$(SkipGet)'!='true' " TeamFoundationServerUrl="$(TeamFoundationServerUrl)" Workspace="$(WorkspaceName)" Filespec="$(AssemblyInfoSpec)"  Recursive="True" Force="True" />

Has forced the AssemblyInfo.cs files to be overwritten with top of tree. It's been working so far, but is more of a hack than something elegant.

Damien Ryan