Setup a Kubernetes 1.24 cluster with kubeadm on CentOS Stream 8 or 9

Audun Nes
4 min readAug 17, 2022

Kubeadm is great for playing around with Kubernetes, and in particular if you are studying for the Certified Kubernetes Administrator (CKA) exam.

File:Kubernetes (container engine).png Google, Inc., CC BY 4.0 <https://creativecommons.org/licenses/by/4.0>, via Wikimedia Commons

Kubernetes 1.24 requires that your use a container runtime that is compliant with the Container Runtime Interface (CRI). This guide explains how to use Kubeadm to install a Kubernetes 1.24 cluster with containerd on CentOS Stream 8 or 9. The steps for each of these versions of CentOS Stream are almost identical. I have only found one additional step that needed to be performed on CentOS Stream 8 compared to on CentOS Stream 9.

The supported CRI implementations can be found in https://kubernetes.io/docs/setup/production-environment/container-runtimes/. That page also contains some of the commands I have added to this article.

For this article I will use two virtual machines on a bridged network in libvirt on Linux. One machine will act as the Kubernetes controlplane, and the other one will act as the worker node. I have tested both CentOS Stream 8 and CentOS Stream 9 as the guest operating system on these virtual machines.

You can see my libvirt setup here: https://github.com/avnes/freehold and the virtual machines here: https://github.com/avnes/kubeadm-vm. Please note that the Ansible role in https://github.com/avnes/freehold is currently broken (due to laziness), but the steps in the role can be run manually on the command line. See here: https://github.com/avnes/freehold/blob/main/ansible/roles/ansible-role-freehold/tasks/main.yml#L102 for manual steps.

Prepare for containerd installation

sudo dnf install -y yum-utils


sudo modprobe overlay
sudo modprobe br_netfilter

cat <<EOF | sudo tee /etc/modules-load.d/containerd.conf
overlay
br_netfilter
EOF

cat <<EOF | sudo tee /etc/sysctl.d/99-kubernetes-cri.conf
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
net.bridge.bridge-nf-call-ip6tables = 1
EOF

sudo sysctl --system

sudo yum-config-manager \
--add-repo \
https://download.docker.com/linux/centos/docker-ce.repo
OS_REL=$(cat /etc/redhat-release)# I only had to remove Podman on CentOS Stream 8if [[ $OS_REL == 'CentOS Stream release 8' ]]; then
sudo dnf remove -y podman;
fi
# If you experience a conflict with buildah, then also remove buildah with dnf.

Install and configure containerd

sudo dnf install -y containerd.io

sudo mkdir -p /etc/containerd
sudo containerd config default | sudo tee /etc/containerd/config.tomlsudo sed -i 's/SystemdCgroup = false/SystemdCgroup = true/g' /etc/containerd/config.tomlsudo systemctl restart containerd

Make SELinux permissive

sudo setenforce 0sudo sed -i 's/^SELINUX=enforcing$/SELINUX=permissive/' /etc/selinux/config

Install kubeadm, kubelet and kubectl

cat <<EOF | sudo tee /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=Kubernetes
baseurl=https://packages.cloud.google.com/yum/repos/kubernetes-el7-\$basearch
enabled=1
gpgcheck=1
gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg
exclude=kubelet kubeadm kubectl
EOF
sudo yum install -y kubelet kubeadm kubectl \
--disableexcludes=kubernetes

sudo systemctl enable --now kubelet

Install crictl

The tool crictl is a command-line interface for CRI-compatible container runtimes.

sudo swapoff -a

VERSION="v1.24.1"
curl -L https://github.com/kubernetes-sigs/cri-tools/releases/download/$VERSION/crictl-${VERSION}-linux-amd64.tar.gz --output crictl-${VERSION}-linux-amd64.tar.gzsudo tar zxvf crictl-$VERSION-linux-amd64.tar.gz -C /usr/local/binrm -f crictl-$VERSION-linux-amd64.tar.gz

Create the Kubernetes controlplane

On the virtual machine you have designated as your controlplane, run the following command to initialize a Kubernetes cluster:

sudo kubeadm init --pod-network-cidr 10.244.0.0/16

If you get any warnings or errors from the above command, you can either fix them, or in some cases you can also suppress them. In my case I was installing Kubernetes on a virtual machine with only 1 vCPU, but kubeadm prefers 2.

I suppressed that by running:

sudo kubeadm init --pod-network-cidr 10.244.0.0/16 --ignore-preflight-errors 'NumCPU'

After initialization, kubeadm will write instructions on how setup kubeconfig to point to your new cluster.

mkdir -p $HOME/.kube
sudo cp /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config

You can verify that it works by running:

kubectl get nodes

Please note that kubeadm also tells you what command to run on your worker nodes in order to join the newly created Kubernetes cluster. Copy that “kubeadm join” command and save it for later.

Install a Container Network Interface (CNI) plugin

At this point we are lacking a container network for cluster networking that implements the Container Network Interface (CNI). I have installed weave-net as CNI plugin using these commands:

sudo sh -c "KUBECONFIG=/etc/kubernetes/admin.conf kubectl apply -f https://cloud.weave.works/k8s/net?k8s-version=v1.24.3"sudo sh -c "KUBECONFIG=/etc/kubernetes/admin.conf kubectl get nodes -A -o wide"

Create the Kubernetes node

On the virtual machine you have designated as your worker node, run the following command to join the Kubernetes cluster:

sudo kubeadm join ......<the instructions you copied after initializing the controlplane>

Remove Kubernetes

In you want to destroy your Kubernetes cluster that you created with kubeadm, then run:

# On worker node:
sudo kubeadm reset


# On controlplane:
sudo kubeadm reset

--

--

Audun Nes

Lead Cloud Engineer/Site Reliability Engineer from Copenhagen, Denmark. GitHub: https://github.com/avnes