April 2013

Volume 28 Number 04

TFS - Building and Validating Windows Store Apps with Team Foundation Service

By Thomas LeBrun | April 2013

Available in final release since October 2012, Team Foundation Service, the cloud version of Visual Studio Team Foundation Server (TFS), offers a number of features that can help you deliver quality software. And it’s no great leap to imagine the software you’re thinking about developing will likely target Windows 8.

You might be wondering whether you can mix the power of the two products—use Team Foundation Service to build Windows Store applications. Unfortunately, this isn’t possible out of the box, due to some limitations I’ll cover later in this article. However, I’ll also show you the steps needed to bypass this issue and help you validate Windows Store apps during the build process.

First, let’s take a quick look at Team Foundation Service.

Overview of Team Foundation Service

As a cloud-based service, Team Foundation Service allows developers to access the features offered by TFS without the hassle of having to install and manage it. Just sign up (for free!) at bit.ly/ZusqUY and you’re ready to go.

Among the services offered by the product, you’ll likely focus on three major features to develop and deliver high-quality software:

Source Code Management You can use the source control feature with your current tools and preferred language—virtually any kind of file (C#, C++, HTML, PHP, Java and more) can be handled by the source controller. If you use an IDE such as Visual Studio or Eclipse, you can continue to use it to develop your applications and to check your files into the source control.

The source controller architecture provides a local workspace that stores a local copy of the source code. In disconnected mode, all modifications are performed in this workspace. When you reconnect, you simply check in your code to push it to the server, keeping the full history of all versions so you can track and roll back changes.

Collaboration Team Foundation Service lets developers work better together, primarily via a tool called the task board. The task board is accessible from any modern browser that lets you create custom dashboards. You use the task board to manage information about work items, build status, tests results and so forth, as shown in Figure 1.

Sample Dashboard for Team Foundation Service
Figure 1 Sample Dashboard for Team Foundation Service

Build Service Still in preview at the time of this writing, the Build Service is based on Team Build, which is part of TFS 2010, and provides automated build in the cloud.

All the standard features of Team Build can be used by the Build Service, including continuous integration, nightly builds and gated check-in builds. Moreover, the build template it uses is fully customizable. There’s even a “ready to go” template for doing continuous deployment on Azure (you can check in code in the source control and see its updates on Azure Web sites).

The Build Service is hosted on a build server deployed with Windows Server 2008 R2, Team Build, Visual Studio 2010 or later, and more (see the full list of required software and options at the bottom of this page: bit.ly/12Sf99Z). The default configuration is good for most applications—except Windows Store apps. As you can see in Figure 2, Windows Store apps need to be built on Windows 8 (or Windows Server 2012) and these are not installed on the build server.

Building Windows Store Apps on Team Foundation Service Is Not Possible out of the Box
Figure 2 Building Windows Store Apps on Team Foundation Service Is Not Possible out of the Box

So, as noted earlier, building Windows Store apps with Team Foundation Service isn’t possible out of the box. But, as you’ll see, there’s a workaround. In essence, the workaround consists of installing a Windows 8 computer that will become a new build agent, dedicated to Windows Store apps, for Team Foundation Service. I’ll show you how to implement it.

Building Windows Store Apps with Team Foundation Service

Here’s a look at the steps needed to build Windows Store apps using Team Foundation Service.

Installing the Build Service First, you need a machine running Windows 8. This can be either a physical or a virtual machine (VM); it’s not important as long as the machine is accessible from the Internet. Next, install TFS 2012 on that machine. Note that installing TFS doesn’t mean it’ll be configured and ready to use. The only reason you’re installing it is to be able to configure the Build Service. You don’t need to get a Team Foundation Application Server, as you have the one from Team Foundation Service.

Once the Build Service is installed, you can configure it using a dedicated team project collection. In this case, because you won’t be setting up other TFS components and you do want to use the Team Foundation Service, specify the team projects collection available with your Team Foundation Service account and finish the configuration, as shown in Figure 3.

Installing the Team Foundation Build Service in a Dedicated Team Projects Collection
Figure 3 Installing the Team Foundation Build Service in a Dedicated Team Projects Collection

Configuring the Build Service For the next part, you need to understand some basics about TFS and its build architecture.

Each TFS has a set of dedicated build controllers. A build controller is the endpoint that will receive the build request and execute it using dedicated build agents. The build agent does the most important work of the build: It gets files from source control, compiles the code, executes unit tests and so on.

Team Foundation Service comes with a dedicated build controller—the hosted build controller—so you might think you just have to create a new agent to run with this controller. Unfortunately, you can’t attach an on-premises build agent to a hosted build controller. You need to either choose another build controller or create a new build controller.

To keep it simple, let’s create a new one, as shown in Figure 4.

Creating a New Build Controller
Figure 4 Creating a New Build Controller

Once the controller is up and running, the next step is to set up a new agent dedicated to the building of Windows Store apps. Creating a new build agent is as simple as clicking on the New Agent link and then filling in the fields. In a real production environment, you might have more agents for your build controller, so to be sure that Windows Store apps will be built only by agents running on Windows 8, add a dedicated tag as shown in Figure 5. This isn’t required, but when you create the build definition later, you’ll be able to specify this tag to ensure that only this agent will be used for the build process.

Creating a New Build Agent
Figure 5 Creating a New Build Agent

Before moving to the next part, you need to go to the Build Service properties and set it to run interactively. This step isn’t mandatory if you just want to build Windows Store apps. But if you want to validate your applications, Team Foundation Service and the Build Service will need to install and launch them on the build machine, and this can’t be done if the Build Service isn’t configured to run interactively.

On the Builds page in Visual Studio Team Explorer, click on Actions, then on Manage Build Controllers to open a window showing a list of all the build controllers (with their dedicated agents) installed. If the configuration was successful, you should see your new controller and agent.

Preparing the Build Agent to Run Unit Tests If the computer that hosts the build agent will be used to perform unit tests, there are two other steps that need to be performed. First, a Windows 8 developer license must be installed on the computer. Developer licenses are free, they need to be renewed every 30 days (or 90 days, if you have a Windows Store account), and you can get as many as you need if you already have a Microsoft account. There are two ways to acquire a developer license. On your build machine, you can simply create a Windows Store app, which opens a dialog box from which you can get a valid license. If you don’t want to create a fake application on the build machine, you can run the following Windows PowerShell command to get the same dialog box:

C:\PS> Show-WindowsDeveloperLicenseRegistration

After you get the developer license, you need to generate and install a unit test certificate (from the code project that contains the unit tests you want to run) on the build agent. For this step, generate an application package on the developer machine. In Visual Studio, click on Store | Create App Package. This creates a folder containing the Windows Store app (in a file with the extension .appx) and its certificate.

To install the certificate on the build machine, open a command prompt as an administrator and enter the following command:

certutil -addstore root certificate_file

Note that certificate_file is the path to the certification file.

Building Windows Store Apps Once the controller and agent are running, building Windows Store apps is the same as building other kinds of applications. You just need to set up a new build definition and specify that you want to use the new build controller you just set up. To be sure that the build process will use the build agent running on Windows 8, in the Process tab of the build definition, select the tag you indicated when you created the build agent (see Figure 6).

Creating the Build Process Using the Specified Tag
Figure 6 Creating the Build Process Using the Specified Tag

Once this is done, queuing a new build using the build definition you just created launches it and, thanks to the specified tag, you can be sure the build is performed using the right agent, so it won’t fail.

As you can see, building a Windows Store app using Team Foundation Service is pretty easy and extremely powerful, and you can fully customize the build process. However, there’s still a problem. Even if the build succeeds, it doesn’t mean the application will run correctly or even that it will pass all the basics steps for validation. Next, I’ll explain how you can validate the application and how to indicate to users (through the build report) whether the validation passed or failed.

Validating Windows Store Apps During Team Build

As you probably know, in order to be published to the Windows Store, an app must be certified. That is, it must pass the required validation steps. You can validate your applications during the build process. This can be performed easily by simply adding a post-build event, which will launch the Windows App Certification Kit (ACK) to validate the application. But, out of the box, the validation doesn’t notify users of the results. I’ll show you how to extend the build process to include this step.

To integrate ACK execution during the build process, you just need to modify your project file to add the following PostPackageEvent:

<Target Name="PostPackageEvent" AfterTargets="_GenerateAppxPackage">
  <Exec Command="&quot;$(TargetPlatformSdkPath)App Certification Kit\appcert.exe&quot; reset"/>
  <Exec Command="&quot;$(TargetPlatformSdkPath)\App Certification Kit\appcert.exe&quot; test -apptype windowsstoreapp -AppxPackagePath &quot;$(FinalAppxPackage)&quot; –reportoutputpath &quot;$(outdir)\ValidationResult.xml&quot;" />
  <Exec Command="copy &quot;$(userprofile)\appdata\Local\Microsoft\appcertkit\ValidationResult.htm&quot; &quot;$(outdir)\ValidationResult.htm&quot;"/>
</Target>

When executed, the code will create the file ValidationResult.html, which contains the results of the validation performed by ACK. If you’re connected to the build server when the build is executed, you’ll see that the application is launched to be validated by ACK. This is normal; the app is installed, validated and then removed automatically when the test is finished. Remember that you configured the Build Service to run interactively, which is what allows the application to be installed and executed. If you hadn’t done this, an error would have occurred during the build.

The build process itself isn’t affected by the results of the validation, so users need to be able to check the test results to know whether the application has validation errors. Fortunately, you can enhance the build report to let users know if the validation encountered any errors. Let’s see how to customize the build report to integrate the validation results of the ACK tool.

Customizing the Build Report ACK creates both an HTML and an XML file and saves them in the folder you choose. You can use this XML file to create a custom workflow activity that will modify the build report to notify users of the validation results.

The code to create this activity is quite simple. It finds the XML file (which contains the validation results), reads the file to find the value of the “OVERALL_RESULT” attribute and returns that value. Figure 7 shows the code that creates the activity CheckWackResultsActivity.

Figure 7 CheckWackResultsActivity

[BuildActivity(HostEnvironmentOption.All)]
public sealed class CheckWackResultsActivity : CodeActivity<bool>
{
  [RequiredArgument]
  public InArgument<string> DropLocation { get; set; }
  [RequiredArgument]
  public InArgument<string> WackResultsFilename { get; set; }
  [RequiredArgument]
  public InArgument<string> WackReportFilename { get; set; }
  public OutArgument<string> WackReportFilePath { get; set; }
  // If your activity returns a value, derive from CodeActivity<TResult>
  // and return the value from the Execute method.
  protected override bool Execute(CodeActivityContext context)
  {
    string dropLocation = context.GetValue(this.DropLocation);
    string wackResultsFilename =
      context.GetValue(this.WackResultsFilename);
    string wackReportFilename = context.GetValue(this.WackReportFilename);
    var dropLocationFiles = Directory.GetFiles(dropLocation, "*.*",
      SearchOption.AllDirectories);
    if (dropLocationFiles.Any())
    {
      var resultFile = dropLocationFiles.FirstOrDefault(
        f => Path.GetFileName(f).ToLowerInvariant() ==
          wackResultsFilename.ToLowerInvariant());
      if (!string.IsNullOrWhiteSpace(resultFile))
      {
        var xDocument = XDocument.Load(resultFile);
        var reportElement = xDocument.Element("REPORT");
        if (reportElement != null)
        {
          var resultAttribute = reportElement.Attribute("OVERALL_RESULT");
          if (resultAttribute != null)
          {
            context.SetValue(this.WackReportFilePath,
              Path.GetDirectoryName(resultFile));
            var validationResult = resultAttribute.Value;
            // Fail or Pass
            if (validationResult.ToLowerInvariant() == "fail")
            {
              return false;
            }
            return true;
          }
        }
      }
      throw new InvalidOperationException(
        "Unable to find the Windows App Certification Kit results file!");
    }
    else
    {
      throw new InvalidOperationException(
        "There are no files in the drop location!");
    }
    throw new InvalidOperationException(
      "Unknow error while checking the content of the Windows App
      Certification Kit results file!");
  }
}

By default, the build activities run on build agents. But there might be some scenarios where you want the activity to execute as early as the first step, even before the build starts, or as the last step before the build is finalized. For that kind of flexibility, you need to have the activity run on the controller, not on the agent. You can do this using the attribute BuildActivityAttribute, which takes as an argument the enumeration value HostEnvironmentOption.All (as you can see in Figure 7). Note that if you don’t use the correct Host­EnvironmentOption option, you’ll get an error during the build process.

The class CheckWackResultsActivity inherits from Code­Activity<bool> so that its result value can be used to display the correct message in the build report. To display this message, you can use a new activity available in TFS 2012: WriteCustomSummaryInfo. This activity is very useful if you want to add a message to the build report because, instead of adding simple text, it allows you to add a dedicated category in the build report.

You have to specify the following properties:

  • Message, which is the text to display in the report
  • SectionDisplayName, which corresponds to the header of the section
  • SectionKey, the unique value of the section
  • SectionPriority, which defines the position of the new section in the report (0 is the highest priority and the standard sections start at 100)

So, using the new activity and WriteCustomSummaryInfo, I’m able to modify the build process to check for the validation results and add a new section in the build report. Figure 8 shows the XAML code of the modified build process.

Figure 8 The Modified Build Process

<Sequence DisplayName="Windows 8" sap2010:WorkflowViewState.IdRef="Sequence_4">
  <Sequence.Variables>
    <Variable x:TypeArguments="x:Boolean" Name="WackToolRanSuccessfully" />
    <Variable x:TypeArguments="x:String" Name="WackReportFilePath" />
  </Sequence.Variables>
  <c:CheckWackResultsActivity DropLocation="[DropLocation]"
    sap2010:WorkflowViewState.IdRef="CheckWackResultsActivity_3"
    Result="[WackToolRanSuccessfully]"
    WackReportFilePath="[WackReportFilePath]"
    WackReportFilename="ValidationResult.html"
    WackResultsFilename="ValidationResult.xml" />
  <If Condition="[Not WackToolRanSuccessfully]"
    sap2010:WorkflowViewState.IdRef="If_4">
    <If.Then>
      <Sequence sap2010:WorkflowViewState.IdRef="Sequence_6">
        <mtbwa:WriteCustomSummaryInformation
          sap2010:WorkflowViewState.IdRef=
            "WriteCustomSummaryInformation_2"
          Message="[&quot;Windows App Certification Kit ran with errors.
          Click [here](&quot; &amp; WackReportFilePath &amp; &quot;) to
          access the folder containing the report.&quot;]"
          SectionDisplayName="Windows 8" SectionKey="Windows8"
            SectionPriority="75"
          mva:VisualBasic.Settings=
            "Assembly references and imported namespaces
            serialized as XML namespaces" />
        <mtbwa:WriteBuildError
          sap2010:WorkflowViewState.IdRef="WriteBuildError_1"
          Message="Windows App Certification Kit ran with errors." />
        <mtbwa:SetBuildProperties
          CompilationStatus=
            "[Microsoft.TeamFoundation.Build.Client.BuildPhaseStatus.Failed]"
          DisplayName="Set Status and CompilationStatus to Failed"
          sap2010:WorkflowViewState.IdRef="SetBuildProperties_1"
          mtbwt:BuildTrackingParticipant.Importance=
            "Low" PropertiesToSet="CompilationStatus" />
      </Sequence>
    </If.Then>
    <If.Else>
      <mtbwa:WriteCustomSummaryInformation
        sap2010:WorkflowViewState.IdRef="WriteCustomSummaryInformation_1"
        Message="[&quot;Windows App Certification Kit ran with success.
        Click [here](&quot; &amp; WackReportFilePath &amp; &quot;) to
        access the folder containing the report.&quot;]"
        SectionDisplayName="Windows 8" SectionKey="Windows8"
          SectionPriority="75"
        mva:VisualBasic.Settings=
          "Assembly references and imported namespaces
          serialized as XML namespaces" />
    </If.Else>
  </If>
</Sequence>

Notice in Figure 8 that if the validation fails, the compilation status is set to “Failed” to prevent the build process from continuing. This isn’t mandatory and you can remove it if you prefer to always finish the build process, regardless of the validation results.

Now, each time a build is triggered, the build report displays a new section, dedicated to Windows 8, which shows the result of the validation (see Figure 9).

The New Section in the Build Report Showing Validation Results
Figure 9 The New Section in the Build Report Showing Validation Results

Using WriteCustomSummaryInfo, the build report can be enhanced with text and links only. If a more complex modification is needed (for example, adding an image), you can still apply the techniques used with TFS 2010.

There are a lot of possibilities for customizing the build process template for Windows Store apps, and the good news is that such customizations are pretty much the same for both Team Foundation Service and on-premises TFS.


Thomas Lebrun is technical leader at Infinite Square, a French Microsoft partner working on technologies including Windows 8/Windows Phone, Team Foundation Server, SharePoint and more. The author of two French books about Windows Presentation Foundation and the Model-View-ViewModel pattern, Lebrun is also a regular speaker during French events. Follow his blog at blog.thomaslebrun.net and follow him on Twitter at twitter.com/thomas_lebrun.

Thanks to the following technical expert for reviewing this article: Chris Patterson (Microsoft)