Learn how to – Managing Kubernetes Cluster using Portainer Web Dashboard.
Containerization is one of the highly adopted technologies in the past decade with Kubernetes playing a significant part. Containerization can well be defined as the packaging of software code required to run a lightweight executable referred to as a container.
Kubernetes as known as K8s is an open-source tool that plays a big role in orchestrating containerized workloads to run on a cluster of hosts. Normally, it works by distributing workloads across the cluster and automating the container networking needs. Moreso, it allocates storage and persistent volumes to the isolated container and works continuously to maintain the desired state of the container application.
Setting up a Kubernetes cluster can be done easily using a number of tools that include Minikube, Kubeadm, RKE2, Kubernetes on AWS (Kube-AWS), and Amazon EKS among many others. The real task now is how to manage the Kubernetes environment as it requires specialized skills. This creates a barrier to entry for companies trying to build and use K8s.
What is Portainer?
Portainer is a Kubernetes cluster management tool developed by Potainer.io. This organization believes that Kubernetes should be available to everyone and not only to those who are familiar with Kubernetes commands.
Portainer has been developed in a way that is easily comprehended by humans, allowing one to control the Kubernetes environment using a natural language. By doing so, it is able to absorb all the complexity involved in deploying and maintaining a Kubernetes cluster.
Portainer can work will several Kubernetes flavors that include MicroK8s, OpenShift K3s, K8s Native, EKS, AKS, DOKS e.t.c. The features associated with this nifty tool are:
- Intuitive Kubernetes GUI allows users/teams to speed up the learning process.
- Ability to deploy even the most complex apps in seconds.
- Easily set up and manage GitOps automation.
- Monitor the memory and CPU usage.
- Monitor events and the applications running in each node.
- It has the ability to convert the docker-compose format file to YAML compatible with k8s.
- Setup RBAC for your team to define user access to each cluster.
- Deploy load-balanced or proxied applications with ease.
- Troubleshoot and monitor apps, volumes, and configurations in a few clicks.
- Segment your cluster into resource pools, and securely assign resources to individuals or teams.
Portainer comes in two versions:
- Portainer Community Edition (CE): This is a free and open-source tool that allows individuals to build and manage containers in Docker, Docker Swarm, Kubernetes, and Azure ACI.
- Portainer Business Edition (BE): This is a commercial tool with features geared towards large organizations. The features include Role-Based Access Control, registry management, dedicated support e.t.c
By following this guide to the end, you should be able to manage a Kubernetes Cluster using Portainer Web Dashboard.
Setup Prerequisites
Portainer installation requires one to have the following requirements met:
- Persistent storage: this is required to maintain the database and configuration information required.
- Ports: to be able to access the web UI and the API, some ports need to be accessible. These are:
- 9443 for the server UI and API/30779 for Kubernetes with NodePort
- 9001 for the Portainer Agents/or 30778 for Kubernetes with NodePort
- A working and up-to-date Kubernetes cluster.
#1. Deploy a Kubernetes Cluster
There are several ways to deploy a Kubernetes cluster. The examples below can be used to deploy a Kubernetes cluster.
- Run Kubernetes on Debian with Minikube
- Deploy Kubernetes Cluster on Linux With k0s
- Install Kubernetes Cluster on Ubuntu using K3s
- Install Kubernetes Cluster on Rocky Linux 8 with Kubeadm & CRI-O
After creating the cluster, you need to install kubectl
:
curl -LO "https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/linux/amd64/kubectl"
chmod +x kubectl
sudo mv kubectl /usr/local/bin
Ensure the you can access the cluster with kubectl
##For RKE2
export PATH=$PATH:/var/lib/rancher/rke2/bin export KUBECONFIG=/etc/rancher/rke2/rke2.yaml
##For K0s
export KUBECONFIG=/var/lib/k0s/pki/admin.conf
Check the available nodes. In this guide, I have configured a cluster with 2 worker nodes and a single control plane.
# kubectl get nodes
NAME STATUS ROLES AGE VERSION
master Ready control-plane 2m24s v1.24.2+k0s
node1 Ready <none> 47s v1.24.2+k0s
node2 Ready <none> 44s v1.24.2+k0s
#2. Create a Persistent Storage.
Portainer requires at least one StorageClass available for data persistence. Here the WaitForFirstConsumer Binding Mode will be used to assign the volumeBindingMode to a persistent volume.
If you have a storage solution deployed in your Kubernetes Cluster, just provision a PVC for Portainer.
Manually creating StorageClass and PVC
To create a StorageClass, proceed as shown:
vim storageClass.yml
Add the below lines to the file
kind: StorageClass
apiVersion: storage.k8s.io/v1
metadata:
name: portainer-local-storage
provisioner: kubernetes.io/no-provisioner
volumeBindingMode: WaitForFirstConsumer
We will run all the deployments in a namespace called portainer and set it as the default namespace:
kubectl create namespace portainer
kubectl config set-context --current --namespace portainer
Apply the manifest.
# kubectl create -f storageClass.yml
storageclass.storage.k8s.io/portainer-local-storage
Proceed and create a local persistent volume:
vim portainer-pv.yml
Add the lines below to the file:
apiVersion: v1
kind: PersistentVolume
metadata:
name: portainer-local-pv
spec:
capacity:
storage: 10Gi
accessModes:
- ReadWriteOnce
persistentVolumeReclaimPolicy: Retain
storageClassName: portainer-local-storage
local:
path: /mnt/disk/vol1
nodeAffinity:
required:
nodeSelectorTerms:
- matchExpressions:
- key: kubernetes.io/hostname
operator: In
values:
- node1
Now on the specified node(node1), create the path/volume:
DIRNAME="vol1"
sudo mkdir -p /mnt/disk/$DIRNAME
sudo chmod 777 /mnt/disk/$DIRNAME
##Also run this On Rhel-based systems#####
sudo chcon -Rt svirt_sandbox_file_t /mnt/disk/$DIRNAME
Now apply the manifest:
kubectl create -f portainer-pv.yml
Check the created PV:
# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
portainer-local-pv 10Gi RWO Retain Available portainer-local-storage 5s
#3. Deploy the Portainer Pod
First, check if the created StorageClass is running:
# kubectl get sc
NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE
portainer-local-storage kubernetes.io/no-provisioner Delete WaitForFirstConsumer false 2m10s
Set the created StorageClass as default:
kubectl patch storageclass portainer-local-storage -p '{"metadata": {"annotations":{"storageclass.kubernetes.io/is-default-class":"true"}}}'
The portainer-local-storage is the name of the StorageClass. Check if the configuration has been applied:
# kubectl get sc
NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE
portainer-local-storage (default) kubernetes.io/no-provisioner Delete WaitForFirstConsumer false 2m53s
There are two ways how to deploy Portainer within a Kubernetes cluster:
- Using helm
- Using manifest file
Option 1 – Deploy Portainer using Helm
The required Helm version should be greater than v3.2. This can be installed using the command:
curl -fsSL -o get_helm.sh https://raw.githubusercontent.com/helm/helm/master/scripts/get-helm-3
chmod 700 get_helm.sh
sudo ./get_helm.sh
Once installed, verify the version:
$ helm version
version.BuildInfo{Version:"v3.10.1", GitCommit:"9f88ccb6aee40b9a0535fcc7efea6055e1ef72c9", GitTreeState:"clean", GoVersion:"go1.18.7"}
Now add the Portainer repository:
helm repo add portainer https://portainer.github.io/k8s/
helm repo update
Once the update is complete, run the below command to deploy Portainer. Remember, you can set how you wish to expose the service either via NodePort, LoadBalancer, or Ingress.
For this guide, we will go for the LoadBalancer service type
helm install --create-namespace -n portainer portainer portainer/portainer
--set service.type=LoadBalancer
For NodePort(Portainer will be available on port 30777 for HTTP and 30779 for HTTPS)
helm install --create-namespace -n portainer portainer portainer/portainer
For Ingress, you need to define the assigned Cluster IP, with an Nginx Ingress Controller at the defined hostname;
helm install --create-namespace -n portainer portainer portainer/portainer
--set service.type=ClusterIP
--set ingress.enabled=true
--set ingress.annotations.'kubernetes.io/ingress.class'=nginx
--set ingress.annotations."nginx.ingress.kubernetes.io/backend-protocol"=HTTPS
--set ingress.hosts[0].host=portainer.example.io
--set ingress.hosts[0].paths[0].path="/"
Verify if the pod is running:
kubectl get pods
Option 2 – Deploy Portainer using YAML manifests
The manifest only allows you to expose the service via NodePort or LoadBalancer. Here, we will apply the manifest and expose the service via LoadBalancer as shown:
kubectl apply -n portainer -f https://raw.githubusercontent.com/portainer/k8s/master/deploy/manifests/portainer/portainer-lb.yaml
If you want a Nodeport service(Portainer will be available on port 30777 for HTTP and 30779 for HTTPS), then the command will be:
kubectl apply -n portainer -f https://raw.githubusercontent.com/portainer/k8s/master/deploy/manifests/portainer/portainer.yaml
Get the pod:
# kubectl get pods
NAME READY STATUS RESTARTS AGE
portainer-755b555999-gdts2 1/1 Running 0 21s
The status of the PV should be bound to the PVC defined in the manifest now:
# kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
portainer-local-pv 10Gi RWO Retain Bound portainer/portainer portainer-local-storage 2m23s
#4. Access the Portainer Web UI
Once the pod has been deployed and the service exposed as desired, check the ports using the command:
# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
portainer LoadBalancer 10.100.239.137 <pending> 9000:30397/TCP,9443:30791/TCP,8000:30692/TCP 2m4s
In this guide, I have a Loadbalancer service with Portainer available on port 9000 for HTTP and 9443 for HTTPS. For NodePort, the service is available on port 30777 for HTTP and 30779 for HTTPS.
Remember self-signed SSL certificates are generated to secure traffic on HTTPS ports. If you have a firewall enabled, allow the ports through it:
##For UFW
sudo ufw allow 30397/tcp
sudo ufw allow 30791/tcp
##For Firewalld
sudo firewall-cmd --add-port=30397/tcp --permanent
sudo firewall-cmd --add-port=30791/tcp --permanent
sudo firewall-cmd --reload
Access the Portainer web interface using the URL https://Node-IP_address:30791/. Remember to capture the exact port to which the NodePort or Loadbalancer service has been exposed to.
In case you meet the above page, do not worry, all you need to do is restart the deployment:
# kubectl get deploy
NAME READY UP-TO-DATE AVAILABLE AGE
portainer 1/1 1 1 26m
# kubectl rollout restart deployment portainer
deployment.apps/portainer restarted
You need to create the administrator. The default username is admin but can be altered later.
#5. Manage Kubernetes using Portainer
Once created, you will be presented with the below dashboard.
You can connect to the local cluster and get started.
Clicking on the cluster, you can see all the available resources and manage them easily.
You can launch the CLI and execute commands as shown.
For example, creating a namespace, select Add namespaces with form and proceed as shown
Once the namespace has been created, it will be available under the namespaces tab.
To connect to another environment, click on environment and add one:
Start the Wizard.
Run the highlighted command on your terminal to deploy and Portainer agent application running on port 9001.
# kubectl get svc
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
portainer LoadBalancer 10.43.234.219 <pending> 9000:31239/TCP,9443:31576/TCP,8000:31904/TCP 59m
portainer-agent LoadBalancer 10.43.250.41 <pending> 9001:32621/TCP 41m
portainer-agent-headless ClusterIP None <none> <none> 41m
Using port 9001, add an environment. Once successfully added, the environment will be available:
Now edit the cluster as preferred by clicking on cluster->setup
To deploy an application, proceed to the applications tab and select add application with form. Select the namespace, and set the pod name, image, and environment variables.
Also, scroll down and configure the service for the application:
Verify this from the terminal
# kubectl get pod -n sample
NAME READY STATUS RESTARTS AGE
nginx-7fd8db4db7-hfsdr 1/1 Running 0 4m41s
# kubectl get svc -n sample
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
nginx LoadBalancer 10.43.208.66 <pending> 80:30626/TCP 5m13s
Access the service from the web.
That is it!
We have systematically walked through how to manage Kubernetes Cluster using Portainer Web Dashboard. We have seen how easy managing Kubernetes resources can be, using Portainer. I hope this was significant.
See more:
- k9s – Best Kubernetes CLI To Manage Your Clusters In Style
- Manage Multiple Kubernetes Clusters with kubectl & kubectx
- Using Mirantis Container Runtime(MCR) in Kubernetes and Docker Swarm
Leave a Reply
You must be logged in to post a comment.