← Назад к вопросам

В чем разница между Docker и Docker Compose?

2.0 Middle🔥 181 комментариев
#Docker, Kubernetes и DevOps

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Разница между Docker и Docker Compose

Это два взаимосвязанные инструмента для контейнеризации, но они решают разные задачи. Docker — это основной инструмент для создания и запуска контейнеров, а Docker Compose — это оркестрация нескольких контейнеров.

Краткое объяснение

  • Docker — инструмент для создания и запуска ОДНОГО контейнера
  • Docker Compose — инструмент для управления НЕСКОЛЬКИМИ взаимосвязанными контейнерами

Docker: Основы

# Docker работает с отдельными контейнерами
# Создание образа из Dockerfile
docker build -t my-app:1.0 .

# Запуск контейнера
docker run -d -p 8080:8080 my-app:1.0

# Запуск второго контейнера (database)
docker run -d -p 5432:5432 -e POSTGRES_PASSWORD=pass postgres:14

# Проверка запущенных контейнеров
docker ps

# Остановка контейнера
docker stop container_id

# Удаление контейнера
docker rm container_id

Проблемы при запуске нескольких контейнеров через Docker:

  • Нужно помнить множество команд
  • Нужно вручную устанавливать сетевые связи
  • Нужно управлять переменными окружения
  • Сложно масштабировать
  • Невозможно гарантировать порядок запуска

Docker Compose: Решение

Один файл (docker-compose.yml) для управления всеми контейнерами:

version: '3.8'

services:
  # Сервис 1: Java приложение
  app:
    build:
      context: .
      dockerfile: Dockerfile
    container_name: my-app
    ports:
      - "8080:8080"
    environment:
      - SPRING_DATASOURCE_URL=jdbc:postgresql://postgres:5432/mydb
      - SPRING_DATASOURCE_USERNAME=user
      - SPRING_DATASOURCE_PASSWORD=password
    depends_on:
      - postgres
    networks:
      - app-network
    restart: always

  # Сервис 2: PostgreSQL база данных
  postgres:
    image: postgres:14
    container_name: postgres-db
    environment:
      - POSTGRES_DB=mydb
      - POSTGRES_USER=user
      - POSTGRES_PASSWORD=password
    ports:
      - "5432:5432"
    volumes:
      - postgres-data:/var/lib/postgresql/data
    networks:
      - app-network
    restart: always

  # Сервис 3: Redis кеш
  redis:
    image: redis:7
    container_name: redis-cache
    ports:
      - "6379:6379"
    networks:
      - app-network
    restart: always

volumes:
  postgres-data:

networks:
  app-network:
    driver: bridge

Команды Docker Compose:

# Запуск всех контейнеров
docker compose up -d

# Просмотр логов
docker compose logs -f app

# Остановка всех контейнеров
docker compose down

# Перестроение образов
docker compose up -d --build

# Просмотр статуса
docker compose ps

# Выполнение команды в контейнере
docker compose exec app bash

# Удаление всего (контейнеры, сети, volumes)
docker compose down -v

Таблица сравнения

ПараметрDockerDocker Compose
Для чегоОдин контейнерНесколько контейнеров
КонфигурацияКомандная строка или Dockerfiledocker-compose.yml файл
СложностьПростая для одного контейнераУдобнее для многих контейнеров
Сетевая связьРучная настройкаАвтоматическая
Порядок запускаРучной контрольdepends_on
Переменные окружения-e флаги.env файл или environment
МасштабированиеСложноВстроенная поддержка
Production❌ Нет❌ Нет (используй Kubernetes)
Development✅ Да✅ Да (лучше)
CI/CD✅ Да✅ Да

Практический пример: Java приложение с базой данных

Вариант 1: Docker (ручная работа)

# Создаём образ приложения
docker build -t java-app:1.0 .

# Запускаем PostgreSQL
docker run -d --name postgres-db \
  -e POSTGRES_DB=myapp \
  -e POSTGRES_USER=user \
  -e POSTGRES_PASSWORD=pass \
  -p 5432:5432 \
  postgres:14

# Ждём пока БД запустится... (нет гарантии!)

# Запускаем приложение
docker run -d --name java-app \
  -e SPRING_DATASOURCE_URL=jdbc:postgresql://postgres-db:5432/myapp \
  -e SPRING_DATASOURCE_USERNAME=user \
  -e SPRING_DATASOURCE_PASSWORD=pass \
  --link postgres-db \
  -p 8080:8080 \
  java-app:1.0

# Проверяем логи
docker logs -f java-app

# Останавливаем всё
docker stop java-app postgres-db
docker rm java-app postgres-db

Проблемы:

  • Много команд
  • Нужно помнить все флаги
  • Нет гарантии порядка запуска
  • Сложно воспроизвести в разных окружениях

Вариант 2: Docker Compose (один файл)

version: '3.8'

services:
  app:
    build: .
    container_name: java-app
    ports:
      - "8080:8080"
    environment:
      SPRING_DATASOURCE_URL: jdbc:postgresql://postgres:5432/myapp
      SPRING_DATASOURCE_USERNAME: user
      SPRING_DATASOURCE_PASSWORD: pass
    depends_on:
      postgres:
        condition: service_healthy
    networks:
      - app-network

  postgres:
    image: postgres:14
    container_name: postgres-db
    environment:
      POSTGRES_DB: myapp
      POSTGRES_USER: user
      POSTGRES_PASSWORD: pass
    ports:
      - "5432:5432"
    volumes:
      - postgres-data:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U user"]
      interval: 10s
      timeout: 5s
      retries: 5
    networks:
      - app-network

volumes:
  postgres-data:

networks:
  app-network:
    driver: bridge
# Всё просто!
docker compose up -d

# Проверка
docker compose ps

# Логи
docker compose logs -f app

# Остановка
docker compose down

Преимущества:

  • Один файл
  • Readable
  • Воспроизводимо
  • Автоматический порядок запуска (depends_on)
  • Встроенная сетевая связь
  • Легко масштабировать

Важные особенности Docker Compose

1. Автоматическая сетевая связь

services:
  app:
    # Может обращаться к postgres как http://postgres:5432
    environment:
      DB_HOST: postgres
  postgres:
    # Для app доступен как postgres:5432

2. depends_on (контроль порядка)

services:
  app:
    depends_on:
      postgres:
        condition: service_healthy  # Ждёт healthcheck
      redis:
        condition: service_started   # Ждёт только запуска

3. Переменные окружения

# docker-compose.yml
services:
  app:
    environment:
      - LOG_LEVEL=INFO
      - SPRING_PROFILES_ACTIVE=prod
# Или из .env файла
docker compose --env-file .env.prod up

4. Volumes (сохранение данных)

services:
  postgres:
    volumes:
      - postgres-data:/var/lib/postgresql/data  # named volume
      - ./init.sql:/docker-entrypoint-initdb.d/init.sql  # bind mount

5. Масштабирование

# Запустить 3 экземпляра app сервиса
docker compose up -d --scale app=3

Когда использовать что

Docker используй когда:

  • Нужно запустить один контейнер
  • Простая одноконтейнерная архитектура
  • Production на Kubernetes
  • Нужна максимальная гибкость в командной строке

Docker Compose используй когда:

  • Микросервисная архитектура (несколько сервисов)
  • Local development
  • Staging окружение
  • CI/CD pipeline
  • Нужна простота воспроизведения
  • Нужна версионная история конфигурации (git)

Production: Kubernetes вместо Docker Compose

# Docker Compose ТОЛЬКО для разработки и staging
# Production использует Kubernetes:
kubectl apply -f deployment.yaml
kubectl apply -f service.yaml
kubectl apply -f postgres-statefulset.yaml

Практический workflow

Для разработчика:
1. docker compose up -d          # Запуск всей инфраструктуры
2. npm install / mvn build      # Установка зависимостей
3. npm start / mvn spring-boot:run  # Запуск приложения
4. docker compose down           # Остановка инфраструктуры

Для CI/CD:
1. docker compose up -d          # Запуск тестовой инфраструктуры
2. mvn test                      # Тесты
3. docker compose down           # Очистка
4. docker build & push           # Push в registry
5. kubectl deploy                # Deploy в production

Заключение

  • Docker = инструмент для создания контейнеров (низкоуровневый)
  • Docker Compose = оркестрация контейнеров (высокоуровневый)
  • Для разработки: используй Docker Compose
  • Для production: используй Kubernetes
  • Docker Compose — best practice для локальной разработки микросервисных приложений

Это важный вопрос, так как показывает, что вы понимаете современный workflow разработки и как локально создавать сложные окружения.

В чем разница между Docker и Docker Compose? | PrepBro