Automate UWP submissions using Cake

Finally we can automate uwp submissions using Cake!

This blog post has been in the makings for about a year now. But due to some technical store issues, it was delayed for a while. But no fear, the time has finally come here!

While working on several UWP apps for the Microsoft store, I found the deployment part very tedious. Especially building the 3 (x86, x64 and ARM) packages with the native toolchain were taking a long time (about 20 minutes).

I had a few ultimate goals while developing UWP apps:

  1. Get rid of the native compilation
  2. Automate the store submission

This pipeline (image taken from the build configuration in Continua CI) was the ultimate goal:


Getting rid of native compilation

Luckily for me, I didn’t have to do a lot of research on this front. Oren Novotny took care of this for the community by investigating this.

To summarize his hard work, you will need to use the following property values:

Property Value
UapAppxPackageBuildMode CI
AppxBundlePlatforms x86|x64|ARM
AppxBundle Always

Automate the store deployment

Next up was to automate the deployment to the store. I wanted to be able to trigger a build and only had to check the newly created deployment in the Windows Microsoft Store to submit it. For me, a logical first step was to take a look at Cake, which is an open-source tool (with lots of add-ons) for automating builds. There are several things that need automation in the deployment process:

  1. Determine the version number – GitVersion
  2. Update the version number in the appxmanifest
  3. Build the app for each target platform (x86, x64 and ARM), but without the slow native compilation
  4. Create a submission in the Microsoft Store (based on the previous one) and upload the new packages

Determine the version number

To determine the version number of the app, you can simply tag a specific commit with the version number and use GitVersion. I won’t go into too much details for this blog post.

Update the version number in the appxmanifest

At this stage, we have the version number and need to update it. Since this is UWP, updating the AssemblyInfo isn’t sufficient. To overcome this in Cake, one can use the MagicChunks add-on for Cake:

Building the app

Below is the code to build the app using Cake without native compilation:

Submitting the app

Unfortunately, due to the level of popularity of the Microsoft Store, there was no add-on yet for submissions. But now there is the Cake.WindowsAppStore add-in, making it very easy to submit the app to the store. The following values are required:

  • Windows Store App Id
  • Windows Store Client Id
  • Windows Store Client Secret
  • Windows Store Tenant ID

Check the official guide on Microsoft Docs on how to obtain these prerequisites.

Below is the Cake task for the submission:


Achievement unlocked! After over 200 manual submissions, I can finally publish app updates automatically via a build server with an acceptable build duration (45 seconds instead of 5 minutes):

All scripts described in this blog post are open source and can be found at


Multi-targeting .NET 4.6, .NET 4.7, UAP 10.0 with a single project

After waiting for the project.json storm to lay down, it was time for me to check whether the new .NET SDK project system was worth checking out. Oh dear, it was! In this post I will try to explain our reasoning to migrate to the new project system and how we overcame some of the issues we encountered during the transition.


One of the companies I work for use a large amount of (open source) libraries target .NET 4.5, .NET 4.6 and .NET 4.7. The reason we supported 3 different target frameworks per library is that it allowed us to switch the runtime of the (WPF) apps at any time and the libraries would be ready for it. However, a big downside of this is that loading the solution takes a long time, and everything is duplicated as you can see in the picture below:

While we are (considering to) making the transition to UWP, this would introduce a 4th platform project, meaning we would have 4 + 1 (for the shared project) = 5 projects per library.


Time to make a change! After reading the very promising blog post by Oren Novotny, I decided to make the jump and try and convert all the libraries to the new SDK project to achieve the following goals:

  • Single project to target multiple platforms (at the moment .NET 4.6, .NET 4.7, UAP 10.0 and .NET Standard 2.0, but more could easily be added in the future)
  • Update the build scripts from FinalBuilder to Cake (make it easier for open source contributors to work with)
  • Automatically generate the NuGet packages via MSBuild instead of FinalBuilder (again to make it easier for open source contributors to work with)

For this blog post, I will be using a fake repository named Ghk.MultiTargeting as an example. Note that this project is useless, but contains per-platform xaml code and shared code-behind.

Project differences compared to the original template

Compared to the original multi-targeting example, we made the following changes.

Project defines

To make sure I could still use the defines we invested in (to maximize code-sharing, we use a lot of #if in code shared between WPF and UWP). This project creates the following defines:

  • .NET 4.6 => NET; NET46
  • .NET 4.7 => NET; NET47
  • UAP 10.0 => UAP; NETFX_CORE
  • .NET Standard 2.0 => NS; NS20; NETSTANDARD; NETSTANDARD2_0

Include solution assembly info

The project structure adds this line to the project to include the SolutionAssemblyInfo and GlobalSuppressions files which are in the root of the solution.

Allow shared code-behind (e.g. MyView.xaml.cs) with a *per platform* view (e.g. MyView.xaml)

To allow sharing of code-behind of a view (for example, for custom controls), we need to to a bit of hacking. We create the view inside each platform specific view directory:

  • Platforms\net\Views\MyView.xaml (+ .cs)
  • Platforms\uap10.0\Views\MyView.xaml (+ .cs)

After creating the views, we will need to customize the code-behind to add a partial method:

Next, we create a partial code-behind class inside the regular views folder that contains the shared code:

  • Views\MyView.xaml.cs

This view should contain the following code and you can share your code-behind but have per-platform xaml files:

As an example, I added a dependency property in the shared code-behind that shows how to deal with the different platforms in shared code using defines.

Final project structure

Below is the final project structure that can serve as a reference.

Note that it is recommended to check out the latest version in the example repository.

Bonus: Cake deployments

Since we also migrated to using Cake as build script tooling, this is a good opportunity to take a look at Cake as well. I added the full build scripts we use for our components in the example repository. Note that you only have to change the variables in build.cake in the root and all should be updated.


Debugging Cake add-ins using Visual Studio

Recently I wanted to (finally) automate builds & submissions for all my UWP apps. Deploying a UWP app manually is a long process since it always creates a full .NET native build. This is only required for the certification kit and the store only uses the MSIL package. Before we dive into automating builds for UWP apps, let’s stay focused on debugging Cake extensions first.

The Cake extension I was working on is Cake.WindowsAppStore. It can be used to automatically create submissions for Windows Store apps. Debugging Cake add-ins is a bit of a thing, and there are several ways to do it. In this post I’ll describe what I think is the easiest way to debug Cake add-ins.

Step 1: Copy extension to the add-in directory in the cake script

The first thing we must do is to make sure that Cake uses the latest debug build of the add-in we want to debug. We can do this by creating this post-build step for the add-in project in Visual Studio:

xcopy /s /f /y “C:\Source\Cake.WindowsAppStore\src\Cake.WindowsAppStore\bin\Debug\net45\*” “C:\Source\MyApp\tools\Addins\Cake.WindowsAppStore\lib\net45\”

Note 1: this is stored in the csproj file and will be used for all users

Note 2: I would normally have used the build macros, but they don’t work (yet)

Step 2: Set the debug options to run Cake directly

In Visual Studio, go to the Project Properties and select the Debug tab:

1. Set Launch to Executable

2. Set Executable to C:\Source\MyProject\tools\Cake\Cake.exe

3. Set Application Arguments to build.cake -target=Deploy (where target is obviously the Cake target you want to run)

4. Set Working Directory to the project directory you want to run the Cake script against, e.g. C:\Source\MyProject\

Note that this is a user-specific setting so will only work on your machine

Below is a screenshot of the final result:


Step 3: Enjoy your debugging experience