Updating my Kubernetes Raspberry Pi Cluster to containerd

,

There’s been a lot of conversations happening on twitter over the last couple of days due to the fact that Docker is deprecated in Kubernetes v1.20.

If you want to know more about the reason why I highly recommend checking out this twitter thread.

I’ve recently built a Raspberry Pi Kubernetes cluster so I thought I’d run through updating them in-place to use containerd as the container runtime instead of Docker.


DISCLAIMER – You’d never do this for a production cluster. For those clusters, you’d simply get rid of the existing nodes and bring new ones in on a rolling basis. This blog is just me mucking about with my Raspberry Pi cluster to see if the update can be done in-place without having to rebuild the nodes (as I really didn’t want to have to do that).


So the first thing to do is drain the node (my node is called k8s-node-1) that is to be updated and cordon it:-

kubectl drain k8s-node-1 --ignore-daemonsets

Then ssh onto the node and stop the kubelet: –

systemctl stop kubelet

Then remove Docker: –

apt-get remove docker.io

Remove old dependencies: –

apt-get autoremove

Now unmask the existing containerd service (containerd is used by Docker so that’s why it’s already there): –

systemctl unmask containerd

Install the dependencies required:-

apt-get install unzip make golang-go libseccomp2 libseccomp-dev btrfs-progs libbtrfs-dev

OK, now we’re following the instructions to install containerd from source detailed here.

I installed from source as I tried to use apt-get to install (as detailed here on the Kubernetes docs) but it wouldn’t work for me. No idea why, didn’t spend to much time looking and tbh, I haven’t installed anything from source before so this was kinda fun (once it worked).

Anyway, doing everything as root, grab the containerd source: –

go get -d github.com/containerd/containerd

Now grab protoc and install: –

wget -c https://github.com/google/protobuf/releases/download/v3.11.4/protoc-3.11.4-linux-x86_64.zip
sudo unzip protoc-3.11.4-linux-x86_64.zip -d /usr/local

Get the runc code: –

go get -d github.com/opencontainers/runc

Navigate to the downloaded package (check your $GOPATH variable) mine was set to ~/go so cd into it and use make to build and install: –

cd ~/go/src/github.com/opencontainers/runc
make
make install

Now we’re going to do the same thing with containerd itself: –

cd ~/go/src/github.com/containerd/containerd
make
make install

Cool. Now copy the containerd.service file to systemd to create the containerd service: –

cp containerd.service /etc/systemd/system/
chmod 644 /etc/systemd/system/containerd.service

And start containerd: –

systemctl daemon-reload
systemctl start containerd
systemctl enable containerd

Let’s confirm containerd is up and running: –

systemctl status containerd

Awesome! Nearly done, now we need to update the kubelet to use containerd as it defaults to docker. We can do this by running: –

sed -i 's/3.2/3.2 --container-runtime=remote --container-runtime-endpoint=unix:///run/containerd/containerd.sock/g' /var/lib/kubelet/kubeadm-flags.env

The flags for the kubelet are detailed here

I’m using sed to append the flags to the cluster but if that doesn’t work, edit manually with vim:-

vim /var/lib/kubelet/kubeadm-flags.env

And the following flags need to be added: –

–container-runtime=remote –container-runtime-endpoint=unix:///run/containerd/containerd.sock

OK, now that’s done we can start the kubelet: –

systemctl start kubelet

And confirm that it’s working:-

systemctl status kubelet

N.B. – Scroll to the right and we can see the new flags

Finally, uncordon the node. So back on the local machine:-

kubectl uncordon k8s-node-1

Run through that for all the worker nodes in the cluster. I did the control node as well following these instructions (didn’t drain/cordon it) and it worked a charm!

kubectl get nodes -o wide

Thanks for reading!

Original post (opens in new tab)
View comments in original post (opens in new tab)

Rate

Share

Share

Rate