Docker Swarm Series: 3rd Create a highly available Container


Hello everyone, This article is part of The Swarm series, The knowledge in this series is built in sequence, Check it out at my profile.

At the last article we covered How to create a highly available environment, And deployed a simple Nignx web-app using DockerCLI on Play-with-docker lab.

In This article We will complete from the stand-up point, Will scaling up our Container, Update the Container and roll-back again, Also will submit some production scenarios for deep understanding how Swarm deal with, in this lab will use Play-with-docker lab and DockerCLI commands.

Lab Overview

After finalize Creation of The Infrastructure and collect the required info, Today’s Article will focus on The Container application section, How to scale-up and scale-down, cover the limits of routing mesh -Load balancer of swarm-, Rolling-Update and Rolling-back, After all will test the high availability of our environment by removing node from our cluster that host the Container and view how Swarm will handle this.

Build the infrastructure

At the last article we went through the hardest way of creating up our environment, However it’s the appropriate way to build up your environment at any platform (i.e. On-prem, Cloud, any where), Today’s will go through the easiest way to build up our environment on Play-with-docker platform.

  • Let’s specify the template that similar to what we used at the past articles.

  • This will build the environment as below:

Build the Past Container

At the last article we built a Service that have an Nginx container by running the following command on any one of the manager nodes:

docker service create --detach=true --name nginx1 --publish 80:80  --mount source=/etc/hostname,target=/usr/share/nginx/html/index.html,type=bind,ro nginx:1.12

And you can print out the Running services by running the following:

docker service ls

Scale-up and Down

Till Now we didn’t deploy a highly available container, Let’s try out to scale our container with extra 6 replicas by running the following:

docker service update --replicas 6 --detach=true nginx1

When this command is run the following events occur:

  • The service state is update with 6 replicas, Which in stored in Swarm internal storage.
  • Swarm recognize that the number of replicas that is scheduled now Does not equal The Actual state.
  • Swarm Schedule a new task with 6 replicas to match the desired state.

Use the following commands to discover the deployed service:

docker service ls

docker service ps nginx1

Use the update command to Scale-Down as well, By running the following Will Scale-Down the replicas to be 5 instead of 6:

docker service update --replicas 5 --detach=true nginx1

Routing mesh limits

Now on our scenario, When you send a request on port 80, The Routing mesh has multiple containers -working on this port- in which to route requests to, Routing mesh act as a load balancer for these containers, Therefor the Routing mesh will send the coming requests randomly to these containers.

let's test this out by running the following multiple times on any Node:
curl localhost:80

You should see which node is serving each request because of the useful `--mount` command option you used earlier.

Another easy way to check which node is serving the requests is to checking the aggregated logs by using the docker service logs [service-name] command. This aggregates the output from every running container and get the output from docker container logs [container-name] command.

Limits of the routing mesh: The routing mesh can publish only one service on port 80. If you want multiple services exposed on port 80, you can use an external application load balancer outside of the swarm to accomplish this.

Rolling update and Rolling back

Now you have your service deployed and running successfully, and you’re going to update the version of Nginx container. You want to update the pulled image and the deployed container that use this image version, with Docker service update command you can update the pulled image and the service as well.

Let's update our Nginx service to version 1.13 by using the following:
docker service update --image nginx:1.13 --detach=true nginx1

This triggers a rolling update of the swarm, Run the following command to view the updates in real time:
# using watch command
watch -n 1 docker service ps nginx1

# Or you can run this command over and over again
docker service ps nginx1

You can fine-tune the rolling update by using these options:
  • --update-parallelism : specifies the number of containers to update immediately (defaults to 1).
  • --update-delay : specifies the delay between finishing updating a set of containers before moving on to the next set.

After a few seconds you figure out that your Nginx application has update successfully and the old version has shunted-down.

Image description


What if find out that the latest update have an issue and your application didn’t work as expected and you want to roll-back you can achieve that by running the following:

# roll back
docker service rollback nginx1

# remove the in useful services
docker service rm 

Test the Swarm environment high available functionality

Now we have our services running on the distrusted nodes, What if a node with it’s containers hosted goes down, In this section will test the Swarm high availability Function by make the node 4 leaving the Swarm cluster.

  • Go to node 1 for example and run the following command to watch the cluster change in real time:
watch -n 1 docker service ps nginx2
  • Now, land on node 4 and run the following to leave the cluster:
docker swarm leave
  • Get back to node 1 and Note that the Swarm will rebuild the containers in another node to match the desired state.

Image description

That’s it, Very straightforward, very fast🚀. Hope this article inspired you and will appreciate your feedback. Thank you.