Provisioning a Raspberry Pi Swarm with IaC: Part 1
The Raspberry Pi is a cheap and fun piece of kit for geeks. My QNAP NAS is running a few too many applications on Docker, and I have a few Raspberry Pi’s laying around, so I thought it’d be a fun weekend project to turn them into a Docker Swarm.
The Swarm
Before getting into the automation side of things, let’s set up a prototype of the swarm itself. I’ll be setting up;
- A Raspberry Pi Rev 1 Model B,
- A Raspberry Pi Rev 3 Model B,
The Raspberry Pi’s will be running Raspberry Pi OS Buster
(2020-08-20). While the Rev 3 is 64 bit, I’ll be using the armhf
on
both. All the machines are on the same network.
Follow the official instructions to burn the image to the SD cards and spin up the Pi’s. We’ll be needing Docker, so follow the instructions for installing that too.
The Docker Swarm has two types of nodes; managers and workers. The managers keep the state of the swarm in a distributed store by using the Raft Consensus Algorithm. For best results, the amount of managers should be odd. I only have three machines to work with, so I’ll stick with a single manager for now. This cluster doesn’t need to be highly available. The Rev 3 is the most powerful RPi, so I’ll be electing it as the manager.
pi@manager:~$ sudo docker swarm init
Swarm initialized: current node (eseiud89bm9gl3eail1tnnznx) is now a manager.
To add a worker to this swarm, run the following command:
docker swarm join --token SWMTKN-1-6814zqm6wpp4q43fe9a9m2ezxcsecjnlmvcayvm5ydzpwkegdh-4n5qaw4ujge9xcmi2vcr0mcrn 192.168.0.2:2377
To add a manager to this swarm, run 'docker swarm join-token manager' and follow the instructions.
pi@manager:~$ sudo docker node ls
ID HOSTNAME STATUS AVAILABILITY MANAGER STATUS ENGINE VERSION
eseiud89bm9gl3eail1tnnznx * manager Ready Active Leader 19.03.13
Docker is nice enough to provide instructions for the workers. Let’s do that.
pi@worker:~$ sudo docker swarm join --token SWMTKN-1-6814zqm6wpp4q43fe9a9m2ezxcsecjnlmvcayvm5ydzpwkegdh-4n5qaw4ujge9xcmi2vcr0mcrn 192.168.0.2:2377
This node joined a swarm as a worker.
All management commands need to be run on the manager, so let’s check the list of nodes;
pi@manager:~$ sudo docker node ls
ID HOSTNAME STATUS AVAILABILITY MANAGER STATUS ENGINE VERSION
eseiud89bm9gl3eail1tnnznx * manager Ready Active Leader 19.03.13
bcm9cnme7ewvx224klfun1qfn worker Ready Active 19.03.13
Now let’s run an application on the swarm. For demonstration purposes
let’s just use some random image, like nginxdemos/hello
.
pi@manager:~$ sudo docker pull nginxdemos/hello
Using default tag: latest
latest: Pulling from nginxdemos/hello
550fe1bea624: Pull complete
d421ba34525b: Pull complete
fdcbcb327323: Pull complete
bfbcec2fc4d5: Pull complete
0497d4d5654f: Pull complete
f9518aaa159c: Pull complete
a70e975849d8: Pull complete
Digest: sha256:f5a0b2a5fe9af497c4a7c186ef6412bb91ff19d39d6ac24a4997eaed2b0bb334
Status: Downloaded newer image for nginxdemos/hello:latest
docker.io/nginxdemos/hello:latest
pi@manager:~$ sudo docker service create -p 8080:80 nginxdemos/hello:0.2
image nginxdemos/hello:0.2 could not be accessed on a registry to record
its digest. Each node will access nginxdemos/hello:0.2 independently,
possibly leading to different nodes running different
versions of the image.
9ldqvus6y2zzp64pj187mmb52
overall progress: 1 out of 1 tasks
1/1: running [==================================================>]
verify: Service converged
pi@manager:~$ sudo docker service ls
ID NAME MODE REPLICAS IMAGE PORTS
9ldqvus6y2zz jolly_rhodes replicated 1/1 nginxdemos/hello:0.2 *:8080->80/tcp
pi@manager:~$ sudo docker service ps jolly_rhodes
ID NAME IMAGE NODE DESIRED STATE CURRENT STATE ERROR PORTS
hfebnhjrg0v7 jolly_rhodes.1 nginxdemos/hello:0.2 manager Running Running 7 minutes ago
Fantastic. We have a service running in the swarm. Let’s see if it works;
pi@manager:~$ links -dump http://localhost:8080
NGINX Logo
Server address: 10.0.0.35:80
Server name: 2c704cbf842b
Date: 12/Nov/2020:19:53:43 +0000
URI: /
[ ] Auto Refresh
Request ID: e620aa94f6e13add9a69cd03340b1551
© NGINX, Inc. 2018
Now you can do all the typical things with Docker Swarm; adding replicas, deploying stacks and adding more nodes. In the next post we’ll go through how this can be automated using Ansible to easily scale to more nodes.