Skip to main content

Docker Compose

Docker Compose nima?

Docker Compose - bu multi-container Docker ilovalarni aniqlash va ishga tushirish uchun tool hisoblanadi. U YAML fayli orqali ilovangizning barcha service'larini konfiguratsiya qilish imkonini beradi.

Docker Compose'ning afzalliklari:

  • Declarative Configuration: YAML orqali infrastructure as code
  • Multi-container Management: Bir buyruq bilan ko'plab containerlarni boshqarish
  • Service Discovery: Container'lar o'rtasida avtomatik networking
  • Environment Management: Turli muhitlar uchun alohida konfiguratsiyalar
  • Development Workflow: Local development'ni soddalashtirish

Docker vs Docker Compose:

DockerDocker Compose
Bitta containerMulti-container
Manual networkingAvtomatik networking
Manual volume managementDeclarative volumes
Complex commandsSimple YAML
Individual containersService orchestration

Docker Compose O'rnatish

Linux'da O'rnatish

# Docker Compose v2 (plugin sifatida)
sudo apt-get update
sudo apt-get install docker-compose-plugin

# Versiyani tekshirish
docker compose version

# Eski standalone versiya (tavsiya etilmaydi)
sudo curl -L "https://github.com/docker/compose/releases/download/v2.24.0/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose

macOS va Windows

Docker Desktop bilan birga keladi, alohida o'rnatish shart emas.

Compose File Syntax

Basic Structure

# docker-compose.yml
version: '3.8' # Compose file format version

services:
web:
# Service configuration
db:
# Service configuration

volumes:
# Named volumes

networks:
# Custom networks

Version Compatibility

# Version 3.8 (tavsiya etiladi)
version: '3.8'

# Version mapping:
# 3.8 - Docker Engine 19.03.0+
# 3.7 - Docker Engine 18.06.0+
# 3.6 - Docker Engine 18.02.0+

Services Configuration

1. Image-based Services

Public Image

services:
redis:
image: redis:7-alpine
ports:
- "6379:6379"

postgres:
image: postgres:15
environment:
POSTGRES_PASSWORD: secret
POSTGRES_DB: myapp
ports:
- "5432:5432"

Private Registry

services:
app:
image: myregistry.com/myapp:latest
# Registry authentication
# docker login myregistry.com

2. Build-based Services

Simple Build

services:
web:
build: . # Current directory'dagi Dockerfile
ports:
- "3000:3000"

Advanced Build

services:
web:
build:
context: . # Build context
dockerfile: Dockerfile.prod # Custom Dockerfile
args: # Build arguments
NODE_VERSION: 18
BUILD_ENV: production
target: production # Multi-stage build target
ports:
- "3000:3000"

Build Options

services:
app:
build:
context: ./app
dockerfile: Dockerfile
cache_from:
- node:18-alpine
shm_size: '2gb'
network: host

3. Environment Variables

Direct Definition

services:
app:
image: node:18
environment:
NODE_ENV: production
API_KEY: abc123
DEBUG: "true"

Environment File

# .env fayl
DATABASE_URL=postgresql://user:pass@db:5432/myapp
REDIS_URL=redis://redis:6379
SECRET_KEY=your-secret-key

# docker-compose.yml
services:
app:
image: myapp:latest
env_file:
- .env
- .env.local

Environment Substitution

# Host environment variable'lardan foydalanish
services:
app:
image: myapp:${VERSION:-latest}
environment:
DATABASE_URL: ${DATABASE_URL}
ports:
- "${APP_PORT:-3000}:3000"

4. Ports va Networking

Port Mapping

services:
web:
image: nginx
ports:
- "80:80" # host:container
- "443:443"
- "127.0.0.1:8080:80" # specific interface
- "3000-3005:3000" # port range

Expose (internal networking)

services:
api:
image: myapi:latest
expose:
- "8000" # Faqat boshqa service'lar uchun

worker:
image: myworker:latest
# api:8000 orqali API'ga murojaat qiladi

5. Volumes

Named Volumes

services:
db:
image: postgres:15
volumes:
- postgres_data:/var/lib/postgresql/data
environment:
POSTGRES_PASSWORD: secret

volumes:
postgres_data:
driver: local

Bind Mounts

services:
web:
image: nginx
volumes:
- ./html:/usr/share/nginx/html:ro # read-only
- ./nginx.conf:/etc/nginx/nginx.conf
- /var/log/nginx:/var/log/nginx

Volume Options

services:
app:
image: myapp:latest
volumes:
- type: bind
source: ./app
target: /app
read_only: true

- type: volume
source: app_data
target: /data
volume:
nocopy: true

- type: tmpfs
target: /tmp
tmpfs:
size: 100M

volumes:
app_data:
driver: local
driver_opts:
type: nfs
o: addr=192.168.1.100,rw
device: ":/path/to/data"

6. Dependencies va Startup Order

depends_on

services:
web:
image: myapp:latest
depends_on:
- db
- redis

db:
image: postgres:15

redis:
image: redis:7-alpine

Healthcheck Dependencies

services:
web:
image: myapp:latest
depends_on:
db:
condition: service_healthy
redis:
condition: service_started

db:
image: postgres:15
healthcheck:
test: ["CMD-SHELL", "pg_isready -U postgres"]
interval: 30s
timeout: 10s
retries: 3
start_period: 60s
environment:
POSTGRES_PASSWORD: secret

7. Restart Policies

services:
web:
image: nginx
restart: always # always, unless-stopped, on-failure, no

worker:
image: myworker:latest
restart: on-failure:3 # 3 marta restart qilish

temp_service:
image: temp:latest
restart: "no" # Restart qilmaslik

8. Resource Limits

services:
app:
image: myapp:latest
deploy:
resources:
limits:
cpus: '2.0'
memory: 1G
reservations:
cpus: '1.0'
memory: 512M
restart_policy:
condition: on-failure
delay: 5s
max_attempts: 3
window: 120s
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 60s

db:
image: postgres:15
restart: always
environment:
POSTGRES_PASSWORD_FILE: /run/secrets/db_password
secrets:
- db_password
volumes:
- postgres_data:/var/lib/postgresql/data
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"

secrets:
db_password:
external: true

volumes:
postgres_data:
driver: local

networks:
default:
driver: bridge
ipam:
config:
- subnet: 172.20.0.0/16

2. CI/CD Integration

GitLab CI Pipeline

# .gitlab-ci.yml
stages:
- build
- test
- deploy

variables:
DOCKER_DRIVER: overlay2
COMPOSE_PROJECT_NAME: myapp

build:
stage: build
script:
- docker compose build
- docker compose push
only:
- main
- develop

test:
stage: test
script:
- docker compose -f docker-compose.yml -f docker-compose.test.yml up -d
- docker compose exec -T web npm test
- docker compose exec -T web npm run e2e
after_script:
- docker compose down -v
only:
- main
- develop

deploy_staging:
stage: deploy
script:
- docker compose -f docker-compose.yml -f docker-compose.staging.yml up -d
environment:
name: staging
url: https://staging.myapp.com
only:
- develop

deploy_production:
stage: deploy
script:
- docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d
environment:
name: production
url: https://myapp.com
when: manual
only:
- main

GitHub Actions

# .github/workflows/deploy.yml
name: Deploy with Docker Compose

on:
push:
branches: [main]
pull_request:
branches: [main]

jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3

- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v2

- name: Run tests
run: |
docker compose -f docker-compose.yml -f docker-compose.test.yml up -d
docker compose exec -T web npm test
docker compose down -v

deploy:
needs: test
runs-on: ubuntu-latest
if: github.ref == 'refs/heads/main'
steps:
- uses: actions/checkout@v3

- name: Deploy to production
env:
HOST: ${{ secrets.PRODUCTION_HOST }}
USER: ${{ secrets.PRODUCTION_USER }}
KEY: ${{ secrets.PRODUCTION_SSH_KEY }}
run: |
echo "$KEY" | ssh-add -
ssh $USER@$HOST "cd /opt/myapp && git pull && docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d"

3. Backup va Recovery

Database Backup

# backup/docker-compose.yml
version: '3.8'

services:
postgres-backup:
image: postgres:15
volumes:
- ./backups:/backups
- postgres_data:/var/lib/postgresql/data:ro
environment:
PGPASSWORD: ${DB_PASSWORD}
command: |
bash -c "
while true; do
pg_dump -h db -U ${DB_USER} -d ${DB_NAME} > /backups/backup_$(date +%Y%m%d_%H%M%S).sql
find /backups -name '*.sql' -mtime +7 -delete
sleep 86400
done
"
depends_on:
- db
restart: always

file-backup:
image: alpine:latest
volumes:
- app_data:/data:ro
- ./backups:/backups
command: |
sh -c "
while true; do
tar -czf /backups/files_$(date +%Y%m%d_%H%M%S).tar.gz -C /data .
find /backups -name 'files_*.tar.gz' -mtime +7 -delete
sleep 86400
done
"
restart: always

volumes:
postgres_data:
external: true
app_data:
external: true

Backup Script

#!/bin/bash
# backup.sh

set -e

PROJECT_NAME="myapp"
BACKUP_DIR="/opt/backups"
DATE=$(date +%Y%m%d_%H%M%S)

# Database backup
docker compose exec -T db pg_dump -U postgres myapp > "${BACKUP_DIR}/db_${DATE}.sql"

# Files backup
docker run --rm \
-v myapp_data:/data:ro \
-v ${BACKUP_DIR}:/backup \
alpine:latest \
tar -czf /backup/files_${DATE}.tar.gz -C /data .

# Volume backup
docker run --rm \
-v myapp_postgres_data:/volume:ro \
-v ${BACKUP_DIR}:/backup \
alpine:latest \
tar -czf /backup/postgres_volume_${DATE}.tar.gz -C /volume .

# Cleanup old backups (keep last 7 days)
find ${BACKUP_DIR} -name "*.sql" -mtime +7 -delete
find ${BACKUP_DIR} -name "*.tar.gz" -mtime +7 -delete

echo "Backup completed: ${DATE}"

Troubleshooting

1. Common Issues

Service Dependencies

# Issue: Service starts before dependencies
# Solution: Use healthcheck conditions

# Muammo
services:
web:
depends_on:
- db # Faqat start order, readiness emas

# Hal qilish
services:
web:
depends_on:
db:
condition: service_healthy

db:
healthcheck:
test: ["CMD-SHELL", "pg_isready"]
interval: 10s
timeout: 5s
retries: 5

Port Conflicts

# Issue: Port already in use
# Error: bind: address already in use

# Tekshirish
sudo netstat -tlnp | grep :80
lsof -i :80

# Hal qilish
# 1. Boshqa port ishlatish
ports:
- "8080:80"

# 2. Service'ni to'xtatish
sudo systemctl stop apache2

Volume Permissions

# Issue: Permission denied in volumes
# Hal qilish

# 1. User mapping
services:
app:
user: "${UID}:${GID}"

# 2. Init container
services:
init:
image: alpine:latest
volumes:
- app_data:/data
command: chown -R 1000:1000 /data

app:
depends_on:
- init
user: "1000:1000"

2. Debugging Commands

Service Investigation

# Service logs batafsil
docker compose logs --details web

# Container ichidagi environment
docker compose exec web env

# Container ichidagi jarayonlar
docker compose exec web ps aux

# Network connectivity test
docker compose exec web ping db
docker compose exec web telnet db 5432

# DNS resolution
docker compose exec web nslookup db

Configuration Debugging

# Configuration validation
docker compose config

# Resolved configuration ko'rish
docker compose config --resolve-envs

# Service definitions
docker compose config --services

# Environment variables
docker compose config --variables

# Debug mode
COMPOSE_LOG_LEVEL=DEBUG docker compose up

3. Performance Issues

Resource Monitoring

# Container resource usage
docker compose exec web cat /proc/meminfo
docker compose exec web cat /proc/cpuinfo

# Docker stats
docker stats $(docker compose ps -q)

# Disk usage
docker compose exec web df -h
docker system df

Network Debugging

# Network inspection
docker network ls
docker network inspect myapp_default

# Port mapping tekshirish
docker compose port web 80

# Traffic monitoring
docker compose exec web tcpdump -i eth0

Advanced Features

1. Profiles

# docker-compose.yml with profiles
version: '3.8'

services:
web:
image: myapp:latest
profiles: ["web"]

api:
image: myapi:latest
profiles: ["api"]

worker:
image: myworker:latest
profiles: ["worker"]

db:
image: postgres:15
# Har doim ishga tushadi

monitoring:
image: grafana/grafana
profiles: ["monitoring", "dev"]

# Usage:
# docker compose --profile web up # Faqat web va db
# docker compose --profile api up # Faqat api va db
# docker compose --profile dev up # web, api, worker, db, monitoring

2. Extensions

Compose Extensions

# docker-compose.yml
version: '3.8'

# Extension fields (reusable configurations)
x-common-variables: &common-variables
NODE_ENV: production
LOG_LEVEL: info

x-restart-policy: &restart-policy
restart: always

x-logging: &logging
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"

services:
web:
image: myapp:latest
environment:
<<: *common-variables
PORT: 3000
<<: *restart-policy
<<: *logging

api:
image: myapi:latest
environment:
<<: *common-variables
PORT: 8000
<<: *restart-policy
<<: *logging

3. Service Mesh Integration

Traefik Integration

# docker-compose.yml with Traefik
version: '3.8'

services:
traefik:
image: traefik:v2.10
command:
- "--api.insecure=true"
- "--providers.docker=true"
- "--providers.docker.exposedbydefault=false"
- "--entrypoints.web.address=:80"
- "--entrypoints.websecure.address=:443"
- "--certificatesresolvers.myresolver.acme.tlschallenge=true"
- "--certificatesresolvers.myresolver.acme.email=admin@example.com"
- "--certificatesresolvers.myresolver.acme.storage=/letsencrypt/acme.json"
ports:
- "80:80"
- "443:443"
- "8080:8080"
volumes:
- /var/run/docker.sock:/var/run/docker.sock:ro
- letsencrypt:/letsencrypt
networks:
- web

web:
image: myapp:latest
labels:
- "traefik.enable=true"
- "traefik.http.routers.web.rule=Host(`myapp.com`)"
- "traefik.http.routers.web.entrypoints=websecure"
- "traefik.http.routers.web.tls.certresolver=myresolver"
- "traefik.http.services.web.loadbalancer.server.port=3000"
networks:
- web

volumes:
letsencrypt:

networks:
web:
external: true

Docker Compose Best Practices

1. File Organization

# Recommended project structure
project/
├── docker-compose.yml # Base configuration
├── docker-compose.override.yml # Local development overrides
├── docker-compose.prod.yml # Production configuration
├── docker-compose.test.yml # Test configuration
├── .env # Environment variables
├── .env.example # Environment template
├── .dockerignore # Docker ignore file
├── Dockerfile # Application Dockerfile
├── docker/ # Docker-related files
│ ├── nginx/
│ │ └── nginx.conf
│ ├── postgres/
│ │ └── init.sql
│ └── scripts/
│ ├── backup.sh
│ └── restore.sh
└── README.md # Project documentation

2. Environment Variables

# Good practices for environment variables
services:
app:
image: myapp:latest
environment:
# Required variables (with defaults)
NODE_ENV: ${NODE_ENV:-development}
PORT: ${PORT:-3000}

# Database configuration
DB_HOST: ${DB_HOST:-db}
DB_PORT: ${DB_PORT:-5432}
DB_NAME: ${DB_NAME:?err} # Required variable
DB_USER: ${DB_USER:?err}

# Optional features
ENABLE_METRICS: ${ENABLE_METRICS:-false}
REDIS_URL: ${REDIS_URL:-redis://redis:6379}

3. Security Practices

# Security-focused configuration
version: '3.8'

services:
app:
image: myapp:latest

# Security configurations
user: "1000:1000" # Non-root user
read_only: true # Read-only filesystem

# Minimal capabilities
cap_drop:
- ALL
cap_add:
- NET_BIND_SERVICE

# Security options
security_opt:
- no-new-privileges:true
- apparmor:docker-default

# Tmpfs for writable directories
tmpfs:
- /tmp:noexec,nosuid,size=100m
- /var/run:noexec,nosuid,size=50m

# Resource limits
deploy:
resources:
limits:
cpus: '1.0'
memory: 512M
reservations:
cpus: '0.5'
memory: 256M

# Health monitoring
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 60s

# Database with security
db:
image: postgres:15

# Secrets instead of environment variables
secrets:
- postgres_password
environment:
POSTGRES_PASSWORD_FILE: /run/secrets/postgres_password
POSTGRES_USER: appuser
POSTGRES_DB: appdb

# Isolated network
networks:
- backend

# No external access
# ports: [] # Don't expose ports externally

secrets:
postgres_password:
file: ./secrets/postgres_password.txt

networks:
backend:
driver: bridge
internal: true # No internet access

4. Performance Optimization

# Performance-optimized configuration
version: '3.8'

services:
app:
image: myapp:latest

# Optimized resource allocation
deploy:
resources:
limits:
cpus: '2.0'
memory: 1G
reservations:
cpus: '1.0'
memory: 512M

# Sysctls for performance
sysctls:
net.core.somaxconn: 65536
net.ipv4.tcp_max_syn_backlog: 65536

# Ulimits
ulimits:
nproc: 65535
nofile:
soft: 65535
hard: 65535

# Volume optimizations
volumes:
- type: tmpfs
target: /tmp
tmpfs:
size: 512M

- type: volume
source: app_cache
target: /app/cache
volume:
nocopy: true

volumes:
app_cache:
driver: local
driver_opts:
type: tmpfs
device: tmpfs

5. Monitoring Integration

# Comprehensive monitoring setup
version: '3.8'

services:
app:
image: myapp:latest
labels:
# Prometheus metrics
- "prometheus.io/scrape=true"
- "prometheus.io/port=3000"
- "prometheus.io/path=/metrics"

# Logging labels
- "logging.driver=fluentd"
- "logging.fluentd.address=localhost:24224"
- "logging.fluentd.tag=app.{{.Name}}"

# Health check
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
interval: 10s
timeout: 5s
retries: 3
start_period: 30s

# Logging configuration
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"
labels: "service,version"

# Environment for monitoring
environment:
METRICS_ENABLED: "true"
LOG_LEVEL: "info"
TRACE_ENABLED: "true"

# Monitoring stack
prometheus:
image: prom/prometheus:latest
ports:
- "9090:9090"
volumes:
- ./monitoring/prometheus.yml:/etc/prometheus/prometheus.yml:ro
- prometheus_data:/prometheus
command:
- '--config.file=/etc/prometheus/prometheus.yml'
- '--storage.tsdb.path=/prometheus'
- '--web.console.libraries=/etc/prometheus/console_libraries'
- '--web.console.templates=/etc/prometheus/consoles'
- '--storage.tsdb.retention.time=15d'

grafana:
image: grafana/grafana:latest
ports:
- "3001:3000"
environment:
GF_SECURITY_ADMIN_PASSWORD: ${GRAFANA_PASSWORD}
GF_INSTALL_PLUGINS: grafana-piechart-panel
volumes:
- grafana_data:/var/lib/grafana
- ./monitoring/grafana/dashboards:/etc/grafana/provisioning/dashboards:ro
- ./monitoring/grafana/datasources:/etc/grafana/provisioning/datasources:ro

volumes:
prometheus_data:
grafana_data:

Docker Compose bilan ishlaganda bu best practice'larni qo'llash orqali scalable, secure va maintainable applications yaratish mumkin. DevOps engineer sifatida bu bilimlar sizga production-ready containerized solutions yaratishda yordam beradi! memory: 1G reservations: cpus: '0.5' memory: 512M

Legacy format (deprecated)

mem_limit: 1g cpus: 2.0 mem_reservation: 512m


## Networks

### 1. Default Network
```yaml
# Avtomatik yaratiladi: projectname_default
services:
web:
image: nginx

api:
image: myapi:latest
# web va api bir xil networkda

2. Custom Networks

Bridge Network

services:
web:
image: nginx
networks:
- frontend

api:
image: myapi:latest
networks:
- frontend
- backend

db:
image: postgres:15
networks:
- backend

networks:
frontend:
driver: bridge
backend:
driver: bridge
internal: true # Internet'ga chiqish yo'q

Network Aliases

services:
web:
image: nginx
networks:
frontend:
aliases:
- webserver
- www

networks:
frontend:
driver: bridge

3. External Networks

services:
app:
image: myapp:latest
networks:
- existing_network

networks:
existing_network:
external: true
name: my_external_network

Amaliy Misollar

1. LAMP Stack

# LAMP Stack (Linux, Apache, MySQL, PHP)
version: '3.8'

services:
web:
image: php:8.1-apache
ports:
- "80:80"
volumes:
- ./src:/var/www/html
depends_on:
- db
environment:
- APACHE_DOCUMENT_ROOT=/var/www/html
networks:
- lamp

db:
image: mysql:8.0
environment:
MYSQL_ROOT_PASSWORD: rootpassword
MYSQL_DATABASE: myapp
MYSQL_USER: appuser
MYSQL_PASSWORD: apppassword
volumes:
- mysql_data:/var/lib/mysql
networks:
- lamp

phpmyadmin:
image: phpmyadmin:latest
ports:
- "8080:80"
environment:
PMA_HOST: db
PMA_USER: root
PMA_PASSWORD: rootpassword
depends_on:
- db
networks:
- lamp

volumes:
mysql_data:

networks:
lamp:
driver: bridge

2. MEAN Stack

# MEAN Stack (MongoDB, Express, Angular, Node.js)
version: '3.8'

services:
frontend:
build:
context: ./frontend
dockerfile: Dockerfile
ports:
- "4200:4200"
volumes:
- ./frontend:/app
- /app/node_modules
depends_on:
- backend
networks:
- mean

backend:
build:
context: ./backend
dockerfile: Dockerfile
ports:
- "3000:3000"
volumes:
- ./backend:/app
- /app/node_modules
environment:
NODE_ENV: development
MONGODB_URI: mongodb://mongo:27017/meanapp
depends_on:
- mongo
networks:
- mean

mongo:
image: mongo:6
ports:
- "27017:27017"
environment:
MONGO_INITDB_ROOT_USERNAME: admin
MONGO_INITDB_ROOT_PASSWORD: password
MONGO_INITDB_DATABASE: meanapp
volumes:
- mongo_data:/data/db
- ./init-mongo.js:/docker-entrypoint-initdb.d/init-mongo.js:ro
networks:
- mean

mongo-express:
image: mongo-express:latest
ports:
- "8081:8081"
environment:
ME_CONFIG_MONGODB_ADMINUSERNAME: admin
ME_CONFIG_MONGODB_ADMINPASSWORD: password
ME_CONFIG_MONGODB_SERVER: mongo
ME_CONFIG_BASICAUTH_USERNAME: admin
ME_CONFIG_BASICAUTH_PASSWORD: admin
depends_on:
- mongo
networks:
- mean

volumes:
mongo_data:

networks:
mean:
driver: bridge

3. WordPress Stack

# WordPress with MySQL and Redis
version: '3.8'

services:
wordpress:
image: wordpress:6-php8.1-apache
ports:
- "80:80"
environment:
WORDPRESS_DB_HOST: db
WORDPRESS_DB_USER: wordpress
WORDPRESS_DB_PASSWORD: wordpress
WORDPRESS_DB_NAME: wordpress
WORDPRESS_CONFIG_EXTRA: |
define('WP_REDIS_HOST', 'redis');
define('WP_REDIS_PORT', 6379);
volumes:
- wordpress_data:/var/www/html
- ./uploads.ini:/usr/local/etc/php/conf.d/uploads.ini
depends_on:
- db
- redis
networks:
- wordpress

db:
image: mysql:8.0
environment:
MYSQL_DATABASE: wordpress
MYSQL_USER: wordpress
MYSQL_PASSWORD: wordpress
MYSQL_ROOT_PASSWORD: rootpassword
volumes:
- db_data:/var/lib/mysql
command: '--default-authentication-plugin=mysql_native_password'
networks:
- wordpress

redis:
image: redis:7-alpine
command: redis-server --appendonly yes
volumes:
- redis_data:/data
networks:
- wordpress

phpmyadmin:
image: phpmyadmin:latest
ports:
- "8080:80"
environment:
PMA_HOST: db
PMA_USER: root
PMA_PASSWORD: rootpassword
depends_on:
- db
networks:
- wordpress

volumes:
wordpress_data:
db_data:
redis_data:

networks:
wordpress:
driver: bridge

4. Microservices Architecture

# E-commerce microservices
version: '3.8'

services:
# API Gateway
gateway:
image: nginx:alpine
ports:
- "80:80"
- "443:443"
volumes:
- ./nginx/nginx.conf:/etc/nginx/nginx.conf
- ./nginx/ssl:/etc/nginx/ssl
depends_on:
- user-service
- product-service
- order-service
networks:
- frontend
- backend

# User Service
user-service:
build: ./services/user
environment:
DATABASE_URL: postgresql://user:pass@user-db:5432/users
REDIS_URL: redis://redis:6379
JWT_SECRET: your-jwt-secret
depends_on:
- user-db
- redis
networks:
- backend
deploy:
replicas: 2

user-db:
image: postgres:15
environment:
POSTGRES_DB: users
POSTGRES_USER: user
POSTGRES_PASSWORD: pass
volumes:
- user_db_data:/var/lib/postgresql/data
networks:
- backend

# Product Service
product-service:
build: ./services/product
environment:
DATABASE_URL: postgresql://product:pass@product-db:5432/products
ELASTICSEARCH_URL: http://elasticsearch:9200
depends_on:
- product-db
- elasticsearch
networks:
- backend

product-db:
image: postgres:15
environment:
POSTGRES_DB: products
POSTGRES_USER: product
POSTGRES_PASSWORD: pass
volumes:
- product_db_data:/var/lib/postgresql/data
networks:
- backend

# Order Service
order-service:
build: ./services/order
environment:
DATABASE_URL: mongodb://mongo:27017/orders
RABBITMQ_URL: amqp://rabbitmq:5672
depends_on:
- mongo
- rabbitmq
networks:
- backend

# Shared Services
redis:
image: redis:7-alpine
volumes:
- redis_data:/data
networks:
- backend

mongo:
image: mongo:6
volumes:
- mongo_data:/data/db
networks:
- backend

rabbitmq:
image: rabbitmq:3-management
ports:
- "15672:15672" # Management UI
environment:
RABBITMQ_DEFAULT_USER: admin
RABBITMQ_DEFAULT_PASS: admin
volumes:
- rabbitmq_data:/var/lib/rabbitmq
networks:
- backend

elasticsearch:
image: elasticsearch:8.11.0
environment:
- discovery.type=single-node
- "ES_JAVA_OPTS=-Xms512m -Xmx512m"
- xpack.security.enabled=false
volumes:
- elasticsearch_data:/usr/share/elasticsearch/data
networks:
- backend

# Monitoring
prometheus:
image: prom/prometheus
ports:
- "9090:9090"
volumes:
- ./prometheus/prometheus.yml:/etc/prometheus/prometheus.yml
- prometheus_data:/prometheus
networks:
- monitoring

grafana:
image: grafana/grafana
ports:
- "3000:3000"
environment:
GF_SECURITY_ADMIN_PASSWORD: admin
volumes:
- grafana_data:/var/lib/grafana
networks:
- monitoring

volumes:
user_db_data:
product_db_data:
redis_data:
mongo_data:
rabbitmq_data:
elasticsearch_data:
prometheus_data:
grafana_data:

networks:
frontend:
driver: bridge
backend:
driver: bridge
internal: true
monitoring:
driver: bridge

Docker Compose Commands

1. Basic Commands

Lifecycle Management

# Service'larni ishga tushirish
docker compose up

# Background'da ishga tushirish
docker compose up -d

# Ma'lum service'larni ishga tushirish
docker compose up web db

# Service'larni to'xtatish
docker compose down

# Volume'lar bilan birga o'chirish
docker compose down -v

# Image'lar bilan birga o'chirish
docker compose down --rmi all

Build Commands

# Service'larni build qilish
docker compose build

# Cache'siz build qilish
docker compose build --no-cache

# Ma'lum service'ni build qilish
docker compose build web

# Build va up bir vaqtda
docker compose up --build

2. Service Management

Scaling Services

# Service'ni scale qilish
docker compose up --scale web=3

# Multiple service'larni scale qilish
docker compose up --scale web=3 --scale worker=2

# Dynamic scaling
docker compose scale web=5

Service Status

# Ishlaydigan service'lar
docker compose ps

# Barcha service'lar (to'xtagan ham)
docker compose ps -a

# Service'lar haqida batafsil ma'lumot
docker compose ps --services

# Status format
docker compose ps --format json

3. Logs va Debugging

Log Management

# Barcha service'lar log'lari
docker compose logs

# Ma'lum service log'lari
docker compose logs web

# Real-time logs
docker compose logs -f

# Oxirgi N ta log entry
docker compose logs --tail 100

# Timestamp bilan
docker compose logs -t

# Multiple service'lar
docker compose logs web db

Exec va Debug

# Service'ga kirish
docker compose exec web bash

# Command ishga tushirish
docker compose exec web ls -la

# Root user sifatida
docker compose exec --user root web bash

# Index bilan (scaled service'lar uchun)
docker compose exec --index 2 web bash

4. Advanced Commands

Configuration Commands

# Configuration'ni ko'rish
docker compose config

# Environment variables bilan
docker compose config --resolve-envs

# Service'lar ro'yxati
docker compose config --services

# Volume'lar ro'yxati
docker compose config --volumes

# Validate qilish
docker compose config --quiet

Cleanup Commands

# To'xtagan container'larni o'chirish
docker compose rm

# Force remove
docker compose rm -f

# Orphan container'larni o'chirish
docker compose down --remove-orphans

# Volume'larni tozalash
docker compose down -v

Multiple Environment Management

1. Environment-specific Files

File Structure

# Project structure
project/
├── docker-compose.yml # Base configuration
├── docker-compose.dev.yml # Development overrides
├── docker-compose.prod.yml # Production overrides
├── docker-compose.test.yml # Test environment
├── .env # Default environment
├── .env.dev # Development environment
├── .env.prod # Production environment
└── .env.test # Test environment

Base Configuration

# docker-compose.yml
version: '3.8'

services:
web:
build: .
environment:
NODE_ENV: ${NODE_ENV:-development}
volumes:
- ./src:/app/src

db:
image: postgres:15
environment:
POSTGRES_DB: ${DB_NAME}
POSTGRES_USER: ${DB_USER}
POSTGRES_PASSWORD: ${DB_PASSWORD}

Development Override

# docker-compose.dev.yml
version: '3.8'

services:
web:
ports:
- "3000:3000"
volumes:
- ./src:/app/src:ro
- /app/node_modules
command: npm run dev
environment:
NODE_ENV: development
DEBUG: "app:*"

db:
ports:
- "5432:5432"
volumes:
- postgres_dev_data:/var/lib/postgresql/data

volumes:
postgres_dev_data:

Production Override

# docker-compose.prod.yml
version: '3.8'

services:
web:
restart: always
command: npm start
environment:
NODE_ENV: production
deploy:
resources:
limits:
cpus: '1.0'
memory: 512M
reservations:
cpus: '0.5'
memory: 256M

db:
restart: always
volumes:
- postgres_prod_data:/var/lib/postgresql/data
deploy:
resources:
limits:
cpus: '2.0'
memory: 2G
reservations:
cpus: '1.0'
memory: 1G

volumes:
postgres_prod_data:
driver: local
driver_opts:
type: nfs
o: addr=nfs-server,rw
device: ":/path/to/data"

2. Environment Usage

Development

# Development environment
docker compose -f docker-compose.yml -f docker-compose.dev.yml up

# With environment file
docker compose --env-file .env.dev -f docker-compose.yml -f docker-compose.dev.yml up

Production

# Production environment
docker compose -f docker-compose.yml -f docker-compose.prod.yml up -d

# With specific environment
export NODE_ENV=production
docker compose --env-file .env.prod -f docker-compose.yml -f docker-compose.prod.yml up -d

Testing

# Test environment
docker compose -f docker-compose.yml -f docker-compose.test.yml run --rm web npm test

3. Environment Variables

.env Files

# .env.dev
NODE_ENV=development
DB_NAME=myapp_dev
DB_USER=dev_user
DB_PASSWORD=dev_password
API_URL=http://localhost:3000
DEBUG=true

# .env.prod
NODE_ENV=production
DB_NAME=myapp_prod
DB_USER=prod_user
DB_PASSWORD=super_secure_password
API_URL=https://api.myapp.com
DEBUG=false

# .env.test
NODE_ENV=test
DB_NAME=myapp_test
DB_USER=test_user
DB_PASSWORD=test_password
API_URL=http://localhost:3001
DEBUG=false

Performance Optimization

1. Build Optimization

Build Context

services:
web:
build:
context: .
dockerfile: Dockerfile
args:
NODE_ENV: production
# .dockerignore file'ni ishlatish muhim

Multi-stage Builds

services:
web:
build:
context: .
target: production
cache_from:
- myapp:builder
- myapp:latest

2. Resource Management

Memory va CPU Limits

services:
web:
image: myapp:latest
deploy:
resources:
limits:
cpus: '2.0'
memory: 1G
reservations:
cpus: '0.5'
memory: 512M
sysctls:
- net.core.somaxconn=1024
ulimits:
nproc: 65535
nofile:
soft: 65535
hard: 65535

3. Volume Optimization

Bind Mount vs Named Volume

services:
web:
image: myapp:latest
volumes:
# Development: bind mount (fast development)
- type: bind
source: ./src
target: /app/src
consistency: delegated # macOS uchun

# Production: named volume (better performance)
- type: volume
source: app_data
target: /app/data

volumes:
app_data:
driver: local
driver_opts:
type: none
device: /opt/myapp/data
o: bind

Monitoring va Debugging

1. Health Checks

services:
web:
image: myapp:latest
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:3000/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 60s
depends_on:
db:
condition: service_healthy

db:
image: postgres:15
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB}"]
interval: 10s
timeout: 5s
retries: 5

2. Monitoring Stack

# monitoring/docker-compose.yml
version: '3.8'

services:
prometheus:
image: prom/prometheus:latest
ports:
- "9090:9090"
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
- prometheus_data:/prometheus
command:
- '--config.file=/etc/prometheus/prometheus.yml'
- '--storage.tsdb.path=/prometheus'
- '--web.console.libraries=/etc/prometheus/console_libraries'
- '--web.console.templates=/etc/prometheus/consoles'

grafana:
image: grafana/grafana:latest
ports:
- "3000:3000"
environment:
GF_SECURITY_ADMIN_PASSWORD: admin
volumes:
- grafana_data:/var/lib/grafana

cadvisor:
image: gcr.io/cadvisor/cadvisor:latest
ports:
- "8080:8080"
volumes:
- /:/rootfs:ro
- /var/run:/var/run:rw
- /sys:/sys:ro
- /var/lib/docker/:/var/lib/docker:ro

volumes:
prometheus_data:
grafana_data:

3. Debugging Tools

Container Inspection

# Container ichidagi jarayonlar
docker compose top

# Resource usage
docker compose exec web htop

# Network connectivity
docker compose exec web ping db

# Port listening
docker compose exec web netstat -tlnp

Security Best Practices

1. Secrets Management

Docker Secrets

# secrets.yml
version: '3.8'

services:
app:
image: myapp:latest
secrets:
- db_password
- api_key
environment:
DB_PASSWORD_FILE: /run/secrets/db_password
API_KEY_FILE: /run/secrets/api_key

secrets:
db_password:
file: ./secrets/db_password.txt
api_key:
external: true # Docker secret'dan

Environment Files Security

# .env fayllarini .gitignore'ga qo'shish
echo ".env*" >> .gitignore

# .env.example yaratish
cp .env .env.example
# Sensitive ma'lumotlarni olib tashlab commit qilish

2. Network Security

services:
web:
image: nginx
networks:
- frontend
# Faqat frontend network'ga kirish

api:
image: myapi:latest
networks:
- frontend
- backend
# Frontend va backend'ga kirish

db:
image: postgres:15
networks:
- backend
# Faqat backend network, external access yo'q

networks:
frontend:
driver: bridge
backend:
driver: bridge
internal: true # Internet'ga chiqish yo'q

3. User Security

services:
app:
image: myapp:latest
user: "1000:1000" # Non-root user
read_only: true # Read-only file system
tmpfs:
- /tmp
- /var/run
cap_drop:
- ALL
cap_add:
- NET_BIND_SERVICE
security_opt:
- no-new-privileges:true

Production Deployment

1. Production Configuration

# docker-compose.prod.yml
version: '3.8'

services:
web:
image: myapp:${VERSION}
restart: always
logging:
driver: "json-file"
options:
max-size: "10m"
max-file: "3"
deploy:
resources:
limits:
cpus: '2.0'