Setup Your Kubernetes Cluster on Bare Metal machines

Jie Liau
5 min readJun 4, 2021

--

Container technology is the most popular topic in recent years. Kubernetes is the orchestration system for container environment which is used by lots of people all around the world. You can easily setup your Kubernetes cluster on AWS, Azure and Google Cloud. What if you have to setup one cluster in your datacenter on your bare metal machines? This article will describe how you setup your Kubernetes cluster on your bare metal machines !!! I will use Ubuntu 18.04 as my example here.

0x01 Prerequisite

Before you kick off you installation, we have to check if br_netfilter kernel module has been loaded or not and let iptables see bridged traffic. Please input the following command on both master and worker nodes:

$ sudo modprobe br_netfilter

$ cat <<EOF | sudo tee /etc/modules-load.d/k8s.conf
br_netfilter
EOF

$ cat <<EOF | sudo tee /etc/sysctl.d/k8s.conf
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
EOF
$ sudo sysctl — system

0x02 Install Container Runtime

Kubernetes uses CRI (Container Runtime Interface) to interface with your chosen container runtime. The following list is the container runtime which is supported by Kubernetes.

Docker : /var/run/dockershim.sock
containerd : /run/containerd/containerd.sock
CRI-O : /var/run/crio/crio.sock

I use Docker as my container runtime in this example. Please check here for installation of Docker.

After installing Docker, please input the following command to configure the Docker daemon to use systemd for the management of the container’s cgroups:

$ sudo mkdir /etc/docker
$ cat <<EOF | sudo tee /etc/docker/daemon.json
{
“exec-opts”: [“native.cgroupdriver=systemd”],
“log-driver”: “json-file”,
“log-opts”: {
“max-size”: “100m”
},
“storage-driver”: “overlay2”
}
EOF

And then reload/restart Docker daemon.

$ sudo systemctl enable docker
$ sudo systemctl daemon-reload
$ sudo systemctl restart docker

Remember installing container runtime on both your master and worker nodes !!!

0x03 Install kubelet/kubeadm/kubectl

Please input the following command to install needed software in your Ubuntu boxes. Both on master and worker nodes:

$ sudo apt-get update
$ sudo apt-get install -y apt-transport-https ca-certificates curl

$ sudo curl -fsSLo /usr/share/keyrings/kubernetes-archive-keyring.gpg https://packages.cloud.google.com/apt/doc/apt-key.gpg

$ echo “deb [signed-by=/usr/share/keyrings/kubernetes-archive-keyring.gpg] https://apt.kubernetes.io/ kubernetes-xenial main” | sudo tee /etc/apt/sources.list.d/kubernetes.list

$ sudo apt-get update
$ sudo apt-get install -y kubelet kubeadm kubectl
$ sudo apt-mark hold kubelet kubeadm kubectl

0x04 Turn Off Swap

You have to turn off your swap. Please input the following command:

$ sudo swapoff -a

If you wanna turn off your swap every time when you restart your cluster, please use the following command:

$ sudo sed -i ‘/ swap / s/^\(.*\)$/#\1/g’ /etc/fstab

0x05 Initialize control-plane

At this stage, you have all your needed prerequisites ready. For now, please initialize your control-plane on your master nodes. Please input the following command on your master node:

# kubeadm init — control-plane-endpoint ‘k8s-endpoint:6443’ — apiserver-advertise-address 192.168.33.10 — pod-network-cidr 10.10.0.0/16

If you want to know more about kubeadm arguments usage, please check here !!!

After control-plane initialized, you will see the following message.

Follow the instruction, copy the admin.conf to your $HOME/.kube/config. You can do it as regular user or super one:

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

If you want more control-plane nodes to join your cluster, please input the following command on other control-plane nodes:

# kubeadm join k8s-endpoint:6443 — token yk730o.x5c2db7v0gkfx0x6 \
— discovery-token-ca-cert-hash sha256:1f2162cd56d11a0ae71eadb11ce361eac4c38e05edb3435ff14307fc9ab50959 \
— control-plane

And the following command is used by worker nodes to join the cluster:

# kubeadm join k8s-endpoint:6443 — token yk730o.x5c2db7v0gkfx0x6 \
— discovery-token-ca-cert-hash sha256:1f2162cd56d11a0ae71eadb11ce361eac4c38e05edb3435ff14307fc9ab50959

0x06 Install Kubernetes Network add-on

Before we let worker nodes join cluster, we have to install Kubernetes network add-on. Some network add-on needs specific pod CIDR to be specified while you initialize your cluster, please check here for it. I use Calico as my network add-on in this setup. Please input the following command:

# curl https://docs.projectcalico.org/manifests/calico.yaml -O
# kubectl apply -f calico.yaml

0x07 Let Worker Node Join Cluster

After installing network add-on, you’re good to let worker node join your cluster. Please input the following command on your worker nodes:

# kubeadm join k8s-endpoint:6443 — token yk730o.x5c2db7v0gkfx0x6 — discovery-token-ca-cert-hash sha256:1f2162cd56d11a0ae71eadb11ce361eac4c38e05edb3435ff14307fc9ab50959

After this, wait a while and type kubectl get node on your master node and you will see your worker nodes are ready to serve:

You can type kubectl get all -A to check all resources running well on your cluster:

0x08 Deploy your service

Now you can deploy your deployment and service on the cluster and provide the service here.

nginxDeploy.yaml
services.yaml

I run my example in Vagrant environment and map host port 8080 to guest port 30390.

Vagrant Config

After applying nginxDeploy.yaml and services.yaml, open up the browser on your host and type http://127.0.0.1:8080, you can see the nginx is up and running.

Hope this article will help you setting up your own Kubernetes cluster and motivate you to start your study of Kubernetes. Love You !!!

--

--