← Назад к вопросам
Какие знаешь основные этапы написания Dockerfile?
1.3 Junior🔥 161 комментариев
#DevOps и инфраструктура
Комментарии (1)
🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)
Ответ сгенерирован нейросетью и может содержать ошибки
# Основные этапы написания Dockerfile
Dockerfile — это набор инструкций для создания Docker образа. Это критически важный навык для Python разработчика в современных реалиях. Рассмотрю полный процесс написания правильного Dockerfile.
1. Выбор базового образа (FROM)
Базовый образ — фундамент контейнера
# НЕПРАВИЛЬНО — слишком тяжёлый
FROM ubuntu:22.04
# ПРАВИЛЬНО для Python
FROM python:3.11-slim
# АЛЬТЕРНАТИВА — минимальный
FROM python:3.11-alpine
# Pinning версии ВАЖЕН для воспроизводимости
FROM python:3.11.8-slim-bullseye
Сравнение базовых образов:
| Образ | Размер | Use Case |
|---|---|---|
| ubuntu:22.04 | 77 MB | Полная ОС, редко нужно |
| python:3.11-slim | 126 MB | Оптимум для приложений |
| python:3.11-alpine | 50 MB | Минимальный, есть проблемы с некоторыми пакетами |
| python:3.11 | 1 GB | Полный образ со всем, не рекомендуется |
2. Установка рабочей директории (WORKDIR)
Организация структуры контейнера
# Устанавливаем рабочую директорию
WORKDIR /app
# Все команды далее выполняются в /app
RUN pwd # выведет /app
COPY . . # копирует в /app
3. Копирование файлов (COPY и ADD)
Copy — более простой и предпочтительный
# Копируем requirements в контейнер
COPY requirements.txt .
# Копируем весь исходный код
COPY . .
# ADD редко используется (для архивов)
ADD https://example.com/file.tar.gz .
4. Установка зависимостей (RUN)
Оптимизация: минимизация слоёв
# НЕПРАВИЛЬНО — много слоёв
RUN apt-get update
RUN apt-get install -y curl
RUN apt-get install -y git
# ПРАВИЛЬНО — один слой
RUN apt-get update && apt-get install -y \
curl \
git \
&& rm -rf /var/lib/apt/lists/*
Установка Python зависимостей
# Обновляем pip (важно!)
RUN pip install --upgrade pip
# Устанавливаем зависимости
RUN pip install --no-cache-dir -r requirements.txt
# --no-cache-dir уменьшает размер образа
5. Expose портов (EXPOSE)
Документирование портов
# EXPOSE не публикует порты, только документирует
EXPOSE 8000 5432
# При запуске используешь -p для маппинга
# docker run -p 8000:8000 my-app
6. Установка переменных окружения (ENV и ARG)
ENV — доступны в контейнере
ENV PYTHONUNBUFFERED=1
ENV PYTHONDONTWRITEBYTECODE=1
ENV APP_HOME=/app
ARG — только во время сборки
ARG PYTHON_VERSION=3.11
FROM python:${PYTHON_VERSION}-slim
# Использование: docker build --build-arg PYTHON_VERSION=3.12
7. Точка входа (ENTRYPOINT и CMD)
ENTRYPOINT — основная команда
# Shell форма (не рекомендуется)
ENTRYPOINT python app.py
# JSON форма (рекомендуется)
ENTRYPOINT ["python", "-m", "uvicorn", "main:app"]
CMD — параметры по умолчанию
ENTRYPOINT ["python", "app.py"]
CMD ["--host", "0.0.0.0", "--port", "8000"]
# Можно переопределить при запуске
# docker run my-app --host localhost --port 9000
8. Multi-stage build (оптимизация размера)
Полный пример с несколькими этапами
# Stage 1: Builder
FROM python:3.11-slim AS builder
WORKDIR /build
COPY requirements.txt .
RUN pip install --user --no-cache-dir -r requirements.txt
# Stage 2: Runtime (финальный образ)
FROM python:3.11-slim
WORKDIR /app
# Копируем только установленные пакеты из builder
COPY --from=builder /root/.local /root/.local
# Копируем исходный код
COPY . .
ENV PATH=/root/.local/bin:$PATH
EXPOSE 8000
ENTRYPOINT ["python", "main.py"]
Преимущества:
- Финальный образ меньше (не содержит build tools)
- Более безопасен (меньше потенциальных уязвимостей)
9. Полный пример Dockerfile для FastAPI приложения
# Build stage
FROM python:3.11-slim as builder
WORKDIR /build
COPY requirements.txt .
RUN pip install --upgrade pip && \
pip install --user --no-cache-dir -r requirements.txt
# Runtime stage
FROM python:3.11-slim
WORKDIR /app
ENV PYTHONUNBUFFERED=1 \
PYTHONDONTWRITEBYTECODE=1 \
PIP_NO_CACHE_DIR=1
# Копируем пакеты
COPY --from=builder /root/.local /root/.local
# Копируем код
COPY . .
ENV PATH=/root/.local/bin:$PATH
EXPOSE 8000
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
CMD curl -f http://localhost:8000/health || exit 1
ENTRYPOINT ["uvicorn", "main:app", "--host", "0.0.0.0", "--port", "8000"]
10. HEALTHCHECK (для мониторинга)
Проверка здоровья контейнера
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
CMD curl -f http://localhost:8000/health || exit 1
# Параметры:
# --interval: интервал проверки (30s)
# --timeout: максимальное время ответа (10s)
# --start-period: время до первой проверки (5s)
# --retries: количество ошибок для unhealthy (3)
11. .dockerignore файл (оптимизация сборки)
Исключаем ненужные файлы
.git
.gitignore
__pycache__
*.pyc
*.pyo
.pytest_cache
.venv
venv
.env
.env.local
node_modules
build/
dist/
.coverage
.mypy_cache
.idea
12. Чек-лист оптимизации Dockerfile
- Используй slim или alpine базовый образ
- Пинн версии всех зависимостей
- Минимизируй слои (RUN команды объединяй)
- Используй multi-stage build для уменьшения размера
- Порядок инструкций важен для кэширования
- Используй .dockerignore для исключения файлов
- Установи HEALTHCHECK для мониторинга
- Логирование без буферизации (PYTHONUNBUFFERED=1)
- Non-root пользователь для безопасности
- Минимизируй размер образа (используй --no-cache-dir)
13. Построение и запуск
# Построить образ
docker build -t my-app:1.0 .
# С аргументами сборки
docker build --build-arg PYTHON_VERSION=3.12 -t my-app:latest .
# Запустить контейнер
docker run -p 8000:8000 my-app:1.0
# С переменными окружения
docker run -p 8000:8000 -e DEBUG=true my-app:1.0
# Проверить размер
docker images | grep my-app
Выводы
- FROM — выбирай slim образы
- COPY — копируй только нужное
- RUN — объединяй команды в один слой
- Multi-stage build — уменьшает финальный размер
- HEALTHCHECK — добавляй для мониторинга
- .dockerignore — исключай ненужные файлы
- Пинн версии для воспроизводимости
- Порядок инструкций влияет на кэширование образа