What is Docker?
Docker is a platform for developing, shipping and running applications in containers. Containers let you package an application with all its dependencies and run it in any environment.
Docker basics
Dockerfile
# Base image
FROM node:20-alpine AS base
# Install dependencies
FROM base AS deps
WORKDIR /app
COPY package*.json ./
RUN npm ci --only=production
# Build the application
FROM base AS builder
WORKDIR /app
COPY --from=deps /app/node_modules ./node_modules
COPY . .
RUN npm run build
# Production image
FROM base AS runner
WORKDIR /app
ENV NODE_ENV=production
# Create a user
RUN addgroup --system --gid 1001 nodejs
RUN adduser --system --uid 1001 nextjs
COPY --from=builder /app/public ./public
COPY --from=builder --chown=nextjs:nodejs /app/.next/standalone ./
COPY --from=builder --chown=nextjs:nodejs /app/.next/static ./.next/static
USER nextjs
EXPOSE 3000
ENV PORT 3000
CMD ["node", "server.js"]
Docker Compose
# docker-compose.yml
version: '3.8'
services:
app:
build: .
ports:
- "3000:3000"
environment:
- DATABASE_URL=postgresql://user:pass@db:5432/mydb
- REDIS_URL=redis://redis:6379
depends_on:
- db
- redis
restart: unless-stopped
db:
image: postgres:16-alpine
volumes:
- postgres_data:/var/lib/postgresql/data
environment:
- POSTGRES_USER=user
- POSTGRES_PASSWORD=pass
- POSTGRES_DB=mydb
restart: unless-stopped
redis:
image: redis:7-alpine
volumes:
- redis_data:/data
restart: unless-stopped
nginx:
image: nginx:alpine
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf
- ./certs:/etc/nginx/certs
depends_on:
- app
restart: unless-stopped
volumes:
postgres_data:
redis_data:
Kubernetes basics
Deployment
# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-app
labels:
app: web-app
spec:
replicas: 3
selector:
matchLabels:
app: web-app
template:
metadata:
labels:
app: web-app
spec:
containers:
- name: web-app
image: myregistry/web-app:latest
ports:
- containerPort: 3000
resources:
requests:
memory: "256Mi"
cpu: "250m"
limits:
memory: "512Mi"
cpu: "500m"
env:
- name: DATABASE_URL
valueFrom:
secretKeyRef:
name: app-secrets
key: database-url
livenessProbe:
httpGet:
path: /health
port: 3000
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /ready
port: 3000
initialDelaySeconds: 5
periodSeconds: 5
Service and Ingress
# service.yaml
apiVersion: v1
kind: Service
metadata:
name: web-app-service
spec:
selector:
app: web-app
ports:
- port: 80
targetPort: 3000
type: ClusterIP
---
# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: web-app-ingress
annotations:
nginx.ingress.kubernetes.io/ssl-redirect: "true"
spec:
tls:
- hosts:
- example.com
secretName: tls-secret
rules:
- host: example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: web-app-service
port:
number: 80
Useful commands
# Docker
docker build -t myapp .
docker run -p 3000:3000 myapp
docker-compose up -d
docker logs -f container_name
docker exec -it container_name sh
# Kubernetes
kubectl apply -f deployment.yaml
kubectl get pods
kubectl logs -f pod_name
kubectl scale deployment web-app --replicas=5
kubectl rollout restart deployment web-app
Container orchestration
Orchestration is managing many containers. Kubernetes is the industry standard for orchestration in production.
Microservices and deployment
Docker is ideal for microservices — each service in its own container. Deployment through CI/CD pipelines automates delivering code to production.
DevOps practices
DevOps unites development and operations. Infrastructure as Code (IaC) lets you version the cluster configuration.
Scaling in the cloud
Kubernetes provides automatic scaling (HPA). A ConfigMap stores configuration, Secrets store sensitive data. Cloud providers (AWS, GCP, Azure) offer managed Kubernetes.
Related articles
Conclusion
Docker and Kubernetes are the industry standard for deploying applications. Start with Docker for local development, then move to Kubernetes for production.
Containerization solves the “works on my machine” problem once and for all.



