Showing posts with label How To:. Show all posts
Showing posts with label How To:. Show all posts

15 June 2010

Removing “Stuck” TFS 2008 Build Controllers

When migrating from Team Foundation Server 2008 to Team Foundation Server 2010 the TFS 2008 build controllers are included.  Even if you’ve setup and configured new build controllers for TFS 2010, you will still see the old (TFS 2008) build controllers in the Manage Build Controllers dialog (note: to display the Manage Build Controllers dialog, expand a team project’s node in Team Explorer, right-click on the Builds node, and select Manage Build Controllers).

In the screen shot below, you can see the Default Build Controller for TFS 2010 at the top along with ten build agents below (spread across five build machines).  At the bottom, there are two build controllers left over from TFS 2008.  Note that the Status is set to “Offline”.  If you no longer need the old (TFS 2008) build controllers, you can select them and click on the Remove button.  In most cases, this works as expected – the build controllers go bye-bye.

Manage Build Controllers

In some cases, you might get a dialog like this:

Can't Delete Build Controller

This dialog is telling you that one or more builds were in a Queued state when TFS 2008 was migrated to TFS 2010.  Since it thinks a build is active/queued, it will not allow you to delete the old build controller.

So, how do you get rid of the build controller?  All you have to do is locate the offending builds (left over from TFS 2008) and cancel them.  Sounds simple, right?  The problem is that there is no built-in mechanism for viewing a list of all queued builds across all build agents for a build controller.  So, you have a couple of choices:

  1. Go through the builds for each of your team projects one-by-one looking for queued builds.  This approach is simple enough if you have only a few team projects.  But what if you have dozens or hundreds?
  2. Locate the queued builds by querying the TFS transactional database.  This option does require at least “Read” access to the Team Project Collection (TPC) database.

Following step 2 above, to get a list of queued builds, run the following SQL script (using the correct collection database name):

SELECT bc.DisplayName, bq.DropLocation, bc.QueueCount, bc.Status
  FROM [Tfs_DefaultCollection].[dbo].[tbl_BuildController] bc
  JOIN [Tfs_DefaultCollection].[dbo].[tbl_BuildQueue] bq ON
bc.ControllerId = bq.ControllerId
WHERE bc.Status = 2 -- Queued
ORDER BY bc.DisplayName

This will give you a list of results including all builds currently in a “Queued” state.  For example:

DisplayName       DropLocation         QueueCount  Status
OLD-Controller1\  \\DropMachine\Proj1  3           2
OLD-Controller2\  \\DropMachine\Proj2  3           2

Using the information above, you should be able to determine which project(s) have queued builds lingering around.

Armed with this information, expand the desired team project in Team Explorer, right-click on the Builds node, and select View Builds.

View Builds

Click on the Queued tab, and if necessary, modify the filters to display all queued builds.  You should now see the queued build in the list.

Show Queued Builds

To cancel the build, simply right-click the desired build in the list and select Cancel.  If there are any remaining builds in your list, simply repeat these steps until all desired builds have been cancelled.

Cancel Build

Once the builds have been cancelled, you should be able to remove the old build controllers from the list as shown above (via the Manage Build Controllers dialog).

As an alternative to the “search-and-cancel” process above, you can also set the value of the tbl_BuildQueue.Status column to 16 – for “Cancelled” (for each of the builds to be cancelled).  This has the same effect as manually cancelling a build in the Build Explorer but it does require rights to update the data in the database.

25 November 2008

How To: Skip Actions When Queuing a Build

One of the tasks we commonly build into our Team Build scripts is the ability to run FitNesse tests along with other tests (such as unit tests).  If any of the tests fail, we do not deploy the product for user acceptance testing.

The advantage to this approach is that we find out relatively quickly if we have "broke" the build if we have failing tests.  The down side to this is two-fold: 1) the build takes longer to run (not that big of an issue in our case) and 2) Sometimes we refactor code that should break the FitNesse tests.

In the latter case, it may take somebody several hours (or even sometimes, days) to review the failing tests and get them corrected.  In the meantime, none of our updates get deployed for further testing.

Properties to the Rescue

Some time ago, I wrote a short post explaining how to access the various properties, items, and meta data that you can define and/or make use of in your Team Build scripts.  By making use of a simple property declared within the build script we can allow the developers to queue a new build and override the execution of the FitNesse tests so the build can proceed.  Configuring the build script to achieve this requires three steps:

1. Create a custom property that will be used as a flag to determine whether the desired functionality should be executed or overridden (i.e. skipped).  In my example below, I named the property SkipFitNesse.

<PropertyGroup> 
  <SkipFitNesse>false</SkipFitNesse>
</PropertyGroup>

2. Place the task(s) to be executed into a custom target specifying a condition.  For example:

<Target Name="RunFitNesseTests" Condition="'$(SkipFitNesse)' == 'false'">
  < tasks go here... />
</Target>

Notice that the property name, SkipFitNesse, is used in the condition.  As long as it remains set to its default value (in this case, false) the target will execute.

3.  Call the target at the desired point from within the build script.  In the example below, I am calling the target to run the FitNesse tests in the <AfterCompile> target.

<Target Name="AfterCompile" Condition="'$(IsDesktopBuild)'!='true'"> 
   <!-- Run FitNesse tests for Risk Rating -->
  <CallTarget Targets="RunFitNesseTests"/>
</Target>

Now that the build script is setup, you can manually override the execution of the FitNesse tests when you queue a new build by entering the following text into the command-line arguments field:

    /p:SkipFitNesse=true

For example:

queue

With this approach, the developers on our team now have a quick and simple method for skipping the execution of FitNesse tests if they are known to be in a "non-passing" condition and we want the build to continue.  This is only one example of how you might override the value of a property on the queue build dialog.  There are undoubtedly countless uses for this technique.

Also, if you're interested in seeing how we execute FitNesse tests as part of our builds, check out this post.