K8s
DevOps K8s Overview 1
- Kubernetes:
- Manages containerized workloads and services.
- A Kubernetes deployment gives you a cluster.
- Service: an abstraction that exposes an application and provides a cluster IP, a DNS name, and a port for a set of pods.
- Pods:
- The basic components of an application workload.
- The smallest deployable units of computing that Kubernetes can create and manage.
- Groups of containers that share namespaces, filesystem volumes, and network resources.
- Containers within the same logical host are tightly coupled. Outside a cloud environment, the logical host is usually the same physical machine or VM.
- Node: a VM or physical machine that hosts pods for the application workload.
- Control plane: in production, the control plane usually runs across multiple machines.
- Namespace: a logical boundary for resource names, commonly used for environments such as
dev,uat, andprod. - Target port: the port on a pod that a service maps incoming traffic to.
DevOps K8s Overview 2
- Ingress controller: users access the ingress controller via domain name, which then routes to different services (music, streaming, shopping, etc.)
- Managed Kubernetes options:
- Azure K8s service
- GCP Kubernetes service
- AWS EKS
- Control plane: Azure Kubernetes Service cluster management, including auto-scaling.
- Cosmos DB: Azure NoSQL database.
- Grafana: visualizes logs and metrics from Azure data sources; it may pull log data from NoSQL storage depending on the architecture.
- Relationships:
- One Kubernetes cluster has many nodes or VMs for fault tolerance and high availability.
- One service can target many pods.
- One node has at least one pod; worker nodes host the pods.
- One pod has at least one container.
DevOps K8s Deep 1
K8s is designed to be more powerful, more flexible, and more robust; refer to earlier posts for basic info.
Docker on a single EC2 instance creates a single point of failure.
Control plane == orchestrator.
Kubernetes provides:
- Service discovery and load balancing: Kubernetes can discover services and expose containers through DNS.
- Storage orchestration across local and cloud storage.
- Automated rollouts and rollbacks for code and configuration across multiple containers.
- Automatic bin packing: Kubernetes places workloads efficiently, scales up or down, and can enforce custom resource allocation. A common target is keeping node CPU below about 60%.
- Self-healing: Kubernetes detects health problems, replaces broken instances, and waits for new instances to become healthy before routing traffic.
- Secret and configuration management for environment variables, passwords, and centralized configuration.
Control panel:
- Decides which pods run on which nodes, maximizing resource utilization.
- Creates pods.
- Can run on one node in a small setup, but should be highly available in production.
- Kube-apiserver: exposes the Kubernetes API and is used for service communication.
- etcd: stores secrets & configuration
- kube-scheduler: assign new pod to available node, better space management
- Kube-controller-manager: logic handler
- Cloud-controller-manager: integrates with cloud provider APIs at the cluster level
DevOps K8s Deep 2
Node:
- == EC2
- A node is managed by the control plane.
- It does the actual work and is also called a worker node.
- Each node runs at least one pod.
- at least one kubelet: a middleman between the brain (control plane) and the worker
- at least one container runtime: responsible for running containers (anything that implements the container runtime interface works)
- Kube-proxy: network proxy, responsible for managing IP communication between pods
- Docker here is responsible for managing containers within each pod
K8s cluster:
- at least one worker node
- Cluster services run across multiple servers and control multiple nodes.
Swarm: creates a swarm using the Docker CLI, think of it as a lightweight, Docker-native Kubernetes
- swarm == Kubernetes cluster
- Kind: a tool for running local Kubernetes clusters using docker container "nodes". Primarily used for testing Kubernetes itself
- namespace == isolated logical project
- ingress controller == load balancer
Swarm troubleshooting tips:
- Version, version, version! Try to match your instructor's version as closely as possible, otherwise there will be many pitfalls
- If using Kubernetes 1.21, remember to use apiVersion: batch/v1beta1 in demojob; otherwise use apiVersion: batch/v1 (I succeeded by upgrading to the latest Kubernetes 1.25)
- Similarly, for kubectl -n create token admin-user, if using an older version, the command will not exist and you cannot directly generate an admin user token
Kubernetes basic components 1
- Kubernetes benefits: high availability, high scalability, and disaster recovery.
- Pods
- abstraction over container
- each pod gets its own private IP address
- smallest unit
- service:
- provide the permanent IP address
- lifecycle of pod and service not connected; so when one fails, another one can connect directly quickly
- load balancer; send traffic to more pods
- internal service vs external service(public ip address with port in the node level): private IP vs public IP
- Ingress: a proxy(provides Public IP address) for external service → connect to service
- ConfigMap: external configuration of your application (the Pod actually gets the data that ConfigMap contains) such as url link (ENV)
- secret: used to store secret data without a plain text (ENV)
- Volumes: preserve data because Kubernetes does not manage application data persistence by itself.
- deployment:
- A blueprint for application pods, including how many replicas should run and how they scale up or down.
- is a layer of abstraction on top of pods
- deployment for stateless Apps vs StatefulSet for stateful apps or DB
K8s Basic components 2
- one node(slave nodes) must have: container runtime, kubelet, Kube proxy
- kubelet: interacts with both container and node; starting a pod with a container inside and assign the resource from node to the container (CPU, RAM)
- Kube Proxy: forwarding requests from services to pods (avoid network overhead of sending the request to another machine)
- Master nodes(control plane):
- API server: like a cluster gateway which gets the initial request of any UPDATE or QUERY; acts as a gatekeeper for authentication.
- scheduler: schedule new pod → api server → scheduler → where to put the pod (like packing luggage, stuffing bags of different sizes into different containers); scheduler just decides on which Node new Pod should be scheduled. (the actual execution is done by kubelet on each node)
- controller management: detect any pods die in any nodes and reschedule those pods as soon as possible; (detects cluster state changes); controller manager → scheduler → kubelet; ensures proper STATE of cluster components.
- etcd: key-value store of a cluster state; cluster brain! dedicated to recording state; this storage cross all the master replica nodes. A typical small cluster has 2 masters and 3 workers; masters require less compute resources, workers require more; masters and workers can be scaled infinitely based on demand
- Worker nodes:
- container runtime engine: Docker, containerd, CRI-O, frakti…
- kubelet: it is an agent that runs on each node in the cluster — ensures each instance is running correctly and reports back to master; scheduler also uses this to create pods
- kube-proxy(network proxy): allows each node communicate with each other (allow network communications)
K8s Services
- A service links to pods through selectors.
- Kubernetes creates an Endpoint object with the same name as the service and tracks which pods are members of that service.
- Headless service: only communicate with 1 specific Pod directly (ClusterIP: None)
- load balancer service is an extension of the NodePort Service
- NodePort Service is an extension of ClusterIP service
K8s Common Imperative Commands
- kubectl edit pod redis: edit the YAML configuration of an already-created pod, which in turn modifies the image used to build the pod
- kubectl run <tagName, your own name> --image=<docker image name> e.g. kubectl run redis --image=redis meaning: create a new pod
- kubectl delete pods <tagName> — delete a specific pod
- kubectl get pods -o wide — get a list of pods with extended output (wide)
- kubectl describe pod <tagName>
- kubectl get pods
- kubectl run redis --images=redis123 --dry-run=client -o YAML > redis.yaml — output configuration to YAML file
- kubectl apply -f <filename> — apply a file to create pods
- kubectl create -f <filename> — create from file
- kubectl get replicaset: get command to see a list of replica sets created
- kubectl delete replicaset <tagName>
- kubectl replace -f replicaset <fileName> — replace configuration
- kubectl scale --replicas=6 -f <fileName>
- kubectl edit replicaset myapp-replicaset — edit replicaset settings
- kubectl scale rs new-replica-set --replicas=2 — rs is short for replicaset
- kubectl get all — get full details including deployments, replicas and pods.
Deployment strategy: create, get, update, status, rollback
- kubectl rollout undo deployment/myapp-deployment — rollback deployed code
-- record=true will record the command execution history
- kubectl set image deployment myapp-deployment Nginx=Nginx:1.18 — update image
Service
- NodePort: allows external access to internal services, split into target port, port, and nodeport
kubectl get pods,svc — view both running services
debugging:
kubectl logs {pod-name}
kubectl exec -it <pod name> --bin/bash
kubectl get deployment nginx-deployment -o YAML > nginx-deployment-result.yaml — copy configuration info to YAML file
'kubectl delete --all deployments --namespace=foo' — delete all deployments, services, etc.
When starting a service with type=loadbalancer, use minikube service mongo-express-service to expose the external IP address
kubectl create namespace uat-petlover
Volume
- PersistentVolume (PV): not tied to any namespace; it is available to the whole cluster.
- PersistentVolumeClaim (PVC): must exist in the same namespace as the pod that uses it.
- StorageClass (SC): provisions persistent volumes dynamically when a PVC requests storage.
- ConfigMaps and Secrets are local volume sources managed by Kubernetes; they are not created through PVs or PVCs.
Usage flow:
- Old approach: admins configure storage (Manually) => create PV => developer claim PV using PVC
- New approach: developer claim PV using PVC => Storage class SC allocate resources (PV) to developer
Helm - Package Manager of K8s
- Helm Charts:
- bundle of Yaml files
- create your own Helm charts with Helm
- push them to Helm repository
- Use charts created by others.
- Helm hub, Helm repository, Helm pages
- templating engine
- define a common blueprint
- dynamic values are replaced by placeholders
- dev - staging - prod
- release management: state management in tiller server (V2, V3 now tiller no longer exists)
- Helm command:
- Add a Helm repository locally: helm repo add bitnami https://charts.bitnami.com/bitnami
- Search for needed application from your added repository: helm search repo Jenkins
- Pull down a Helm chart: helm pull bitnami/<image_name> --untar=true
- Install a Helm chart: helm install <give-a-name> bitnami/nginx
- Delete a Helm chart's deployed service from the node: helm delete <give-a-name> (note: at this point, the service inside the pod will also be deleted)
Namespaces in system
- Arch knowledge:
- deployment manage a replica set
- replica set manage all replica of its pod
- the pod is an abstraction of a container
- Kubernetes namespaces
- a virtual cluster inside a cluster
- kubernetes-dashboard(namespace) only with minikube
- kube-system: system processes; master and kubectl processes; do not create or modify in kube-system
- kube-public: publicly accessible data; a configmap, which contains cluster information
- kube-node-lease: heartbeats of nodes; each node has associated lease object in namespace; determines the availability of a node
- default: resources you create are located here
- kubectl create namespace my-namespace
- create a namespace with a configuration file
- When should you use multiple namespaces?
- To group resources such as databases, monitoring, logging, Elastic Stack, and Nginx-ingress.
- To let multiple teams work on the same application without affecting each other.
- resource sharing: staging and development
- blue/green deployment (reuse those components in both envs)
- To enforce resource limits in constrained environments. Each namespace should define its own ConfigMaps; services can communicate across namespaces.
- Volumes and nodes are not namespaced; they are shared cluster resources.
- Add
--namespace=my-namespaceto isolate commands to a namespace. - Switch namespace:
- kubectl config set-context $(kubectl config current-context) --namespace=test-ns — switch to test-ns
- kubectl config set-context $(kubectl config current-context) --namespace=default — switch back to default
- kube-node-lease: improves the performance of our node heartbeats (benefit for cluster autoscaling)
- kube-public: readable for cluster
- kube-system:
- kube-dns
- kube-proxy
- ebs-csi-node
Probes
- liveness Probe
- kubelet uses liveness probes to know when to restart a container
- liveness probes could catch a deadlock, restart container " livenessProbe: exec: command: - /bin/sh - -c - nc -z localhost 8095 initialDelaySeconds: 60 periodSeconds: 10 " 'nc -z' will check if someone is listening on the other side
- readiness probe
- to know when a container is ready to accept traffic
- When the container is not ready, remove it from load balancers based on the readiness probe signal.
- startup probe:
- when a container application has started
- it will disable liveness & readiness checks first to avoid restarting container repeatedly
OIDC and IRSA with IAM identity federation
- To enable and use AWS IAM roles for Kubernetes service accounts on our EKS cluster, we must create & associate OIDC identity provider. Allow it to make calls to AWS APIs on your behalf.
- IRSA: IAM role service account — can associate an IAM role with a Kubernetes service account, so that service account can provide AWS permissions to any pods using that service account
- To create and associate an OIDC identity provider with our EKS cluster, we need to follow these steps:
- Create an IAM OIDC provider in the IAM console.
- Associate the IAM OIDC provider with our EKS cluster.
- Create an IAM policy that allows our Kubernetes service account to assume the IAM role.
- Create a Kubernetes service account that uses the IAM role.
- Verify that the Kubernetes service account can assume the IAM role by running a test pod.
- OpenID connect provider: EKS acts as a provider, you can use the AWS EKS OpenID Connect provider to access AWS services using the IAM identity federation https://docs.aws.amazon.com/eks/latest/userguide/iam-roles-for-service-accounts.html