This post is going to talk about continuous deployment on Visual Studio Team Services (VSTS) for .NET Core applications. With VSTS, we can manage projects, codes, builds, tests, and releases. However, it doesn’t fully support .NET Core applications at the time of this writing. More specifically, all necessary environment has been ready but the official build steps by Microsoft are not ready. Therefore, we’re writing our own PowerShell scripts for both continuous integration (CI) and continuous deployment (CD), and integrate them with VSTS build/release pipelines.
The complete PowerShell scripts can be found at: https://github.com/devkimchi/VSTS-CD-Sample
Build Steps – Part 1
For .NET Core application in CI, we should run the following steps in our build pipeline:
- Restore –
- Build –
- Test –
In a real world example, there are always more than one .NET Core library project in one .NET Core solution. Therefore, we need some PowerShell scripts for each build step.
dotnet restore – Restore NuGet Package
This is simple. In a PowerShell script, we only need one line of code:
So we’ve restored all necessary NuGet package libraries. Let’s move on.
dotnet build – Build Solution
Within the solution, there are two different directories –
test. Each contains one or more projects. Not all projects are related to the .NET Core application we are building. Therefore, we need to filter out projects for build like:
Each .NET Core project must have
project.json, so we only take projects that include that file. Once we find all project directories to build, build them by iterating the
$projects value. Let’s look at the script below:
$projects variable contains a list of directories that contain
project.json. Therefore, we simply iterate each project and build it using the
dotnet build command.
Now, we’ve restored NuGet package libraries followed by building entire .NET Core projects. Let’s move onto the next step.
dotnet test – Run Tests
Projects under the
test directory are considered for tests. Therefore, unlike the previous step, we this time only take directories from the
test directory like:
Once all necessary directories are populated, iterate
$projects and run
dotnet test like:
All tests are passed! We’re good to publish package for the .NET Core application. Let’s move onto the next step.
Build Steps – Part 2
This part is a sort of bridge between CI and CD. In order to deploy application to Azure, we need an artifact and tooling. We need additional steps within the build pipeline:
- Publish –
- Package – zip artifact
- Tooling – copy
dotnet publish – Publish Package
publish used here is a bit confusing because, in Visual Studio,
publish actually includes two distinctive steps – publish and deploy. In this post, we’re separating
publish, which will be dealt at the next section. For publish, we don’t need the whole .NET Core projects, but only need application project. Let’s have a look at the script below:
We explicitly give a name to get the project directory. With this details, run the following script:
As we run this script at the solution root level,
$PWD points to that directory and we point
$output to store published artifact. Once we run this script, we’ll be able to see a new directory under the
Package – Zip Artifact
As we can see in the picture above, the
publish merely means that all relevant dependencies are compiled in one place. So, it’s always a good idea to put everything in one
.zip file for deployment. Let’s have a look at the following script for zipping:
$BuildStagingDirectory takes an environment variable,
$(Build.StagingDirectory), from VSTS, which refers to the local path on VSTS where artifacts are copied to before deployment.
Once the zip file is ready, it’s time for deployment. Oh, wait. We need a tooling. Let’s move on.
WAWSDeploy – Deploy Artifact
Before performing actual deployment, we need a tool for that, called
WAWSDeploy. We can still use
msdeploy.exe, but its bunch of parameters are overwhelming.
Actually, in order to deploy applications to Azure, there is a much easier way, if we use
WAWSDeploy. With this, we can simply download publish settings file from Azure Web app and pass it to
WAWSDeploy as a parameter.
Therefore, in order to use
WAWSDeploy for deployment, we also need to copy this to the artifact directory at the same time when the artifact is copied.
Now we’re really ready for deployment!
Once everything is done in the build pipeline as CI, it triggers CD process. For .NET Core apps, the release pipeline in the CD process has two steps:
- Prepare Tooling – unzip
- Release – run
$PackagePath takes an environment variable,
$(System.DefaultWorkingDirectory), from VSTS, where artifacts are downloaded during deployment of a release. Running this scrpt will extract
WAWSDeploy.zip for deployment. We now have one last step.
As stated above, we’re going to use a publish settings file directly downloaded from Azure web app. There is a cmdlet for this. Let’s have a look at the script:
We’re all set! Now, we just push a new commit to a repository on VSTS, it will trigger the build pipeline for CI then, if build and test is successful, activate release pipeline for CD. Once everything is done, we’ll be able to see the actual API application deployed to Azure web app. How easy!
I used VSTS in this post, but these PowerShell scripts can be used any CI/CD service as long as the service supports PowerShell and .NET Core environment.