YAML with Kubernetes
Kubernetes is the leading platform for managing containerized applications at scale. Every resource in Kubernetes — pods, services, deployments, config maps — is defined using YAML files. YAML is not just useful in Kubernetes; it is the primary language of Kubernetes. Understanding how Kubernetes uses YAML is essential for anyone working with modern cloud infrastructure.
How Kubernetes Uses YAML
Kubernetes reads YAML files called manifests. Each manifest describes one resource — what it is, how it should behave, and what configuration it needs. These files are submitted to the Kubernetes API using the kubectl apply -f filename.yaml command.
Standard YAML Structure for Any Kubernetes Resource
Every Kubernetes YAML manifest follows the same four top-level keys:
apiVersion: apps/v1 # API version for this resource type kind: Deployment # What type of resource this is metadata: # Name, namespace, labels name: my-app namespace: default spec: # Desired state and configuration ...
| Key | Purpose | Example |
|---|---|---|
apiVersion | Which API group and version manages this resource | apps/v1, v1, networking.k8s.io/v1 |
kind | The type of Kubernetes resource | Pod, Deployment, Service |
metadata | Name, labels, annotations, and namespace | name: my-app |
spec | The desired configuration and behavior | Replicas, containers, ports, volumes |
Example 1 – Pod Definition
A Pod is the smallest deployable unit in Kubernetes. It contains one or more containers.
apiVersion: v1
kind: Pod
metadata:
name: hello-pod
labels:
app: hello
spec:
containers:
- name: hello-container
image: nginx:latest
ports:
- containerPort: 80
Example 2 – Deployment
A Deployment manages multiple identical Pods and handles updates, scaling, and recovery from failures.
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-deployment
namespace: default
labels:
app: web
spec:
replicas: 3 # Run 3 identical pods
selector:
matchLabels:
app: web # Manages pods with this label
template:
metadata:
labels:
app: web
spec:
containers:
- name: web-container
image: nginx:1.25
ports:
- containerPort: 80
resources:
requests:
memory: "64Mi"
cpu: "250m"
limits:
memory: "128Mi"
cpu: "500m"
Deployment Structure Diagram
Deployment
│
├── metadata (name, labels)
│
└── spec
├── replicas: 3
├── selector (which pods to manage)
└── template (pod blueprint)
├── metadata (pod labels)
└── spec
└── containers
├── name
├── image
├── ports
└── resources
Example 3 – Service
A Service exposes Pods over the network. It acts as a stable address for a set of Pods that may change.
apiVersion: v1
kind: Service
metadata:
name: web-service
spec:
selector:
app: web # Routes traffic to pods labeled app: web
ports:
- protocol: TCP
port: 80 # Port exposed by the service
targetPort: 80 # Port on the pod container
type: ClusterIP # Internal cluster access only
Service Types
| Type | Access | Use Case |
|---|---|---|
ClusterIP | Only within the cluster | Internal service communication |
NodePort | From outside the cluster via node IP | Development and testing |
LoadBalancer | From the internet via cloud load balancer | Production internet-facing services |
Example 4 – ConfigMap
A ConfigMap stores non-sensitive configuration data that containers can access as environment variables or files.
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config
namespace: default
data:
APP_ENV: production
LOG_LEVEL: info
MAX_CONNECTIONS: "100"
config.properties: |
server.port=8080
server.timeout=30
cache.enabled=true
Example 5 – Secret
A Secret stores sensitive data like passwords and API keys. Values must be base64-encoded.
apiVersion: v1 kind: Secret metadata: name: db-secret type: Opaque data: username: YWRtaW4= # base64 for "admin" password: c2VjcmV0MTIz # base64 for "secret123"
Multiple Resources in One File
YAML's multi-document feature (using ---) allows multiple Kubernetes resources to be defined in one file.
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-deployment
spec:
replicas: 2
selector:
matchLabels:
app: web
template:
metadata:
labels:
app: web
spec:
containers:
- name: web
image: nginx:latest
ports:
- containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
name: web-service
spec:
selector:
app: web
ports:
- port: 80
targetPort: 80
type: ClusterIP
Running kubectl apply -f app.yaml creates both the Deployment and the Service from this single file.
Labels and Selectors
Labels are key-value pairs attached to resources using the metadata.labels key. Selectors find resources that match specific labels. This is how Deployments know which Pods they manage and how Services know which Pods to route traffic to.
# Pod has this label
metadata:
labels:
app: web
version: v2
# Service selects pods with this label
spec:
selector:
app: web # Matches all pods where app = web
Common Kubernetes YAML Resources
| Resource | apiVersion | Purpose |
|---|---|---|
| Pod | v1 | Single unit of containers |
| Deployment | apps/v1 | Manages and scales pods |
| Service | v1 | Exposes pods over network |
| ConfigMap | v1 | Stores non-sensitive config |
| Secret | v1 | Stores sensitive data |
| Ingress | networking.k8s.io/v1 | HTTP routing rules |
| PersistentVolumeClaim | v1 | Requests storage for pods |
| Namespace | v1 | Logical cluster isolation |
Summary
- Every Kubernetes resource is defined in a YAML manifest
- All manifests share four top-level keys:
apiVersion,kind,metadata, andspec - Deployments manage multiple pod replicas and handle rolling updates
- Services provide stable network access to pods
- ConfigMaps and Secrets store configuration and sensitive data
- Multiple resources can be defined in one file using
---separators - Labels and selectors connect resources to each other
