1. Введение
Docker Compose стал де-факто стандартом для оркестрации многоконтейнерных приложений в среде разработки и тестирования. При работе с веб-приложениями стек LEMP (Linux, Nginx, MySQL, PHP) представляет собой классическую архитектуру, которая идеально подходит для контейнеризации.
В данном руководстве мы детально рассмотрим процесс создания производственно-готовой инфраструктуры LEMP-стека с использованием Docker Compose. Мы охватим все аспекты: от базовой настройки до продвинутых техник оптимизации и мониторинга.
Важно понимать, что правильная настройка Docker Compose не только упрощает разработку, но и обеспечивает консистентность между различными средами развертывания.
2. Предварительные требования
Прежде чем начать работу с Docker Compose, убедитесь, что ваша система соответствует минимальным требованиям и установлены необходимые компоненты.
2.1. Системные требования
- Операционная система: Linux, macOS или Windows 10/11 с WSL2
- ОЗУ: минимум 4 ГБ (рекомендуется 8 ГБ или более)
- Свободное место на диске: минимум 10 ГБ
- Процессор: поддержка виртуализации (Intel VT-x или AMD-V)
2.2. Установка Docker и Docker Compose
Для Ubuntu/Debian установка выполняется следующими командами:
# Обновление списка пакетов sudo apt update # Установка необходимых пакетов sudo apt install apt-transport-https ca-certificates curl gnupg lsb-release # Добавление официального GPG ключа Docker curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg # Добавление репозитория Docker echo "deb [arch=amd64 signed-by=/usr/share/keyrings/docker-archive-keyring.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null # Установка Docker Engine sudo apt update sudo apt install docker-ce docker-ce-cli containerd.io docker-compose-plugin # Добавление пользователя в группу docker sudo usermod -aG docker $USER # Проверка установки docker --version docker compose version
2.3. Базовые знания
Для эффективной работы с данным руководством рекомендуется иметь базовые знания:
- Понимание основ работы с Docker
- Знание синтаксиса YAML
- Опыт работы с Linux командной строкой
- Базовое понимание веб-технологий (HTTP, SQL, PHP)
3. Структура проекта
Правильная организация файлов проекта является ключевым фактором для поддерживаемости и масштабируемости вашей инфраструктуры. Рассмотрим рекомендуемую структуру каталогов.
3.1. Базовая структура
lemp-docker/
├── docker-compose.yml
├── docker-compose.override.yml
├── docker-compose.prod.yml
├── .env
├── .env.example
├── .dockerignore
├── .gitignore
├── README.md
├── Makefile
├── config/
│ ├── nginx/
│ │ ├── default.conf
│ │ ├── nginx.conf
│ │ ├── ssl/
│ │ └── sites-available/
│ ├── php/
│ │ ├── php.ini
│ │ ├── php-fpm.conf
│ │ └── www.conf
│ └── mysql/
│ ├── my.cnf
│ └── init/
│ └── 01-database.sql
├── data/
│ ├── mysql/
│ ├── nginx/
│ │ └── logs/
│ └── uploads/
├── logs/
│ ├── nginx/
│ ├── php/
│ └── mysql/
├── www/
│ ├── html/
│ │ ├── index.php
│ │ └── phpinfo.php
│ ├── site1/
│ └── site2/
└── scripts/
├── backup.sh
├── restore.sh
└── deploy.sh
3.2. Описание каталогов
- config/ — файлы конфигурации для всех сервисов
- data/ — persistent данные (базы данных, загруженные файлы)
- logs/ — файлы логов всех сервисов
- www/ — веб-файлы и приложения
- scripts/ — вспомогательные скрипты для развертывания и обслуживания
3.3. Создание структуры проекта
# Создание базовой структуры проекта
mkdir -p lemp-docker/{config/{nginx/{ssl,sites-available},php,mysql/init},data/{mysql,nginx/logs,uploads},logs/{nginx,php,mysql},www/{html,site1,site2},scripts}
cd lemp-docker
# Создание основных файлов
touch docker-compose.yml .env .env.example .dockerignore .gitignore README.md Makefile
# Создание конфигурационных файлов
touch config/nginx/{default.conf,nginx.conf}
touch config/php/{php.ini,php-fpm.conf,www.conf}
touch config/mysql/{my.cnf,init/01-database.sql}
# Создание базового веб-контента
echo "" > www/html/phpinfo.php
echo "" > www/html/index.php
4. Базовый docker-compose.yml
Файл docker-compose.yml является сердцем нашей инфраструктуры. Он определяет все сервисы, сети и тома, необходимые для работы LEMP-стека.
4.1. Основная структура файла
version: '3.8'
services:
nginx:
image: nginx:alpine
container_name: ${PROJECT_NAME:-lemp}_nginx
restart: unless-stopped
ports:
- "${NGINX_HTTP_PORT:-80}:80"
- "${NGINX_HTTPS_PORT:-443}:443"
volumes:
- ./www:/var/www/html:cached
- ./config/nginx/nginx.conf:/etc/nginx/nginx.conf:ro
- ./config/nginx/default.conf:/etc/nginx/conf.d/default.conf:ro
- ./logs/nginx:/var/log/nginx
depends_on:
- php
networks:
- lemp-network
php:
build:
context: ./config/php
dockerfile: Dockerfile
container_name: ${PROJECT_NAME:-lemp}_php
restart: unless-stopped
volumes:
- ./www:/var/www/html:cached
- ./config/php/php.ini:/usr/local/etc/php/php.ini:ro
- ./config/php/php-fpm.conf:/usr/local/etc/php-fpm.conf:ro
- ./logs/php:/var/log/php
depends_on:
- mysql
networks:
- lemp-network
mysql:
image: mysql:8.0
container_name: ${PROJECT_NAME:-lemp}_mysql
restart: unless-stopped
environment:
MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD}
MYSQL_DATABASE: ${MYSQL_DATABASE}
MYSQL_USER: ${MYSQL_USER}
MYSQL_PASSWORD: ${MYSQL_PASSWORD}
volumes:
- ./data/mysql:/var/lib/mysql
- ./config/mysql/my.cnf:/etc/mysql/my.cnf:ro
- ./config/mysql/init:/docker-entrypoint-initdb.d:ro
- ./logs/mysql:/var/log/mysql
ports:
- "${MYSQL_PORT:-3306}:3306"
networks:
- lemp-network
volumes:
mysql-data:
driver: local
networks:
lemp-network:
driver: bridge
4.2. Ключевые особенности конфигурации
- version: '3.8' — спецификация Docker Compose, поддерживающая все необходимые функции
- restart: unless-stopped — автоматический перезапуск контейнеров
- depends_on — определяет порядок запуска сервисов
- cached в volumes — оптимизация производительности для макОС и Windows
4.3. Конфигурация переменных окружения (.env)
# Общие настройки проекта PROJECT_NAME=lemp-stack ENVIRONMENT=development # Настройки Nginx NGINX_HTTP_PORT=80 NGINX_HTTPS_PORT=443 # Настройки MySQL MYSQL_ROOT_PASSWORD=your_secure_root_password MYSQL_DATABASE=app_database MYSQL_USER=app_user MYSQL_PASSWORD=your_secure_password MYSQL_PORT=3306 # Настройки PHP PHP_VERSION=8.2 PHP_MAX_EXECUTION_TIME=300 PHP_MEMORY_LIMIT=512M PHP_UPLOAD_MAX_FILESIZE=100M
5. Настройка сервиса Nginx
Nginx выступает в роли веб-сервера и обратного прокси, обрабатывая статические файлы и перенаправляя динамические запросы к PHP-FPM.
5.1. Основной конфигурационный файл nginx.conf
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log notice;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
use epoll;
multi_accept on;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
# Логирование
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
# Оптимизация производительности
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
types_hash_max_size 2048;
server_tokens off;
# Сжатие gzip
gzip on;
gzip_vary on;
gzip_min_length 1024;
gzip_comp_level 6;
gzip_types
text/plain
text/css
text/xml
text/javascript
application/javascript
application/xml+rss
application/json
image/svg+xml;
# Буферы и тайм-ауты
client_body_buffer_size 128k;
client_max_body_size 100m;
client_header_buffer_size 1k;
large_client_header_buffers 4 4k;
output_buffers 1 32k;
postpone_output 1460;
# Инклюд конфигураций сайтов
include /etc/nginx/conf.d/*.conf;
}
5.2. Конфигурация виртуального хоста default.conf
server {
listen 80;
listen [::]:80;
server_name localhost;
root /var/www/html;
index index.php index.html index.htm;
# Обработка статических файлов
location ~ \.(css|js|png|jpg|jpeg|gif|ico|svg|woff|woff2|ttf|eot)$ {
expires 1y;
add_header Cache-Control "public, immutable";
access_log off;
}
# Основное местоположение
location / {
try_files $uri $uri/ /index.php?$query_string;
}
# Обработка PHP файлов
location ~ \.php$ {
try_files $uri =404;
fastcgi_split_path_info ^(.+\.php)(/.+)$;
fastcgi_pass php:9000;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param PATH_INFO $fastcgi_path_info;
# Оптимизация FastCGI
fastcgi_buffer_size 128k;
fastcgi_buffers 4 256k;
fastcgi_busy_buffers_size 256k;
fastcgi_temp_file_write_size 256k;
fastcgi_connect_timeout 60;
fastcgi_send_timeout 60;
fastcgi_read_timeout 60;
}
# Запрет на доступ к скрытым файлам
location ~ /\. {
deny all;
access_log off;
log_not_found off;
}
}
6. Настройка сервиса PHP-FPM
PHP-FPM (ФастПроцессМенеджер) обеспечивает выполнение PHP-скриптов в отдельном контейнере.
6.1. Dockerfile для PHP-FPM
FROM php:8.2-fpm-alpine
# Установка системных зависимостей
RUN apk add --no-cache \
linux-headers \
libpng-dev \
libjpeg-turbo-dev \
freetype-dev \
zip \
libzip-dev \
curl-dev \
oniguruma-dev \
icu-dev \
postgresql-dev \
mysql-client
# Установка PHP расширений
RUN docker-php-ext-configure gd --with-freetype --with-jpeg \
&& docker-php-ext-install \
pdo \
pdo_mysql \
mysqli \
gd \
zip \
curl \
mbstring \
intl \
opcache \
bcmath
# Установка Composer
COPY --from=composer:latest /usr/bin/composer /usr/bin/composer
# Установка Xdebug для разработки
RUN apk add --no-cache $PHPIZE_DEPS \
&& pecl install xdebug \
&& docker-php-ext-enable xdebug
# Копирование конфигураций
COPY php.ini /usr/local/etc/php/php.ini
COPY php-fpm.conf /usr/local/etc/php-fpm.conf
COPY www.conf /usr/local/etc/php-fpm.d/www.conf
# Создание пользователя
RUN addgroup -g 1000 -S www && \
adduser -u 1000 -S www -G www
USER www
WORKDIR /var/www/html
EXPOSE 9000
CMD ["php-fpm"]
6.2. Конфигурация php.ini
[PHP] engine = On short_open_tag = Off precision = 14 output_buffering = 4096 zlib.output_compression = Off implicit_flush = Off unserialize_callback_func = serialize_precision = -1 disable_functions = disable_classes = zend.enable_gc = On # Ограничения ресурсов max_execution_time = 300 max_input_time = 60 memory_limit = 512M # Обработка ошибок error_reporting = E_ALL & ~E_DEPRECATED & ~E_STRICT display_errors = On display_startup_errors = On log_errors = On log_errors_max_len = 1024 ignore_repeated_errors = Off ignore_repeated_source = Off report_memleaks = On # Загрузка файлов file_uploads = On upload_max_filesize = 100M max_file_uploads = 20 post_max_size = 100M # Оптимизация OPcache [opcache] opcache.enable = 1 opcache.enable_cli = 1 opcache.interned_strings_buffer = 8 opcache.max_accelerated_files = 10000 opcache.memory_consumption = 128 opcache.save_comments = 1 opcache.revalidate_freq = 1 # Xdebug конфигурация [xdebug] xdebug.mode = debug xdebug.start_with_request = yes xdebug.client_host = host.docker.internal xdebug.client_port = 9003 xdebug.log = /var/log/php/xdebug.log
7. Настройка сервиса MySQL
MySQL 8.0 обеспечивает надежное хранение данных для наших веб-приложений.
7.1. Конфигурация my.cnf
[mysqld] port = 3306 datadir = /var/lib/mysql innodb_buffer_pool_size = 1G innodb_log_file_size = 256M max_connections = 500 character-set-server = utf8mb4 collation-server = utf8mb4_unicode_ci general_log = 1 general_log_file = /var/log/mysql/general.log log_error = /var/log/mysql/error.log slow_query_log = 1 slow_query_log_file = /var/log/mysql/slow.log long_query_time = 2
7.2. Инициализация базы данных
-- 01-database.sql CREATE DATABASE IF NOT EXISTS app_database CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci; CREATE USER IF NOT EXISTS 'app_user'@'%' IDENTIFIED BY 'your_secure_password'; GRANT SELECT, INSERT, UPDATE, DELETE, CREATE, DROP, INDEX, ALTER ON app_database.* TO 'app_user'@'%'; FLUSH PRIVILEGES;
10. Запуск и развертывание
После подготовки всех конфигурационных файлов можно приступать к запуску среды.
# Первый запуск docker compose config docker compose build docker compose up -d # Проверка статуса docker compose ps docker compose logs -f # Основные команды docker compose stop docker compose start docker compose restart nginx # Проверка работоспособности curl -I http://localhost curl http://localhost/phpinfo.php
12. Лучшие практики и безопасность
Соблюдение лучших практик обеспечивает безопасность и надежность вашей инфраструктуры.
12.1. Безопасность
- Используйте сильные пароли для всех сервисов
- Не выносите порты баз данных наружу в production
- Ограничивайте права пользователей в контейнерах
- Используйте SSL/TLS сертификаты для HTTPS
- Регулярно обновляйте образы Docker
Помните: безопасность — это не однократная настройка, а непрерывный процесс. Регулярно обновляйте свои конфигурации и следите за обновлениями безопасности.
15. Заключение
Docker Compose предоставляет мощные возможности для организации современной инфраструктуры LEMP-стека. Правильная настройка позволяет достичь высокой производительности, масштабируемости и надежности.
Основные преимущества данного подхода: изоляция сервисов, легкость развертывания, портативность между окружениями и стандартизация процессов разработки.
Продолжайте изучать возможности контейнеризации и адаптируйте предложенные решения под специфику ваших проектов.