Level 1 — Foundations · wrap-up
Cheat sheet & self-check
Every command from this section on one page.
Cluster lifecycle (kind)
kind create cluster --name lab --config kind-lab.yaml | Create the 3-node practice cluster |
kind get clusters | List your kind clusters |
kind delete cluster --name lab | Delete it (start fresh any time) |
First kubectl commands
kubectl version | Client and server versions |
kubectl cluster-info | Where the API server lives |
kubectl get nodes -o wide | Nodes, their IPs, OS and runtime |
kubectl config get-contexts | Which clusters kubectl knows about |
kubectl config use-context kind-lab | Point kubectl at the lab cluster |
Make life easier
alias k=kubectl | Shorter commands |
source <(kubectl completion bash) | Tab completion in bash |
kubectl explain pod.spec | Built-in docs for any field |
See the control plane
kubectl get pods -n kube-system -o wide | Control-plane and system pods, and which node they run on |
kubectl get --raw='/readyz?verbose' | API server health checks, one line each |
kubectl get events -A --sort-by=.lastTimestamp | Recent cluster events, newest last |
kubectl api-resources | Every object type the API server knows |
Look inside a node (kind)
docker exec -it lab-control-plane bash | Open a shell 'on' the node |
ls /etc/kubernetes/manifests | Static pod manifests for the control plane |
crictl ps | Containers the kubelet is running |
journalctl -u kubelet -f | Follow kubelet logs |
Pods
kubectl apply -f pod.yaml | Create or update from a file |
kubectl get pods -o wide | Pods with IP and node |
kubectl describe pod <name> | Details and events: first stop when debugging |
kubectl logs <pod> [-c container] [--previous] | Logs; --previous shows the crashed run |
kubectl exec -it <pod> -- sh | Shell inside the container |
kubectl run tmp --rm -it --image=busybox:1.36 -- sh | Throwaway debug pod |
Deployments
kubectl create deployment web --image=nginx:1.27 | Quick Deployment |
kubectl scale deployment web --replicas=5 | Scale out or in |
kubectl set image deployment/web nginx=nginx:1.27-alpine | Start a rolling update |
kubectl rollout status deployment/web | Wait for the rollout to finish |
kubectl rollout history deployment/web | Past revisions |
kubectl rollout undo deployment/web | Roll back to the previous revision |
kubectl rollout restart deployment/web | Restart all pods, one by one |
Generate YAML instead of typing it
kubectl create deployment web --image=nginx:1.27 --dry-run=client -o yaml > web.yaml | A starter manifest |
Services
kubectl expose deployment web --port=80 | Create a ClusterIP Service for a Deployment |
kubectl get svc,endpointslices -l app=web | Service and the pod IPs behind it |
kubectl describe svc web | Selector, ports and endpoints in one view |
kubectl port-forward svc/web 8080:80 | Reach a Service from your laptop |
DNS & connectivity tests
kubectl run tmp --rm -it --image=busybox:1.36 --restart=Never -- sh | Debug shell inside the cluster |
nslookup web | Resolve a Service name (inside the debug pod) |
wget -qO- http://web | Call the Service (inside the debug pod) |
kubectl get pods -n kube-system -l k8s-app=kube-dns | Are the CoreDNS pods healthy? |
DNS names
web | Same namespace |
web.shop | Service 'web' in namespace 'shop' |
web.shop.svc.cluster.local | Fully qualified name |
Install & inspect
kubectl apply -f https://kind.sigs.k8s.io/examples/ingress/deploy-ingress-nginx.yaml | ingress-nginx for kind (cluster needs port mappings + ingress-ready label) |
helm upgrade --install ingress-nginx ingress-nginx --repo https://kubernetes.github.io/ingress-nginx -n ingress-nginx --create-namespace | ingress-nginx with Helm (other clusters) |
kubectl get svc -n ingress-nginx ingress-nginx-controller | The controller's Service: EXTERNAL-IP or NodePorts |
kubectl get ingressclass | Which controllers exist (e.g. nginx) |
Rules & debugging
kubectl get ingress -A / kubectl describe ingress shop | Rules, backends, address |
kubectl get endpointslices -l kubernetes.io/service-name=shop | Pod IPs the controller will use |
kubectl logs -n ingress-nginx deploy/ingress-nginx-controller | Access log: status, upstream, latency |
curl -H 'Host: shop.example.com' http://<ingress-ip>/ | Test a host rule without DNS |
ConfigMaps
kubectl create configmap app-config --from-literal=APP_COLOR=blue | From key=value pairs |
kubectl create configmap nginx-conf --from-file=default.conf | From a file (key = file name) |
kubectl get configmap app-config -o yaml | See the contents |
Secrets
kubectl create secret generic db-cred --from-literal=username=app --from-literal=password='S3cr3t!' | Generic secret |
kubectl create secret tls web-tls --cert=tls.crt --key=tls.key | TLS certificate + key |
kubectl get secret db-cred -o jsonpath='{.data.password}' | base64 -d | Decode one value (anyone with read access can) |
Apply changes
kubectl rollout restart deployment/app | Pick up changed env vars |
kubectl exec deploy/app -- env | grep APP_ | Check what a pod actually sees |
Inspect storage
kubectl get storageclass | Available storage types (default marked) |
kubectl get pvc,pv | Claims and the volumes bound to them |
kubectl describe pvc <name> | Why a claim is Pending (events) |
Access modes
ReadWriteOnce (RWO) | Read-write by pods on ONE node |
ReadOnlyMany (ROX) | Read-only by many nodes |
ReadWriteMany (RWX) | Read-write by many nodes (NFS, CephFS, EFS) |
ReadWriteOncePod (RWOP) | Read-write by exactly one pod |
Volume types
emptyDir | Scratch space; lives and dies with the pod |
hostPath | A folder on the node; avoid for apps |
persistentVolumeClaim | Durable storage that outlives pods |
configMap / secret | Config files (lesson 05) |
Namespaces
kubectl create namespace shop | Create a namespace |
kubectl config set-context --current --namespace=shop | Make it your default for this context |
kubectl get all -n shop | Deployments, pods, Services in one list |
kubectl delete namespace shop | Delete it and everything inside |
Everyday debugging
kubectl get pods -n shop -w | Watch pods change state |
kubectl -n shop describe pod <name> | Events: scheduling, pulls, probes, mounts |
kubectl -n shop logs deploy/web | Logs from one pod of a Deployment |
kubectl -n shop get endpointslices | Which pods each Service really points to |
kubectl -n shop exec deploy/postgres -- psql -U shop -d shop -c 'select 1' | Run a command in a pod |