Core Concepts

9 min read
Rapid overview

Kubernetes Core Concepts

Architecture Overview

Control Plane Components

ComponentPurpose
kube-apiserverFrontend for the Kubernetes control plane, exposes REST API
etcdConsistent, highly-available key-value store for cluster data
kube-schedulerWatches for newly created Pods and assigns nodes
kube-controller-managerRuns controller processes (Node, Job, EndpointSlice, ServiceAccount)
cloud-controller-managerLinks cluster to cloud provider's API

Node Components

ComponentPurpose
kubeletAgent that ensures containers are running in a Pod
kube-proxyNetwork proxy maintaining network rules on nodes
Container RuntimeSoftware responsible for running containers (containerd, CRI-O)

Workload Resources

Pods

The smallest deployable unit in Kubernetes.

apiVersion: v1
kind: Pod
metadata:
  name: nginx-pod
  labels:
    app: nginx
spec:
  containers:
  - name: nginx
    image: nginx:1.25
    ports:
    - containerPort: 80
    resources:
      requests:
        memory: "64Mi"
        cpu: "250m"
      limits:
        memory: "128Mi"
        cpu: "500m"

Key Interview Points:

  • Pods are ephemeral - designed to be replaced, not repaired
  • Multi-container patterns: sidecar, ambassador, adapter
  • Init containers run before app containers
  • Pod lifecycle: Pending → Running → Succeeded/Failed

Deployments

Manages ReplicaSets and provides declarative updates for Pods.

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  strategy:
    type: RollingUpdate
    rollingUpdate:
      maxSurge: 1
      maxUnavailable: 0
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1.25
        ports:
        - containerPort: 80

Deployment Strategies:

  • RollingUpdate (default): Gradually replaces old pods
  • Recreate: Terminates all existing pods before creating new ones

StatefulSets

For stateful applications requiring stable identities.

apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: postgres
spec:
  serviceName: "postgres"
  replicas: 3
  selector:
    matchLabels:
      app: postgres
  template:
    metadata:
      labels:
        app: postgres
    spec:
      containers:
      - name: postgres
        image: postgres:15
        volumeMounts:
        - name: data
          mountPath: /var/lib/postgresql/data
  volumeClaimTemplates:
  - metadata:
      name: data
    spec:
      accessModes: ["ReadWriteOnce"]
      resources:
        requests:
          storage: 10Gi

StatefulSet Guarantees:

  • Stable, unique network identifiers (pod-0, pod-1, pod-2)
  • Stable, persistent storage
  • Ordered, graceful deployment and scaling
  • Ordered, automated rolling updates

DaemonSets

Ensures all (or some) nodes run a copy of a Pod.

apiVersion: apps/v1
kind: DaemonSet
metadata:
  name: fluentd
spec:
  selector:
    matchLabels:
      name: fluentd
  template:
    metadata:
      labels:
        name: fluentd
    spec:
      tolerations:
      - key: node-role.kubernetes.io/control-plane
        operator: Exists
        effect: NoSchedule
      containers:
      - name: fluentd
        image: fluentd:v1.16

Use Cases:

  • Log collectors (Fluentd, Filebeat)
  • Node monitoring (Prometheus node-exporter)
  • Storage daemons (Ceph, GlusterFS)

Jobs and CronJobs

apiVersion: batch/v1
kind: Job
metadata:
  name: database-migration
spec:
  ttlSecondsAfterFinished: 100
  backoffLimit: 4
  template:
    spec:
      restartPolicy: Never
      containers:
      - name: migrate
        image: myapp:latest
        command: ["./migrate.sh"]
---
apiVersion: batch/v1
kind: CronJob
metadata:
  name: nightly-backup
spec:
  schedule: "0 2 * * *"
  concurrencyPolicy: Forbid
  jobTemplate:
    spec:
      template:
        spec:
          restartPolicy: OnFailure
          containers:
          - name: backup
            image: backup-tool:latest

Services and Networking

Service Types

TypeDescriptionUse Case
ClusterIPInternal cluster IP (default)Inter-service communication
NodePortExposes service on each Node's IP at static portDevelopment/debugging
LoadBalancerExternal load balancer (cloud provider)Production external access
ExternalNameMaps service to external DNS nameExternal service integration
apiVersion: v1
kind: Service
metadata:
  name: my-service
spec:
  type: ClusterIP
  selector:
    app: my-app
  ports:
  - port: 80
    targetPort: 8080
    protocol: TCP

Ingress

HTTP/HTTPS routing to services.

apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: app-ingress
  annotations:
    nginx.ingress.kubernetes.io/rewrite-target: /
spec:
  ingressClassName: nginx
  rules:
  - host: api.example.com
    http:
      paths:
      - path: /v1
        pathType: Prefix
        backend:
          service:
            name: api-v1
            port:
              number: 80
      - path: /v2
        pathType: Prefix
        backend:
          service:
            name: api-v2
            port:
              number: 80
  tls:
  - hosts:
    - api.example.com
    secretName: tls-secret

NetworkPolicy

Control traffic flow at the IP address or port level.

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: api-network-policy
spec:
  podSelector:
    matchLabels:
      app: api
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - podSelector:
        matchLabels:
          app: frontend
    ports:
    - protocol: TCP
      port: 8080
  egress:
  - to:
    - podSelector:
        matchLabels:
          app: database
    ports:
    - protocol: TCP
      port: 5432

Configuration and Secrets

ConfigMaps

apiVersion: v1
kind: ConfigMap
metadata:
  name: app-config
data:
  DATABASE_HOST: "postgres.default.svc.cluster.local"
  LOG_LEVEL: "info"
  config.json: |
    {
      "feature_flags": {
        "new_ui": true
      }
    }

Usage Patterns:

  • Environment variables
  • Command-line arguments
  • Configuration files via volumes

Secrets

apiVersion: v1
kind: Secret
metadata:
  name: db-credentials
type: Opaque
data:
  username: YWRtaW4=  # base64 encoded
  password: cGFzc3dvcmQxMjM=
---
# Using in a Pod
spec:
  containers:
  - name: app
    envFrom:
    - secretRef:
        name: db-credentials
    # Or individual keys:
    env:
    - name: DB_PASSWORD
      valueFrom:
        secretKeyRef:
          name: db-credentials
          key: password

Secret Types:

  • Opaque - arbitrary user-defined data
  • kubernetes.io/tls - TLS certificates
  • kubernetes.io/dockerconfigjson - Docker registry credentials
  • kubernetes.io/service-account-token - Service account tokens

Storage

PersistentVolume and PersistentVolumeClaim

apiVersion: v1
kind: PersistentVolume
metadata:
  name: pv-storage
spec:
  capacity:
    storage: 10Gi
  accessModes:
    - ReadWriteOnce
  persistentVolumeReclaimPolicy: Retain
  storageClassName: standard
  hostPath:
    path: /data/pv
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: pvc-storage
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 5Gi
  storageClassName: standard

Access Modes:

  • ReadWriteOnce (RWO) - mounted read-write by single node
  • ReadOnlyMany (ROX) - mounted read-only by many nodes
  • ReadWriteMany (RWX) - mounted read-write by many nodes

Reclaim Policies:

  • Retain - manual reclamation
  • Delete - automatic deletion
  • Recycle - basic scrub (deprecated)

StorageClass

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
  name: fast-storage
provisioner: kubernetes.io/aws-ebs
parameters:
  type: gp3
  iopsPerGB: "50"
reclaimPolicy: Delete
allowVolumeExpansion: true
volumeBindingMode: WaitForFirstConsumer

Resource Management

Resource Requests and Limits

resources:
  requests:
    memory: "256Mi"
    cpu: "500m"
  limits:
    memory: "512Mi"
    cpu: "1000m"

Interview Key Points:

  • Requests: Guaranteed resources, used for scheduling
  • Limits: Maximum resources, enforced by kubelet
  • CPU is compressible (throttled), memory is not (OOMKilled)
  • QoS Classes: Guaranteed, Burstable, BestEffort

LimitRange

Enforces default limits on a namespace.

apiVersion: v1
kind: LimitRange
metadata:
  name: cpu-memory-limits
spec:
  limits:
  - default:
      memory: "512Mi"
      cpu: "500m"
    defaultRequest:
      memory: "256Mi"
      cpu: "250m"
    max:
      memory: "1Gi"
      cpu: "1"
    min:
      memory: "128Mi"
      cpu: "100m"
    type: Container

ResourceQuota

Limits aggregate resource consumption per namespace.

apiVersion: v1
kind: ResourceQuota
metadata:
  name: compute-quota
spec:
  hard:
    requests.cpu: "10"
    requests.memory: "20Gi"
    limits.cpu: "20"
    limits.memory: "40Gi"
    pods: "50"
    services: "10"
    persistentvolumeclaims: "10"

Scheduling

Node Selectors

spec:
  nodeSelector:
    disktype: ssd
    kubernetes.io/os: linux

Affinity and Anti-Affinity

spec:
  affinity:
    nodeAffinity:
      requiredDuringSchedulingIgnoredDuringExecution:
        nodeSelectorTerms:
        - matchExpressions:
          - key: topology.kubernetes.io/zone
            operator: In
            values:
            - us-east-1a
            - us-east-1b
    podAntiAffinity:
      preferredDuringSchedulingIgnoredDuringExecution:
      - weight: 100
        podAffinityTerm:
          labelSelector:
            matchLabels:
              app: web
          topologyKey: kubernetes.io/hostname

Taints and Tolerations

# Taint a node
kubectl taint nodes node1 key=value:NoSchedule
# Pod toleration
spec:
  tolerations:
  - key: "key"
    operator: "Equal"
    value: "value"
    effect: "NoSchedule"

Taint Effects:

  • NoSchedule - New pods won't be scheduled
  • PreferNoSchedule - System will try to avoid scheduling
  • NoExecute - Existing pods will be evicted

Common kubectl Commands

# Context and configuration
kubectl config get-contexts
kubectl config use-context <context-name>

# Resource management
kubectl get pods -n <namespace> -o wide
kubectl describe pod <pod-name>
kubectl logs <pod-name> -c <container-name> --previous
kubectl exec -it <pod-name> -- /bin/sh

# Debugging
kubectl get events --sort-by='.lastTimestamp'
kubectl top pods
kubectl top nodes

# Rollouts
kubectl rollout status deployment/<name>
kubectl rollout history deployment/<name>
kubectl rollout undo deployment/<name> --to-revision=2

# Scaling
kubectl scale deployment <name> --replicas=5
kubectl autoscale deployment <name> --min=2 --max=10 --cpu-percent=80

Interview Questions

Q: What is a Pod and why is it the smallest deployable unit in Kubernetes?

A: A Pod is a group of one or more containers that share the same network namespace (localhost), storage volumes, and lifecycle. It is the smallest deployable unit because Kubernetes schedules and manages at the Pod level, not the individual container level. Pods are ephemeral by design -- they are meant to be replaced, not repaired.

Q: What are the common multi-container Pod patterns?

A: The three main patterns are: sidecar (adds functionality like log shipping or proxying alongside the main container), ambassador (proxies network connections on behalf of the main container, e.g., to a database), and adapter (transforms the main container's output into a standardized format, e.g., for monitoring). Init containers also run before app containers to perform setup tasks.

Q: How does a Deployment manage rolling updates?

A: A Deployment creates a new ReplicaSet with the updated Pod template and gradually scales it up while scaling down the old ReplicaSet. The maxSurge parameter controls how many extra Pods can exist above the desired count, and maxUnavailable controls how many Pods can be unavailable during the update. You can roll back with kubectl rollout undo if something goes wrong.

Q: What are the four Kubernetes Service types and when would you use each?

A: ClusterIP (default) exposes the service on an internal cluster IP for inter-service communication. NodePort exposes the service on a static port on each node's IP, useful for development. LoadBalancer provisions an external cloud load balancer for production external access. ExternalName maps the service to an external DNS name for integrating with services outside the cluster.

Q: How do ConfigMaps and Secrets differ, and what are the best practices for each?

A: ConfigMaps store non-sensitive configuration data as key-value pairs, while Secrets store sensitive data (passwords, tokens, keys) with base64 encoding. Both can be consumed as environment variables or mounted as files. Best practices: use Secrets for anything sensitive, integrate external secrets managers (Vault, AWS Secrets Manager) for production, use RBAC to restrict Secret access, and prefer volume mounts over environment variables since env vars can leak into logs and child processes.

Q: What are liveness, readiness, and startup probes, and when should you use each?

A: Liveness probes detect if a container is stuck or deadlocked -- kubelet restarts the container if the probe fails. Readiness probes determine if a container is ready to accept traffic -- failing containers are removed from Service endpoints. Startup probes run once during container startup for slow-starting apps, disabling liveness/readiness checks until the app is initialized. Use liveness for crash recovery, readiness for load balancing, and startup for applications with long initialization times.

Q: What are Kubernetes namespaces and how do they help manage a cluster?

A: Namespaces provide logical isolation within a cluster, allowing you to partition resources by team, environment (dev/staging/prod), or application. They scope resource names (avoiding collisions), enable per-namespace ResourceQuotas and LimitRanges to control resource consumption, and support RBAC policies for access control. Default namespaces include default, kube-system, kube-public, and kube-node-lease.

Q: What happens when a node fails in a Kubernetes cluster?

A: The controller manager detects the failure via kubelet heartbeat timeout (default 40s). After the pod-eviction-timeout (default 5 minutes), pods on the failed node are marked as Terminating. The ReplicaSet controller detects the desired replica count is not met and creates replacement pods. The scheduler places those new pods on healthy nodes based on resource availability and constraints.

Q: How does Kubernetes service discovery work?

A: Kubernetes provides DNS-based service discovery through CoreDNS. Every Service gets a DNS entry in the format <service-name>.<namespace>.svc.cluster.local that resolves to the Service's ClusterIP. Pods can also discover services via environment variables injected at startup (legacy approach). Headless services (ClusterIP: None) return individual Pod IPs instead, useful for StatefulSets.

Q: Explain the difference between a Deployment and a StatefulSet.

A: Deployments manage stateless applications where pods are interchangeable, can scale in parallel, and use random names (e.g., nginx-abc123). StatefulSets manage stateful applications requiring stable, unique network identifiers (pod-0, pod-1, pod-2), persistent storage tied to each pod, and ordered graceful deployment, scaling, and rolling updates. Use Deployments for web servers and APIs; use StatefulSets for databases and distributed systems like Kafka or Elasticsearch.