Skip to content

Building the Zerg Nest#

Installation is based on a fresh Centos Stream minimal server. Therefore, it is only adapted for CentOS installation, it may or may not work on other distribution.

Prerequise#

3 x nodes (bare-metal or VMs), each with:

  • A mainstream Linux OS (tested on CentOS 8/9 Stream)
  • At least 2GB RAM (You will need more Powaaaa, for the stack I will present futher allongs)
  • At least 50GB disk space (but it'll be tight)
  • Connectivity to each other within the same subnet, and on a low-latency link (i.e., no WAN links)

Installing Docker and Docker compose#

### Remove runc
dnf remove runc

### Adding docker repo


dnf install -y dnf-utils
dnf config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
dnf install -y docker-ce docker-ce-cli containerd.io


### Installing docker-compose


dnf install -y python3-pip
pip3 install --upgrade pip
pip3 install setuptools-rust
pip3 install docker-compose

Let's start the whale#

systemctl enable docker --now

And now create a zerg swarm from it#

From swarm1:

# docker swarm init
Swarm initialized: current node (ksdjlqsldjqsd2516685485) is now a manager.
To add a worker to this swarm, run the following command:

    docker swarm \
     join --token SWMTKN-1-5pykfhyfvtsij0tg4ewrtqk7hz2twuq21okeqv54p1gw2ufdde-814yer1z55vmyk2mwdhvjbob1 \
     10.0.0.51:2377

To add a manager to this swarm, run 'docker swarm join-token manager' and follow the instructions.

We are going to add the two other nodes as manager:

docker swarm join-token manager
To add a manager to this swarm, run the following command:

    docker swarm join --token SWMTKN-1-5pykfhyfvtsij0tg4ewrtqk7hz2twuq21okeqv54p1gw2ufdde-2k0vay9aub5eheikw7qi9v82o 10.0.0.51:2377

Run the command provided on your other nodes to join them to the swarm as managers. After addition of a node, the output of docker node ls (on either host) should reflect all the nodes:

# docker node ls
ID                            HOSTNAME           STATUS    AVAILABILITY   MANAGER STATUS   ENGINE VERSION
p424u0yvmu0vvc8nsnspv83zw *   swarm1.lab.local   Ready     Active         Leader           20.10.6
kg6w6ucpb2jf8v8xqai23pv3a     swarm2.lab.local   Ready     Active         Reachable        20.10.6
lam7mgs5wus40iaydvp8u3ss7     swarm3.lab.local   Ready     Active         Reachable        20.10.6

You are now ready to swarm.

Official Documentation : https://docs.docker.com/engine/swarm/

Little Network tweak#

When running Docker Swarm on RedHat or CentOS VMs under VMware you may run into issues with communication over the swarm node routing mesh. This issue is traced back to UDP packets being dropped by the source node. Disabling checksum offloading appears to resolve this issue.

Run the following on your VMs:

ethtool -K [interface] tx-checksum-ip-generic off
cat > /etc/NetworkManager/dispatcher.d/pre-up.d/10-tx-checksum-ip-generic <<'EOF'
ethtool -K ens192 tx-checksum-ip-generic off
EOF

chmod +x /etc/NetworkManager/dispatcher.d/pre-up.d/10-tx-checksum-ip-generic

Note: [interface] is your network adaptater so change it accordingly.

Firewalling#

data:image/png;base64,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

Base configuration#

Activate firewalld, you may want to check in /etc/firewalld/zones/ to check what is going to happen ^^ . One issue happening quite often is when you changed the default ssh port. As the ssh service declared in /usr/lib/firewalld/services/ssh.xml is referencing to port 22. If it's the case, copy the service.xml into /etc/firewalld/service and change the port of it.

(And yes, this happen to me a few times)

systemctl enable firewalld --now

Unmask the service if needed :

systemctl unmask firewalld

By default, firewalld is having a public zone created.

This public zone allow the use of ssh, cockpit, dhcpv6-client.

cat /etc/firewalld/zones/public.xml
 <?xml version="1.0" encoding="utf-8"?>
 <zone>
  <short>Public</short>
  <description>For use in public areas. You do not trust the other computers on networks to not harm your computer. Only selected incoming connections are accepted.</description>
  <service name="ssh"/>
  <service name="dhcpv6-client"/>
  <service name="cockpit"/>  
</zone>

If you don't use cockpit or dhcpv6-client, you can remove them from the configuration.

For example to delete cockpit service:

firewall-cmd --permamnent --zone=public --remove-service=cockpit
firewall-cmd --reload

Note here the parameters:

  • --permanent: means the rules gonna last after service restart

  • --zone: is used to indicate what zone should be modified, by default it's the public one

  • --remove-service : remove the service declared in /etc/firewalld/services/ without the .xml ending

firewall-cmd --reload is going to reload firewalld with latest configuration.

Let's add some services

firewall-cmd --permanent --zone=public --add-service=http

firewall-cmd --permanent --zone=public --add-service=https

firewall-cmd --reload

We are going now to create a new zone representing the nodes of our cluster, and add sources to it (understand incoming traffic).

firewall-cmd --permanent --new-zone=swarm

firewall-cmd --permanent --zone=swarm --add-source=10.0.0.51
firewall-cmd --permanent --zone=swarm --add-source=10.0.0.52
firewall-cmd --permanent --zone=swarm --add-source=10.0.0.53

firewall-cmd --reload

Let's check if sources where added

firewall-cmd --zone=swarm --list-sources
Ajouter les services nécessaires au cluster :
cp -a /usr/lib/firewalld/services/docker-swarm.xml /etc/firewalld/services/

firewall-cmd --zone=swarm --add-service=docker-swarm --permanent

firewall-cmd --reload

Docker Swarm#

Let's add the service to the swarm zone:

By default firewalld come bundled with some services. You can find them in /usr/lib/firewalld/services.

I like to copy them in /etc/firewalld/services when I use them as it prevent it to be changed after an update. Firewalld prioritize service in "/etc/firewalld/services/" then in /usr/lib/firewalld/services .

So let's copy the docker-swarm service:

cp /usr/lib/firewalld/services/docker-swarm.xml /etc/firewalld/services/

cat /etc/firewalld/services/docker-swarm.xml
<?xml version="1.0" encoding="utf-8"?>
<service>
  <short>Docker integrated swarm mode</short>
  <description>Natively managed cluster of Docker Engines (>=1.12.0), where you deploy services.</description>
  <port port="2377" protocol="tcp"/>
  <port port="7946" protocol="tcp"/>
  <port port="7946" protocol="udp"/>
  <port port="4789" protocol="udp"/>
  <protocol value="esp"/>
</service>

Then add it to the zone:

firewall-cmd --permanent --zone=swarm --add-service=docker-swarm
firewall-cmd --reload

firewall-cmd --zone=swarm --list-services
docker-swarm

Now we did allow the port and protocols for the nodes to be used our cluster, and off course all those action have to be done on each host of the cluster.