Publish Multi-Container app images using VSTS


This is the third part of the series of blog posts on Continuous Deployment of Multi-Container app in Azure using VSTS and Docker. In the first part we covered the brief overview of all the tools we will be using during this series. In the previous post we established connection between VSTS and GitHub to trigger the build every time there is change in the source control pushed to the repository. This post will continue from there to build Docker images and publish them to the container registry. Lets get started.

Integrate DockerHub with VSTS build

We will be using the Multi-Stage build feature of Docker to build our images for the Web and API parts of the application. We will publish these images to DockerHub registry. Ensure that you have valid DockerHub account. We will need to perform following steps to continuously build and push docker images

  1. Create Docker Compose file which creates the latest version of the images
  2. Edit VSTS build definition to add task to trigger docker-compose build command
  3. Add task to trigger docker push command for coremvc and corewebapi images to DockerHub using docker compose task

Create Docker-compose file

During the earlier post, I had demonstrated how to build Docker images using multi-stage build feature. In that example I had to separately build two docker images one for AspNet Core MVC web application and the other one is for ASPNet Core WebAPI project. This approach works fine if we have just couple of images. As the application grows, more likely you will have multiple images. We need a convenient way of creating the images. Docker provides us that convenience by means of Docker-compose. It gives us the ability to use declarative syntax to describe different parameters required to build different images and then build all the images using one single command.

As we can see from the above code snippet, all the parameters we were specifying at the terminal to docker cli are specified in declarative manner. This compose file is referencing the existing dockerfile from mvc and api projects. One of the advantage of using a compose file is also that we can specify dependencies between different services of an application. You can see this in action on lines 9 & 10 where we specify that the frontend MVC site depends on the web API. Docker will automatically take care of build the images in correct order to satisfy these dependencies. I am using version 3 of docker compose. You can read more about the docker compose features using docker documentation.

Edit VSTS build definition

VSTS provides out of the box integration with Docker tools. Lets start by editing the build definition which we created earlier. Click the plus sign on the Phase 1 section to bring up available tasks

add docker compose task

There are various types of tasks available which can be viewed differently under categories like Build, Utility, Test, Package, Deploy and Tools. For simplicity we will search for docker in the search box as shown in the screenshot. We get 4 tasks filtered. Select Docker Compose and click Add button.

We need specify all the details in order to work with Docker tools. Select the newly added task and give some meaningful display name to it. By default the task is configured to run against Azure Container Registry. As we will be using DockerHub change the selection to Container Registry. As this is the first time we are connecting to DockerHub registry, we need to configure it. If you already have an existing connection we can select it from the dropdown instead of creating new. Click on New to configure DockerHub.

customize docker compose task

The new Docker Registry Connection dialog box is self explanatory. Choose the type of registry as DockerHub, provide username and password and you are done. Verify that the settings are correct.

Dockerhub connection

By default the task is configured to look for a file named docker-compose. In my case I am using a file named docker-compose-build.yml to distinguish between the build and deploy versions. We need to update the filename in the text box for Docker compose file as shown below by clicking on the ellipses next to the text box

docker compose file selection

The file is located under the DotNet2017 folder. We are almost done with the setup. The last step remaining is to configure the build command. This is done by setting the Action to Run a Docker Compose command and setting the Command to build.

docker compose build config

Let us test that the settings are correct and all the things are glued together as expected. Click on the Save & Queue button on the top right to queue a new build. A hyperlink will be provided when the build is queued. Click that link to monitor the progress of the build.

compose task output

The build succeeded and we have the two images created as the output. coremvc:latest is highlighted in the screenshot. Similarly we have the corewebapi:latest also tagged and ready to be pushed to DockerHub.

Publish images to DockerHub

Go back editing the build definition and add one more Docker Compose task. This time we will reuse the DockerHub connection. The compose filename remains the same because we want to publish the images created using the file. Modify the action to Push Service Images.

Docker Compose push config

That is all we need to push the newly created docker images to DockerHub. Save the changes and queue a new build. We should be able to see our images being pushed to the DockerHub registry in the final build log output.

VSTS build log

The build log confirms that the two images have been successfully pushed to registry. I still like to get a double confirmation by checking Dockerhub. Login to the DockerHub account and verify that the recent images are available. The screenshot below confirms that the coremvc image was updated less than a minute ago. Same is the case with corewebapi image.



We can see that it is very easy to integrate Docker, DockerHub and VSTS. With the help of Docker Compose files we are able to build multiple images using single command. And then Microsoft makes it super easy by providing out of the box functionalities with VSTS to build and publish images to container registries. Without these tasks we would have to do lot of hand coding to create and push images to DockerHub using cli commands. VSTS has abstracted this functionalities and by providing GUI tools the process is seamless.

This completes our continuous integration CI phase where a code change will be able to produce a latest version of the docker image and push it to DockerHub. The image below is the summary of what we have achieved so far for the CI part. The blue arrows indicate build section and the purple ones are the publishing part.

CI phase

The complete source code for this post is available on GitHub. In the upcoming posts we will see how to provision a Docker Swarm cluster in Azure running using Azure Container Service and continuously deploy the docker images to Swarm. Until next time code with passion and strive for excellence.


No comments:

Post a Comment