Как настроить docker-compose для разработки и продакшна по-разному?
Подробный ответ
Почему конфигурации различаются
Разработка требует быстрого feedback loop: bind mounts, hot reload, debug-порты и локальные инструменты. Production требует воспроизводимости, минимального runtime-образа, безопасных секретов, ограниченных портов, мониторинга и запуска готового image из registry.
Базовый compose.yaml
services:
web:
image: ${IMAGE_REF:-my-app:local}
env_file:
- .env
depends_on:
db:
condition: service_healthy
db:
image: postgres:16
environment:
POSTGRES_DB: app_db
POSTGRES_USER: app
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
volumes:
- postgres_data:/var/lib/postgresql/data
healthcheck:
test: ["CMD-SHELL", "pg_isready -U app -d app_db"]
interval: 10s
timeout: 5s
retries: 5
volumes:
postgres_data:compose.dev.yaml
services:
web:
build:
context: .
target: development
command: uvicorn app.main:app --host 0.0.0.0 --port 8000 --reload
volumes:
- .:/app
ports:
- "8000:8000"
environment:
APP_ENV: development
DEBUG: "true"
db:
ports:
- "5432:5432"compose.prod.yaml
services:
web:
image: ${IMAGE_REF}
restart: unless-stopped
environment:
APP_ENV: production
DEBUG: "false"
ports:
- "127.0.0.1:8000:8000"
read_only: true
tmpfs:
- /tmpЗапуск с несколькими файлами
docker compose -f compose.yaml -f compose.dev.yaml up --build
docker compose -f compose.yaml -f compose.prod.yaml up -dВажные отличия production
не использовать bind mount исходного кода;
не собирать image прямо на production-сервере;
не включать debug-режим и не открывать внутренние порты наружу;
не хранить секреты в коммитящемся env-файле;
использовать конкретный version tag или digest вместо неопределённого latest.
Как ответить на собеседовании
Я держу общую базовую Compose-конфигурацию и отдельные файлы для development и production. В dev подключаю исходный код через bind mount и включаю hot reload, а в production запускаю готовый image из registry с конкретным тегом, без bind mounts и debug-портов, с безопасными secrets и restart policy.
Оцени свой прогресс