Create your own Kubernetes Cluster with VirtualBox

I am going to show you that It is easy to create your K8s Cluster in Windows Machine.
Sometimes working on Windows force you to deal with many bugs. Because you are using Ubuntu on Windows machine. Especially for Kubernetes, I have faced bugs when I used Docker Desktop to use Docker and K8s at the same time. Sometimes it’s hard or exhausting to deal with the bugs, and it’s time consuming. This is why I wanted to create this K8s cluster to have less or none buggy environment, and you can also use the docker.
VMs Setup
At first, by following the link below, we create 4 VMs on Virtual Box and make them reachable via SSH. Yet, just create one VM which is k8smaster because we are going to clone the rest of the machines from it.
https://codebots.com/library/techies/ubuntu-18-04-virtual-machine-setup
I have a 16 GB RAM Desktop Computer, I decided to give 2GB RAM to every VM. Also, make sure you give at least 2 CPU each VM.
You can read about the CPU minimum requirement: https://stackoverflow.com/a/60896835/14091937
We created the first VM with the name k8smaster.
Here is the all of the VMs host and their ip addresses for my setup.
192.168.56.101 k8smaster
192.168.56.102 k8sworker1
192.168.56.103 k8sworker2
192.168.56.104 k8sworker3
Connect to k8smaster machine and run the commands below to install the packages for Kubernetes setup.
$ sudo apt-get update && sudo apt-get install -y vim docker.io apt-transport-https curl $ curl -s https://packages.cloud.google.com/apt/doc/apt-key.gpg | sudo apt-key add -$ cat <<EOF | sudo tee /etc/apt/sources.list.d/kubernetes.list
deb https://apt.kubernetes.io/ kubernetes-xenial main
EOF$ sudo apt-get update && sudo apt-get install -y kubelet kubeadm kubectl$ sudo apt-mark hold kubelet kubeadm kubectl
OK. Let’s clone the other three VM from k8smaster. Then, change the host and enp0s8 ip address by following the processes shown below. The other VMs will have these information below.
# To edit the host name
$ sudo nano /etc/hostname
# To edit the host
$ sudo nano /etc/hosts
# To edit 50-cloud-init
$ sudo nano /etc/netplan/50-cloud-init.yaml
# To apply the all new settings
$ sudo netplan apply && sudo reboot

While you are doing steps above, add the following line to /etc/hosts
for all nodes. Because we are going to use the “ControlPlaneEndpoint” that allow us to use ip addreses and DNS names. (Link)
192.168.56.101 k8smaster
Also, do not forget to let all the VMs talked to each other. You can do this by following this video.
https://www.youtube.com/watch?v=vReAkOq-59I

192.168.100.8 k8smaster
192.168.100.5 k8sworker1
192.168.100.6 k8sworker2
192.168.100.7 k8sworker3
Here, all the VMs are running.

Reference:
https://rudimartinsen.com/2020/08/08/setting-up-a-kubernetes-cluster-vms/
K8s Cluster Setup
Now, we are ready to initialize the K8s Cluster.
- If you have a plan to upgrade to HA you should specify the
--control-plane-endpoint
(Link) --pod-network-cidr
is to specify the subnet for pod networking.
It’s time to install the cluster. As you can see we are using the k8smaster DNS name. This is why I wanted to add the following line in the /etc/hosts
. We also could use the ip address (192.168.100.8).
$ sudo kubeadm init --control-plane-endpoint k8smaster:6443 --apiserver-advertise-address=192.168.100.8 --pod-network-cidr 34.55.53.0/23
The IP address the API Server will advertise it’s listening on. If not set the default network interface will be used. (Link)
Probably, you are going to face the same error I had here. Before that happens use the command below for all the VMs.

$ sudo swapoff -a
But this is not permanent, each reboot of the system you’ll need to use the command again.
As you can see, it has done successfully. Do not forget to note this output, it gives you the command to add your workers to the cluster.

To be able to use the kubectl
command, copy and paste the commands mentioned in the output.
$ mkdir -p $HOME/.kube
$ sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
$ sudo chown $(id -u):$(id -g) $HOME/.kube/config
Calico is going to be the network provider for the Pods.
$ kubectl apply -f https://docs.projectcalico.org/manifests/calico.yaml

Now, the current state of the k8smaster
is ready. And, you can check the pods already created in the cluster.

Finally, we are going to add the worker nodes to the cluster with the following command.
You can now join any number of control-plane nodes by copying certificate authorities
and service account keys on each node and then running the following as root:kubeadm join k8smaster:6443 --token mv6zy3.09pqxe7a7097j6p0 \
--discovery-token-ca-cert-hash sha256:defa99ebe3726ba8a05ae8c22cf008e99df0a42a2700107e7f7ffec4feaa1e9e \
--control-planeThen you can join any number of worker nodes by running the following on each as root:kubeadm join k8smaster:6443 --token mv6zy3.09pqxe7a7097j6p0 \
--discovery-token-ca-cert-hash sha256:defa99ebe3726ba8a05ae8c22cf008e99df0a42a2700107e7f7ffec4feaa1e9e
For the workers, this is the command
$ sudo kubeadm join k8smaster:6443 --token mv6zy3.09pqxe7a7097j6p0 \
--discovery-token-ca-cert-hash sha256:defa99ebe3726ba8a05ae8c22cf008e99df0a42a2700107e7f7ffec4feaa1e9e

After sometime, you can see new worker is added, and it gets ready status.

Now, time to add the other workers nodes.

Before you go, let’s test our enviroment with a simple nginx container. Run this command on the k8smaster
# First, create a deployment named nginx
$ kubectl create deployment nginx --image=nginx# Then, increase the replica number
$ kubectl scale deployment/nginx --replicas=3

Our homemade cluster is working. Great job!