Book Image

IoT Edge Computing with MicroK8s

By : Karthikeyan Shanmugam
Book Image

IoT Edge Computing with MicroK8s

By: Karthikeyan Shanmugam

Overview of this book

Are you facing challenges with developing, deploying, monitoring, clustering, storing, securing, and managing Kubernetes in production environments as you're not familiar with infrastructure technologies? MicroK8s - a zero-ops, lightweight, and CNCF-compliant Kubernetes with a small footprint is the apt solution for you. This book gets you up and running with production-grade, highly available (HA) Kubernetes clusters on MicroK8s using best practices and examples based on IoT and edge computing. Beginning with an introduction to Kubernetes, MicroK8s, and IoT and edge computing architectures, this book shows you how to install, deploy sample apps, and enable add-ons (like DNS and dashboard) on the MicroK8s platform. You’ll work with multi-node Kubernetes clusters on Raspberry Pi and networking plugins (such as Calico and Cilium) and implement service mesh, load balancing with MetalLB and Ingress, and AI/ML workloads on MicroK8s. You’ll also understand how to secure containers, monitor infrastructure and apps with Prometheus, Grafana, and the ELK stack, manage storage replication with OpenEBS, resist component failure using a HA cluster, and more, as well as take a sneak peek into future trends. By the end of this book, you’ll be able to use MicroK8 to build and implement scenarios for IoT and edge computing workloads in a production environment.
Table of Contents (24 chapters)
1
Part 1: Foundations of Kubernetes and MicroK8s
4
Part 2: Kubernetes as the Preferred Platform for IOT and Edge Computing
7
Part 3: Running Applications on MicroK8s
14
Part 4: Deploying and Managing Applications on MicroK8s
21
Frequently Asked Questions About MicroK8s

Understanding StatefulSets and DaemonSets

In this section, we'll go over two distinct approaches to deploying our application on Kubernetes: using StatefulSets and DaemonSets.

StatefulSets

The StatefulSet API object is used to handle stateful applications. A StatefulSet, like a deployment, handles pods that have the same container specification. A StatefulSet, unlike a deployment, continues using a persistent identity for each of its pods. These pods are generated for identical specifications, but they can't be exchanged: each has a unique identity that it keeps throughout any rescheduling.

The following example demonstrates the components of a StatefulSet:

apiVersion: v1
kind: Service
metadata:
  name: nginx
  labels:
    app: nginx
spec:
  ports:
  - port: 80
    name: web
  clusterIP: None
  selector:
    app: nginx
---
apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: web
spec:
  selector:
    matchLabels:
      app: nginx 
  serviceName: "nginx"
  replicas: 3 
  template:
    metadata:
      labels:
        app: nginx 
    spec:
      containers:
      - name: nginx
        image: nginx:latest
        ports:
        - containerPort: 80
          name: web
        volumeMounts:
        - name: www_volume
          mountPath: /usr/share/nginx/html
  volumeClaimTemplates:
  - metadata:
      name: www_volume
    spec:
      accessModes: [ "ReadWriteOnce" ]
      storageClassName: "my-storage-class"
      resources:
        requests:
          storage: 10Gi

In the preceding example, we have the following:

  • nginx is the headless service that is used to control the network domain.
  • web is the StatefulSet that has a specification that indicates that three replicas from the nginx container will be launched in unique pods.
  • volumeClaimTemplates will use PersistentVolumes provisioned by a PersistentVolume provisioner to offer stable storage.

Now, let's move on to DaemonSets.

DaemonSets

A DaemonSet guarantees that all (or some) nodes have a copy of a pod running. As nodes are added to the cluster, pods are added to them. As nodes are removed from the cluster, garbage is collected in pods. When you delete a DaemonSet, the pods it produced are also deleted.

The following are some example use cases regarding DaemonSets:

  • Run a daemon for cluster storage on each node, such as glusterd and ceph.
  • Run a daemon for logs to be collected on each node, such as Fluentd or FluentBit and logstash.
  • Run a daemon for monitoring on every node, such as Prometheus Node Exporter, collectd, or Datadog agent.

The following code shows a DaemonSet that's running the fluent-bit Docker image:

apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: fluent-bit
  namespace: kube-system
  labels:
    k8s-app: fluent-bit
spec:
  selector:
    matchLabels:
      name: fluent-bit
  template:
    metadata:
      labels:
        name: fluent-bit
    spec:
      tolerations:
      - key: node-role.kubernetes.io/master
        operator: Exists
        effect: NoSchedule
      containers:
      - name: fluent-bit
        image: fluent/fluent-bit:latest
        resources:
          limits:
            memory: 200Mi
          requests:
            cpu: 100m
            memory: 200Mi

In the preceding example, the fluent-bit DaemonSet has a specification that tells fluent-bit to run on all the containers.

The most commonly used kubectl commands concerning DaemonSets are as follows:

  • The create or apply command creates the DaemonSet:
    kubectl apply -f FILENAME.

For example, the kubectl apply -f ./daemonset-deployment.yaml command will create a new DaemonSet from the daemonset-deployment.yaml YAML file.

  • The get daemonset command is used to monitor the status of the DaemonSet:
    kubectl get daemonset 

This will produce the following output:

NAME               READY   UP-TO-DATE   AVAILABLE   AGE
daemonset-deployment   3/3     0            0           1s

The following fields are displayed:

  • NAME indicates the names of the DaemonSets in the namespace.
  • READY shows how many replicas of the application are available.
  • UP-TO-DATE shows the number of replicas that have been updated to achieve the desired state.
  • AVAILABLE shows how many replicas of the application are available.
  • AGE indicates the length of time the application has been running.
  • The describe daemonset command indicates the details of the DaemonSets:
    kubectl describe daemonset
  • The delete command removes the deployment that was made by the apply command:
    kubectl delete <<daemonset>>

With that, we've learned that a DaemonSet ensures that all or a set of nodes run a copy of a pod, while a StatefulSet is used to manage stateful applications. In the next section, we will look at jobs and CronJobs.