Geeks With Blogs


Jakob Ehn Visual Studio ALM MVP - Works @ActiveSE

*** UPDATE 2010-08-17 ** Several people have asked me for a complete sample application, so I have put this together and it is available here:


In this post I will show how to create a new build definition in TFS 2010 using the TFS API. When creating a build definition manually, using Team Explorer, the necessary steps are lined
out in the New Build Definition Wizard:




So, lets see how the code looks like, using the same order. To start off, we need to connect to TFS and get a reference to the IBuildServer object:

TfsTeamProjectCollection server = newTfsTeamProjectCollection(newUri("http://<tfs>:<port>/tfs"));
IBuildServer buildServer = (IBuildServer) server.GetService(typeof (IBuildServer));

First we create a IBuildDefinition object for the team project and set a name and description for it:

var buildDefinition = buildServer.CreateBuildDefinition(teamProject);
buildDefinition.Name = "TestBuild";
buildDefinition.Description = "description here...";

Next up, we set the trigger type. For this one, we set it to individual which corresponds to the Continuous Integration - Build each check-in trigger option

buildDefinition.ContinuousIntegrationType = ContinuousIntegrationType.Individual;

For the workspace mappings, we create two mappings here, where one is a cloak. Note the user of $(SourceDir) variable, which is expanded by Team Build into the sources directory when running the build.

buildDefinition.Workspace.AddMapping("$/Path/project.sln", "$(SourceDir)", WorkspaceMappingType.Map);
buildDefinition.Workspace.AddMapping("$/OtherPath/", "", WorkspaceMappingType.Cloak);

Build Defaults
In the build defaults, we set the build controller and the drop location. To get a build controller, we can (for example) use the GetBuildController method to get an existing build controller by name:

buildDefinition.BuildController = buildServer.GetBuildController(buildController);
buildDefinition.DefaultDropLocation = @\\SERVER\Drop\TestBuild;

So far, this wasy easy. Now we get to the tricky part. TFS 2010 Build is based on Windows Workflow 4.0. The build process is defined in a separate .XAML file called a Build Process Template. By default, every new team team project containtwo build process templates called DefaultTemplate and UpgradeTemplate. In this sample, we want to create a build definition using the default template. We use te QueryProcessTemplates method to get a reference to the default for the current team project

//Get default template
var defaultTemplate = buildServer.QueryProcessTemplates(teamProject).Where(p => p.TemplateType == ProcessTemplateType.Default).First();
buildDefinition.Process = defaultTemplate;


There are several build process templates that can be set for the default build process template. Only one of these are required, the ProjectsToBuild parameters which contains the solution(s) and configuration(s) that should be built. To set this info, we use the ProcessParameters property of thhe IBuildDefinition interface. The format of this property is actually just a serialized dictionary (IDictionary<string, object>) that maps a key (parameter name) to a value which can be any kind of object. This is rather messy, but fortunately, there is a helper class called WorkflowHelpers inthe Microsoft.TeamFoundation.Build.Workflow namespace, that simplifies working with this persistence format a bit. The following code shows how to set the BuildSettings information for a build definition:

//Set process parameters
varprocess = WorkflowHelpers.DeserializeProcessParameters(buildDefinition.ProcessParameters);

//Set BuildSettings properties
BuildSettings settings = newBuildSettings();
settings.ProjectsToBuild = newStringList("$/pathToProject/project.sln");
settings.PlatformConfigurations = newPlatformConfigurationList();
settings.PlatformConfigurations.Add(newPlatformConfiguration("Any CPU", "Debug"));
process.Add("BuildSettings", settings);

buildDefinition.ProcessParameters = WorkflowHelpers.SerializeProcessParameters(process);

The other build process parameters of a build definition can be set using the same approach


Retention  Policy
This one is easy, we just clear the default settings and set our own:

buildDefinition.AddRetentionPolicy(BuildReason.Triggered, BuildStatus.Succeeded, 10, DeleteOptions.All);
buildDefinition.AddRetentionPolicy(BuildReason.Triggered, BuildStatus.Failed, 10, DeleteOptions.All);
buildDefinition.AddRetentionPolicy(BuildReason.Triggered, BuildStatus.Stopped, 1, DeleteOptions.All);
buildDefinition.AddRetentionPolicy(BuildReason.Triggered, BuildStatus.PartiallySucceeded, 10, DeleteOptions.All);

Save It!
And we’re done, lets save the build definition:


That’s it!


Posted on Monday, April 26, 2010 8:09 PM TFS , Team Build , Visual Studio 2010 , TFS API | Back to top

Comments on this post: Creating a Build Definition using the TFS 2010 API

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
Hi Jokob, can you post an example of a working solution/project that can be downloaded?
Left by Bob Hardister on Aug 16, 2010 2:59 AM

# Here are some other setters. . .
Requesting Gravatar...
//Set BuildSettings properties
var settings = GenerateBuildSettings();
process.Add("BuildSettings", settings);
process.Add("TestSpecs", new TestSpecList());
process.Add("RunCodeAnalysis", CodeAnalysisOption.Never);
process.Add("SourceAndSymbolServerSettings", new SourceAndSymbolServerSettings());
process.Add("CreateWorkItem", false);
process.Add("PerformTestImpactAnalysis", false);
process.Add("DisableTests", true);
process.Add("Verbosity", BuildVerbosity.Minimal);
Left by Y.B on Sep 16, 2010 7:38 AM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
How can I run private Build (based on Shelveset) through the API?
Left by Shmil on Oct 11, 2010 4:13 AM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
The WorkflowHelpers class is inside a private assembly to Visual Studio. You are not allowed to use it. Fallback is to use the XamlServices.Save method in the System.Xaml assembly.
Left by Wouter van Vugt on Apr 08, 2011 11:00 AM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
How can I pass paramters through the build definition? Would adding a couple fields to dynamically created build definition be the best way to make that happen?
Left by Willow Wagner on May 17, 2011 3:55 PM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
Is there another link to download the complete sample application? The mentioned one above is broken.
Left by Cristian Casanova on Nov 12, 2012 11:49 PM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
Hi, thanks so much for post this. Everything is working great except 1 thing. This code only works the first time I run it. Subsequent attempts result in the followwing error: Sequence contains no elements.
So it finds the template the first time, but that's it.

var defaultTemplate = buildServer.QueryProcessTemplates(teamProject).Where(p => p.TemplateType == ProcessTemplateType.Default).First();

Thanks, John
Left by John Bruno on Apr 04, 2013 8:45 PM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
thanks for your post, its very helpfull. But I still got a question.
I want to add a RetentionPolicy, but i want to add multiple DeleteOptions, but i don't see a way to do this.
For example the delete options should be set to DropLocation, Label AND Symbols.
Thanks for your help.
Left by Tobi on Aug 11, 2014 10:19 AM

# re: Creating a Build Definition using the TFS 2010 API
Requesting Gravatar...
Hi there. Great post.
Your link to the build sample app is broken. Can you please transfer this example to github?

Left by Tom Harrison on Aug 17, 2015 10:55 AM

Your comment:
 (will show your gravatar)

Copyright © Jakob Ehn | Powered by: | Join free