How to install Kubernetes with microk8s and deploy apps on Debian/Mint/Ubuntu Linux

Kubernetes Easy Beginners Architecture Guide

Kubernetes is known as container orchestration and we should start at explaining the container part of it.

A Container is what runs the actual application and based on an Image, and are more comparable to something like an LXC Container, Virtuozzo/OpenVZ using the Linux Kernel Namespaces feature.  Containers run these images as independent, isolated operating environments under the OS's existing kernel.  Unlike full virtualization which emulates a real computer, images run under the existing OS kernel and do not have their own virtual hardware, which makes them perform and deploy faster.

An Image is like a pre-built template that has everything we need to run the application eg. nginx, Apache, MySQL and almost anything can be turned into a purpose built application inside an image file.

Multiple Containers run within Pods, and Multiple Pods can run on Nodes, and there can be Multiple Nodes in the Cluster, which is the general/basic hierarchy of Kubernetes.

Pods are basically just a grouping of Containers which are generally related or may need to have tighter coupling of storage and networking.

Nodes can be anything that runs the kubernetes services, and would most commonly be some sort of VM or even a physical server.

Note that Linux Mint disables snap, read this post to fix snapd install missing in Linux Mint.

sudo apt install kubernetes snapd
Reading package lists... Done
Building dependency tree       
Reading state information... Done
The following NEW packages will be installed:
0 upgraded, 1 newly installed, 0 to remove and 123 not upgraded.
Need to get 3,340 B of archives.
After this operation, 19.5 kB of additional disk space will be used.
Get:1 focal/universe amd64 kubernetes all 1.0 [3,340 B]
Fetched 3,340 B in 0s (9,475 B/s)      
Selecting previously unselected package kubernetes.
(Reading database ... 378576 files and directories currently installed.)
Preparing to unpack .../kubernetes_1.0_all.deb ...
Unpacking kubernetes (1.0) ...
Setting up kubernetes (1.0) ...
Processing triggers for man-db (2.9.1-1) ...

kubernetes install

Choose 1 for microk8s:




Create our first app deployment using nginx

microk8s.kubectl create deployment nginx --image nginx
deployment.apps/nginx created

enable/expose it so it can start working

microk8s.kubectl expose deployment nginx --port 8000 --target-port 8000 --selector app=nginx --type ClusterIP --name rtttest
service/rtttest exposed

View all running services:

microk8s.kubectl get all
NAME                         READY   STATUS    RESTARTS   AGE
pod/nginx-6799fc88d8-sm5gd   1/1     Running   0          3m43s

NAME                 TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)    AGE
service/kubernetes   ClusterIP             443/TCP    25m
service/areebtest    ClusterIP           8000/TCP   2m49s

NAME                    READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/nginx   1/1     1            1           3m43s

NAME                               DESIRED   CURRENT   READY   AGE
replicaset.apps/nginx-6799fc88d8   1         1         1       3m43s


Enable Dashboard

microk8s.enable dns dashboard
Enabling DNS
Applying manifest
serviceaccount/coredns created
configmap/coredns created
Warning: spec.template.metadata.annotations[]: non-functional in v1.16+; use the "priorityClassName" field instead
deployment.apps/coredns created
service/kube-dns created created created
Restarting kubelet
DNS is enabled

Enabling Kubernetes Dashboard
Enabling Metrics-Server
serviceaccount/metrics-server created created created created created created
service/metrics-server created
deployment.apps/metrics-server created created created
Metrics-Server is enabled
Applying manifest
serviceaccount/kubernetes-dashboard created
service/kubernetes-dashboard created
secret/kubernetes-dashboard-certs created
secret/kubernetes-dashboard-csrf created
secret/kubernetes-dashboard-key-holder created
configmap/kubernetes-dashboard-settings created created created created created
Warning: spec.template.spec.nodeSelector[]: deprecated since v1.14; use "" instead
deployment.apps/kubernetes-dashboard created
service/dashboard-metrics-scraper created
deployment.apps/dashboard-metrics-scraper created

If RBAC is not enabled access the dashboard using the default token retrieved with:

token=$(microk8s kubectl -n kube-system get secret | grep default-token | cut -d " " -f1)
microk8s kubectl -n kube-system describe secret $token

In an RBAC enabled setup (microk8s enable RBAC) you need to create a user with restricted
permissions as shown in:

microk8s.kubectl get all --all-namespaces
NAMESPACE     NAME                                             READY   STATUS              RESTARTS       AGE
default       pod/nginx-6799fc88d8-sm5gd                       1/1     Running             1 (134m ago)   147m
kube-system   pod/coredns-7f9c69c78c-jhhkq                     1/1     Running             0              2m25s
kube-system   pod/calico-node-2jnsp                            1/1     Running             1 (134m ago)   169m
kube-system   pod/calico-kube-controllers-58d7965c58-qpw8j     1/1     Running             1 (134m ago)   169m
kube-system   pod/dashboard-metrics-scraper-58d4977855-7dnzm   0/1     ContainerCreating   0              13s
kube-system   pod/kubernetes-dashboard-59699458b-7t52l         0/1     ContainerCreating   0              13s
kube-system   pod/metrics-server-85df567dd8-7rfsm              0/1     Running             0              13s

NAMESPACE     NAME                                TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)                  AGE
default       service/kubernetes                  ClusterIP             443/TCP                  169m
default       service/areebtest                   ClusterIP           8000/TCP                 146m
kube-system   service/kube-dns                    ClusterIP            53/UDP,53/TCP,9153/TCP   2m25s
kube-system   service/metrics-server              ClusterIP           443/TCP                  97s
kube-system   service/kubernetes-dashboard        ClusterIP           443/TCP                  77s
kube-system   service/dashboard-metrics-scraper   ClusterIP            8000/TCP                 77s

kube-system   daemonset.apps/calico-node   1         1         1       1            1    169m

NAMESPACE     NAME                                        READY   UP-TO-DATE   AVAILABLE   AGE
kube-system   deployment.apps/calico-kube-controllers     1/1     1            1           169m
default       deployment.apps/nginx                       1/1     1            1           147m
kube-system   deployment.apps/coredns                     1/1     1            1           2m26s
kube-system   deployment.apps/dashboard-metrics-scraper   0/1     1            0           77s
kube-system   deployment.apps/metrics-server              0/1     1            0           97s
kube-system   deployment.apps/kubernetes-dashboard        0/1     1            0           77s

NAMESPACE     NAME                                                   DESIRED   CURRENT   READY   AGE
kube-system   replicaset.apps/calico-kube-controllers-58d7965c58     1         1         1       169m
default       replicaset.apps/nginx-6799fc88d8                       1         1         1       147m
kube-system   replicaset.apps/coredns-7f9c69c78c                     1         1         1       2m26s
kube-system   replicaset.apps/dashboard-metrics-scraper-58d4977855   1         1         0       13s
kube-system   replicaset.apps/metrics-server-85df567dd8              1         1         0       13s
kube-system   replicaset.apps/kubernetes-dashboard-59699458b         1         1         0       13s



How to Expose the Dashboard

microk8s.kubectl expose service kubernetes-dashboard -n kube-system --port 8000 --type=NodePort --name kubserv
service/kubserv exposed

This is an excellent intro to namespaces, as you will notice the dashboard belongs to the namespace "kube-system" so we have to use "-n" for namespace and specify kube-system or it will not work (without -n it defaults to the "default" namespace).  As when we exposed nginx previously, it was running in the "default" namespace.

kube-system   service/kubernetes-dashboard        ClusterIP           443/TCP                                         42h

default       service/areebtest                   ClusterIP           80/TCP  

We can also delete the "kubserv" exposed service:

microk8s.kubectl delete service -n kube-system kubserv
service "kubserv" deleted



Let's Extend To an HA Kubernetes Cluster:

On the first node from above that you already created, run this command:

microk8s add-node
From the node you wish to join to this cluster, run the following:
microk8s join

If the node you are adding is not reachable through the default interface you can use one of the following:
 microk8s join


On the other nodes, use the join statement from above: microk8s join


microk8s cluster invalid token (500)

Be sure that you have connectivity to the master node in the join statement, that no firewall is blocking the connection, and that the join statement is copied and pasted correctly without any extra whitespace in the middle or typos.



install, kubernetes, debian, mint, ubuntu, linuxhttps, io, docs, tasks, kubectl, linux, https, microk, sudo, apt, snapd, lists, dependency, packages, installed, upgraded, newly, archives, kb, additional, disk, http, archive, focal, amd, fetched, selecting, previously, unselected, database, directories, currently, preparing, unpack, kubernetes_, _all, deb, unpacking, processing, triggers, db, enable, ips, ufw, firewall, apps, cni, default, routed, app, deployment, nginx, images, selector, clusterip, rtttest, restarts, pod, fc, sm, gd, cluster, ip, external, tcp, areebtest, desired, replicaset, dashboard, dns, enabling, applying, manifest, serviceaccount, coredns, configmap, spec, template, metadata, annotations, scheduler, alpha, functional, quot, priorityclassname, kube, clusterrole, rbac, authorization, clusterrolebinding, restarting, kubelet, enabled, metrics, server, aggregated, reader, rolebinding, auth, delegator, apiservice, apiregistration, beta, admin, certs, csrf, holder, settings, nodeselector, os, deprecated, scraper, token, retrieved, grep, user, restricted, permissions, github, blob, creating, md, namespaces, namespace, jhhkq, calico, node, jnsp, controllers, qpw, dnzm, containercreating, df, dd, rfsm, udp, daemonset, echo, nodeport, nic, microbot, vm, publicly,

Latest Articles

  • CentOS 7 / 8 cannot boot with with mdadm RAID array solution
  • How To Add Default Gateway in Linux using the ip route command routing
  • Error: Failed to download metadata for repo 'appstream': Cannot prepare internal mirrorlist: No URLs in mirrorlist Solution for Centos8 yum package install error
  • md mdadm array inactive how to start and activate the RAID array
  • Loaded: masked (Reason: Unit hostapd.service is masked.) Solution in Linux Debian Mint Ubuntu
  • Linux Mint Ubuntu Ubiquity Installer Bug EFI Installed To Wrong Partition Solution
  • Libreoffice Impress How To Change The Color of Links
  • ecryptfs How To Backup / Migrate Linux Mint Ubuntu Debian system ecryptfs properly and restore access
  • i915 nouveau Nvidia GPU not starting lightdm Xorg failing solution for Could not determine valid watermarks for inherited state
  • br0: received packet on bond0 with own address as source address Linux Solution Mint Debian Redhat CentOS bridge bridging
  • Debian Mint Ubuntu Howto Disable Network Manager
  • AMD GPU Xorg Won't Start [3576284.324] (EE) Segmentation fault at address 0x0 [3576284.325] (EE) Fatal server error: [3576284.325] (EE) Caught signal 11 (Segmentation fault). Server aborting
  • symbol 'grub_calloc' not found grub boot error solution / fix
  • /var/log/journal huge/too large solution in Debian Mint Ubuntu Linux Howot Fix
  • Libreoffice Calc Opens CSV Spreadsheet File as Asian Language/Chinese Characters Solution Fix
  • RTL8821AU Setup Configure Wifi Realtek 8821 in Linux Debian Mint Ubuntu Howto
  • How To Tell Which Repository a Package Comes From Debian Mint Ubuntu
  • How To Reload All Kernel Modules And List Required Moduels for Each Device - Linux Mint Debian Ubuntu Troubleshooting
  • Debian Ubuntu Mint How To Change Default Display Manager
  • Ubuntu Mint Debian Howto Execute Command / Script / Program Upon Wakeup From Sleep