Docker Containers: Fundamentals, Images, Dockerfile & Docker Compose
Docker transformed software development through containerization. It delivers consistent environments from development through production and solves the “works on my machine” problem.
Docker Fundamentals
What is Containerization?
Containerization is an operating system-level virtualization technology that runs applications with all their dependencies in isolated environments.
Docker vs Virtual Machines
# Virtual Machine (VM)
# - Full operating system
# - Hypervisor required
# - High resource consumption
# - Slower startup
# Docker Container
# - Shared OS kernel
# - No hypervisor required
# - Low resource consumption
# - Fast startup
Docker Architecture
# Docker Components
# 1. Docker Daemon (dockerd)
# - Manages containers, images, networks, volumes
# - Runs in the background
# - API endpoint for clients
# 2. Docker Client (docker)
# - Command-line interface
# - Communicates with Docker Daemon
# - User interaction
# 3. Docker Registry
# - Storage for images (Docker Hub)
# - Public and private registries
# 4. Docker Objects
# - Images: Templates for containers
# - Containers: Running instances
# - Networks: Container communication
# - Volumes: Data storage
Docker Installation and Setup
Installation
# Ubuntu/Debian
sudo apt update
sudo apt install docker.io
sudo systemctl start docker
sudo systemctl enable docker
# CentOS/RHEL
sudo yum install docker
sudo systemctl start docker
sudo systemctl enable docker
# Docker Desktop (Windows/Mac)
# Download from https://www.docker.com/products/docker-desktop
# Add user to docker group
sudo usermod -aG docker $USER
newgrp docker
# Verify installation
docker --version
docker info
Core Commands
# Docker version and system information
docker version
docker info
docker system df
# Manage images
docker images
docker pull ubuntu:latest
docker search nginx
docker rmi nginx:latest
# Manage containers
docker ps # Running containers
docker ps -a # All containers
docker run nginx # Start container
docker stop container_id # Stop container
docker rm container_id # Remove container
# Logs and inspection
docker logs container_id
docker inspect container_id
docker exec -it container_id bash
Docker Images
What Are Docker Images?
Docker images are read-only templates used to create containers. They consist of multiple layers.
Image Structure
# Docker Image layer structure
# 1. Base Layer (e.g., Ubuntu)
# 2. Dependencies Layer (e.g., Python)
# 3. Application Layer (e.g., web app)
# 4. Configuration Layer (e.g., environment variables)
# View layers
docker history nginx:latest
# Image information
docker inspect nginx:latest
Dockerfile
A Dockerfile is a text file containing instructions for building a Docker image.
# Dockerfile example for Node.js application
# Base Image
FROM node:16-alpine
# Metadata
LABEL maintainer="max@example.com"
LABEL version="1.0"
LABEL description="Node.js web application"
# Working directory
WORKDIR /app
# Environment variables
ENV NODE_ENV=production
ENV PORT=3000
# Copy files
COPY package*.json ./
RUN npm install --production
# Copy application code
COPY . .
# Create user (security best practice)
RUN addgroup -g 1001 -S nodejs
RUN adduser -S nodejs -u 1001
USER nodejs
# Expose port
EXPOSE 3000
# Health check
HEALTHCHECK --interval=30s --timeout=3s --start-period=5s --retries=3 \
CMD curl -f http://localhost:3000/health || exit 1
# Startup command
CMD ["node", "server.js"]
Dockerfile Best Practices
# Best practices for Dockerfile
# 1. Minimal base image
FROM alpine:latest
# 2. Use specific tags (not latest)
FROM node:16.14.2-alpine
# 3. Use .dockerignore
# .dockerignore
node_modules
npm-debug.log
.git
.gitignore
README.md
.env
# 4. Optimize layer caching
COPY package*.json ./
RUN npm install
COPY . .
# 5. Multi-stage builds
FROM node:16-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm install
COPY . .
RUN npm run build
FROM node:16-alpine AS production
WORKDIR /app
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/node_modules ./node_modules
EXPOSE 3000
CMD ["node", "dist/server.js"]
# 6. Security best practices
USER nonrootuser
RUN rm -rf /var/cache/apk/*
Build and Manage Images
# Build image
docker build -t myapp:1.0 .
docker build -t myapp:latest -f Dockerfile.prod .
# Build with args
docker build --build-arg NODE_ENV=production -t myapp:prod .
# Multi-platform build
docker buildx build --platform linux/amd64,linux/arm64 -t myapp:multi .
# Tag images
docker tag myapp:1.0 myregistry/myapp:1.0
docker tag myapp:latest myregistry/myapp:latest
# Push images
docker login myregistry.com
docker push myregistry/myapp:1.0
docker push myregistry/myapp:latest
# Cleanup images
docker image prune -f
docker image prune -a -f
Docker Containers
Container Lifecycle
# Create and start container
docker run --name mywebserver -d -p 8080:80 nginx
# Container with volumes
docker run --name mydb -v /data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=password mysql:8.0
# Container with network
docker network create mynetwork
docker run --name myapp --network mynetwork -d myapp:latest
# Manage containers
docker start mywebserver
docker stop mywebserver
docker restart mywebserver
docker pause mywebserver
docker unpause mywebserver
# Inspect containers
docker logs mywebserver
docker logs -f mywebserver # Follow logs
docker stats mywebserver # Resource usage
docker exec -it mywebserver bash
Container Configuration
# Resource limits
docker run --memory="512m" --cpus="1.0" myapp:latest
# Environment variables
docker run -e NODE_ENV=production -e PORT=3000 myapp:latest
# Volumes
docker run -v /host/path:/container/path myapp:latest
docker run -v myvolume:/container/path myapp:latest
# Ports
docker run -p 8080:80 -p 8443:443 myapp:latest
# Networks
docker run --network bridge myapp:latest
docker run --network host myapp:latest
docker run --network none myapp:latest
# Restart policies
docker run --restart=always myapp:latest
docker run --restart=on-failure:5 myapp:latest
docker run --restart=unless-stopped myapp:latest
Docker Volumes
# Volume types
# 1. Bind mounts: Host filesystem
docker run -v /host/data:/container/data myapp:latest
# 2. Named volumes: Docker-managed
docker volume create mydata
docker run -v mydata:/container/data myapp:latest
# 3. Anonymous volumes: Auto-created
docker run -v /container/data myapp:latest
# Volume management
docker volume ls
docker volume inspect mydata
docker volume rm mydata
docker volume prune
# Backup and restore
docker run --rm -v mydata:/data -v $(pwd):/backup alpine tar czf /backup/mydata-backup.tar.gz /data
docker run --rm -v mydata:/data -v $(pwd):/backup alpine tar xzf /backup/mydata-backup.tar.gz -C /
Docker Networks
Network Types
# Bridge Network (Standard)
docker network create mybridge
docker run --network mybridge myapp:latest
# Host Network
docker run --network host myapp:latest
# None Network
docker run --network none myapp:latest
# Overlay Network (Multi-Host)
docker network create --driver overlay myoverlay
Network Configuration
# Create a network
docker network create --driver bridge --subnet 192.168.1.0/24 mynetwork
# Run a container on the network
docker run --network mynetwork --ip 192.168.1.10 myapp:latest
# Manage network connections
docker network connect mynetwork mycontainer
docker network disconnect mynetwork mycontainer
# Inspect networks
docker network inspect mynetwork
docker network ls
docker network prune
Docker Compose
Getting Started with Docker Compose
Docker Compose lets you define and manage multi-container applications.
# docker-compose.yml
version: '3.8'
services:
# Web service
web:
build: .
ports:
- "3000:3000"
environment:
- NODE_ENV=production
- DATABASE_URL=postgresql://user:password@db:5432/myapp
depends_on:
- db
- redis
volumes:
- ./logs:/app/logs
restart: unless-stopped
networks:
- app-network
# Database service
db:
image: postgres:13
environment:
- POSTGRES_DB=myapp
- POSTGRES_USER=user
- POSTGRES_PASSWORD=password
volumes:
- postgres_data:/var/lib/postgresql/data
- ./init.sql:/docker-entrypoint-initdb.d/init.sql
restart: unless-stopped
networks:
- app-network
# Redis cache
redis:
image: redis:6-alpine
command: redis-server --appendonly yes
volumes:
- redis_data:/data
restart: unless-stopped
networks:
- app-network
# Nginx reverse proxy
nginx:
image: nginx:alpine
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf
- ./ssl:/etc/nginx/ssl
depends_on:
- web
restart: unless-stopped
networks:
- app-network
# Volumes
volumes:
postgres_data:
redis_data:
# Networks
networks:
app-network:
driver: bridge
Docker Compose Commands
# Start services
docker-compose up
docker-compose up -d # Detached mode
docker-compose up --build # With rebuild
# Stop services
docker-compose down
docker-compose down -v # Including volumes
# View logs
docker-compose logs
docker-compose logs -f web
docker-compose logs --tail=100 web
# Manage services
docker-compose ps
docker-compose restart web
docker-compose stop web
docker-compose start web
# Scale services
docker-compose up -d --scale web=3
# Build images
docker-compose build
docker-compose build --no-cache
docker-compose build web
# Multiple configuration files
docker-compose -f docker-compose.yml -f docker-compose.prod.yml up
Environment-Specific Configuration
# docker-compose.override.yml (Development)
version: '3.8'
services:
web:
environment:
- NODE_ENV=development
volumes:
- .:/app
- /app/node_modules
command: npm run dev
db:
ports:
- "5432:5432"
# docker-compose.prod.yml (Production)
version: '3.8'
services:
web:
environment:
- NODE_ENV=production
deploy:
replicas: 3
resources:
limits:
cpus: '0.5'
memory: 512M
nginx:
ports:
- "80:80"
- "443:443"
Docker Security
Security Best Practices
# 1. Use minimal base images
FROM alpine:latest
# 2. Run as non-root user
RUN addgroup -g 1001 -S appgroup && \
adduser -S appuser -u 1001 -G appgroup
USER appuser
# 3. Use secrets (keep them out of the image)
# docker run --secret=mysecret myapp:latest
# 4. Set the filesystem to read-only
docker run --read-only --tmpfs /tmp myapp:latest
# 5. Apply resource limits
docker run --memory=512m --cpus=1.0 myapp:latest
Docker Security Scanning
# Scan images with Trivy
trivy image myapp:latest
# Docker Scout (official tool)
docker scout cves myapp:latest
# Check your Dockerfile
hadolint Dockerfile
Docker Monitoring and Logging
Logging Strategies
# docker-compose.yml with logging configuration
version: '3.8'
services:
web:
image: myapp:latest
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"
labels:
- "logging=promtail"
# ELK Stack for logging
elasticsearch:
image: docker.elastic.co/elasticsearch/elasticsearch:7.14.0
environment:
- discovery.type=single-node
volumes:
- elasticsearch_data:/usr/share/elasticsearch/data
logstash:
image: docker.elastic.co/logstash/logstash:7.14.0
volumes:
- ./logstash.conf:/usr/share/logstash/pipeline/logstash.conf
kibana:
image: docker.elastic.co/kibana/kibana:7.14.0
ports:
- "5601:5601"
depends_on:
- elasticsearch
Monitoring with Prometheus
# docker-compose.monitoring.yml
version: '3.8'
services:
prometheus:
image: prom/prometheus:latest
ports:
- "9090:9090"
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
- prometheus_data:/prometheus
grafana:
image: grafana/grafana:latest
ports:
- "3000:3000"
environment:
- GF_SECURITY_ADMIN_PASSWORD=admin
volumes:
- grafana_data:/var/lib/grafana
- ./grafana/dashboards:/etc/grafana/provisioning/dashboards
node-exporter:
image: prom/node-exporter:latest
ports:
- "9100:9100"
volumes:
- /proc:/host/proc:ro
- /sys:/host/sys:ro
- /:/rootfs:ro
volumes:
prometheus_data:
grafana_data:
Docker and Kubernetes
Kubernetes Basics
# kubernetes/deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: myapp-deployment
spec:
replicas: 3
selector:
matchLabels:
app: myapp
template:
metadata:
labels:
app: myapp
spec:
containers:
- name: myapp
image: myregistry/myapp:1.0
ports:
- containerPort: 3000
env:
- name: NODE_ENV
value: "production"
resources:
requests:
memory: "256Mi"
cpu: "250m"
limits:
memory: "512Mi"
cpu: "500m"
livenessProbe:
httpGet:
path: /health
port: 3000
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /ready
port: 3000
initialDelaySeconds: 5
periodSeconds: 5
Migrating from Docker to Kubernetes
# Use Kompose to convert files
kompose convert -f docker-compose.yml
# Apply Kubernetes manifests
kubectl apply -f deployment.yaml
kubectl apply -f service.yaml
kubectl apply -f ingress.yaml
# Manage deployments
kubectl get deployments
kubectl get pods
kubectl logs -f deployment/myapp-deployment
kubectl scale deployment myapp-deployment --replicas=5
Docker Best Practices
Performance Optimization
# Multi-stage builds for smaller images
FROM node:16-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci --only=production && npm cache clean --force
COPY . .
RUN npm run build
FROM node:16-alpine AS runtime
WORKDIR /app
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/node_modules ./node_modules
USER node
EXPOSE 3000
CMD ["node", "dist/server.js"]
Production Deployment
# docker-compose.prod.yml
version: '3.8'
services:
web:
image: myregistry/myapp:${VERSION}
deploy:
replicas: 3
update_config:
parallelism: 1
delay: 10s
failure_action: rollback
restart_policy:
condition: on-failure
delay: 5s
max_attempts: 3
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 40s
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"
Troubleshooting
Common Issues
# 1. Container won't start
docker logs container_id
docker inspect container_id
# 2. Disk space full
docker system df
docker system prune -a -f
docker volume prune -f
# 3. Network issues
docker network inspect network_name
docker exec -it container_id ping other_container
# 4. Permission errors
sudo chown -R $USER:$USER /var/run/docker.sock
# 5. Image pull failures
docker system prune -f
docker pull --no-cache image_name
Debugging Techniques
# Inspect container
docker exec -it container_id /bin/sh
docker exec -it container_id /bin/bash
# Copy files
docker cp container_id:/path/file.txt .
docker cp file.txt container_id:/path/
# Analyze image layers
docker history image_name
dive image_name
# Performance analysis
docker stats
docker top container_id
Exam-Relevant Concepts
Essential Docker Commands
| Command | Description | Use Case |
|---|---|---|
docker build | Build an image | From a Dockerfile |
docker run | Start a container | Run an application |
docker-compose up | Start multi-container setup | Development environment |
docker push | Upload an image | Registry upload |
docker pull | Download an image | Registry download |
Typical Exam Tasks
- Create Dockerfiles for various applications
- Configure Docker Compose for multi-container apps
- Implement security best practices
- Optimize Docker images for production
- Migrate applications to Kubernetes
Summary
Docker is fundamental to modern software development:
- Containerization: Consistent environments everywhere
- Images: Reusable templates for applications
- Dockerfile: Automated build processes
- Docker Compose: Define multi-container applications
- Kubernetes: Orchestration for large-scale deployments
Effective Docker management requires understanding container concepts, security practices, and orchestration techniques.
Book Recommendations
Docker is quick to learn and useful for simple deployments, but the platform offers far more capabilities for boosting productivity and security. Invest time in quality resources to unlock the full potential of containers. The recommended books guide you from fundamentals through advanced enterprise solutions, helping you design and operate professional Docker architectures.
Docker: Das Praxisbuch für Entwickler und DevOps-Teams. Grundlagen, Einstieg, Konzepte. Für Windows, macOS und Linux. Ausgabe 2026
44,99 €
Bei Amazon ansehenAffiliate-Link: Bei einem Kauf erhalten wir möglicherweise eine Provision.
Das Komplette Docker Handbuch: Containerisierte Anwendungen Erstellen, Verteilen, Ausführen
39,99 €
Bei Amazon ansehenAffiliate-Link: Bei einem Kauf erhalten wir möglicherweise eine Provision.



