A Practical Guide to Managing Kubernetes Resources
Most of day-to-day Kubernetes work comes down to a handful of object types and the lifecycle around them. If you are comfortable with Deployments, Services, ConfigMaps, and Secrets — and how to create, inspect, update, and delete them — you can operate the vast majority of workloads. This guide ties those pieces together.
Deployments: how your app actually runs
You rarely run bare Pods. A Deployment manages a ReplicaSet, which in turn keeps the right number of identical Pods alive and rolls out new versions safely.
apiVersion: apps/v1
kind: Deployment
metadata:
name: web
labels:
app: web
spec:
replicas: 3
selector:
matchLabels:
app: web
template:
metadata:
labels:
app: web
spec:
containers:
- name: web
image: ghcr.io/acme/web:1.4.2
ports:
- containerPort: 8080
Updating the image triggers a rolling update — new Pods come up, old ones drain — controlled by the strategy block. Roll forward or back without downtime:
kubectl set image deployment/web web=ghcr.io/acme/web:1.4.3
kubectl rollout status deployment/web
kubectl rollout undo deployment/web
Services: stable addressing for moving Pods
Pods are ephemeral and their IPs change. A Service gives a stable virtual IP and DNS name, load-balancing across the Pods that match its selector.
apiVersion: v1
kind: Service
metadata:
name: web
spec:
selector:
app: web
ports:
- port: 80
targetPort: 8080
The selector must match your Deployment's Pod labels. A Service with no matching Pods is the classic "it deployed but I can't reach it" bug — check the endpoints:
kubectl get endpoints web
ConfigMaps: configuration, not code
Keep environment-specific configuration out of your image with a ConfigMap, then mount it as env vars or files.
apiVersion: v1
kind: ConfigMap
metadata:
name: web-config
data:
LOG_LEVEL: "info"
FEATURE_BETA: "true"
envFrom:
- configMapRef:
name: web-config
Secrets: the same idea, for sensitive data
Secrets work like ConfigMaps but are meant for credentials and tokens. Values are base64-encoded (not encrypted by default), so enable encryption at rest and restrict access with RBAC.
kubectl create secret generic db-creds \
--from-literal=username=app \
--from-literal=password='s3cr3t'
The everyday lifecycle
Create and apply
Prefer declarative apply over imperative create — it is idempotent and works with version control:
kubectl apply -f ./manifests/
Inspect
kubectl get deploy,svc,cm,secretfor a quick overview.kubectl describe deploy/webfor events and rollout detail.kubectl logs deploy/webto read application output.
Update
Edit the manifest and re-apply, or patch in place. Re-applying is preferable because your Git history stays the source of truth.
Clean up
kubectl delete -f ./manifests/
Deleting a Deployment garbage-collects its ReplicaSets and Pods via owner references — you do not delete Pods by hand.
Labels tie it all together
Labels are the glue. Services select Pods by label, you query by label, and you group resources by label. A consistent labeling scheme (app, tier, env) pays for itself the first time you debug at 3am.
Seeing the whole picture
The hard part of resource management is not any single object — it is holding the relationships in your head: which Service points at which Deployment, which ConfigMap a Pod actually mounted, why endpoints are empty. A visual cockpit like Kubexer lets you browse these objects side by side, follow owner references, and confirm at a glance that your selectors line up, instead of stitching the picture together from a dozen kubectl commands.
Wrapping up
Master these four objects and the apply/inspect/update/delete loop, lean on labels, and keep your manifests in Git. Everything more advanced — autoscaling, ingress, policies — builds on this foundation.