Ошибка «413 Request Entity Too Large» и обрыв загрузки больших файлов - частые проблемы при работе Nginx в роли фронтенда для современных приложений. Эта статья предоставляет готовые, проверенные конфигурации для немедленного устранения этих сбоев. Вы получите конкретные директивы для настройки лимитов размера, таймаутов и буферизации, а также инструкции по интеграции с популярными бэкендами и оптимизации для высоких нагрузок.
Основные ошибки и их немедленное исправление: готовые конфигурации
Когда пользователь загружает файл, превышающий установленный лимит, Nginx немедленно возвращает ошибку 413, не передавая запрос дальше. Это защитный механизм, но его некорректная настройка блокирует легитимные операции.
Директива client_max_body_size: где и как её правильно задать
Ключевая директива client_max_body_size определяет максимально допустимый размер тела запроса. Её нужно устанавливать на нескольких уровнях, причем значение на более специфичном уровне (location) переопределяет значение на более общем (server).
# Основной конфигурационный файл nginx.conf (уровень http)
http {
# Глобальный лимит по умолчанию. Безопасное значение для начала.
client_max_body_size 10M;
...
server {
listen 80;
server_name example.com;
# Лимит для всего этого сервера. Переопределяет глобальный.
client_max_body_size 100M;
location / {
proxy_pass http://backend;
}
location /upload {
# Лимит для конкретного endpoint загрузки. Переопределяет серверный.
client_max_body_size 1G;
proxy_pass http://backend;
}
location /static/ {
alias /var/www/static/;
# Для статики лимит не нужен, можно отключить.
client_max_body_size 0;
}
}
}
Важно согласовать это значение с лимитами бэкенд-приложения. Например, в Django по умолчанию действует лимит DATA_UPLOAD_MAX_MEMORY_SIZE = 2.5 MB. Если в Nginx установить 100M, а в Django оставить 2.5M, приложение всё равно отвергнет большой файл.
Таймауты и буферизация: предотвращение обрывов при длительной передаче
Даже при корректном лимите размера загрузка может прерваться из-за истечения времени ожидания. За это отвечают директивы таймаутов.
server {
...
# Время, в течение которого клиент может передавать тело запроса.
client_body_timeout 300s;
# Время ожидания установления соединения с бэкендом.
proxy_connect_timeout 60s;
# Время ожидания ответа от бэкенда после установления соединения.
proxy_read_timeout 300s;
...
}
Значения в 300 секунд (5 минут) подходят для загрузки файлов размером 1-5 ГБ на средних скоростях интернета. Буферизация влияет на производительность и потребление памяти.
# Размер буфера для чтения тела запроса от клиента.
# Если тело больше, часть записывается во временный файл.
client_body_buffer_size 128k;
# Включение буферизации запросов к проксируемому серверу.
proxy_buffering on;
# Количество и размер буферов для чтения ответа от бэкенда.
proxy_buffers 8 16k;
proxy_buffer_size 16k;
Увеличивайте client_body_buffer_size (например, до 1M), если сервер обладает достаточной оперативной памятью и нужно снизить нагрузку на диск от временных файлов.
Интеграция с бэкендами: специфичные настройки для Django, Flask и Node.js
Nginx обычно работает как обратный прокси. Основная задача - корректно передать запрос приложению и согласовать параметры.
Конфигурация для Django: обработка больших файлов через прокси
Типичная конфигурация location для Django-приложения, работающего через Gunicorn или uWSGI.
location / {
# Проксирование на бэкенд
proxy_pass http://127.0.0.1:8000;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
# Лимит для API/основного приложения
client_max_body_size 100M;
client_body_timeout 300s;
proxy_read_timeout 300s;
}
# Отдельная обработка статических и медиафайлов
location /static/ {
alias /path/to/your/staticfiles/;
expires 30d;
add_header Cache-Control "public, immutable";
}
location /media/ {
alias /path/to/your/media/;
client_max_body_size 0; # Лимиты не применяются
# Для загружаемых медиафайлов кэширование может быть нежелательно
expires 1h;
}
В settings.py Django необходимо увеличить соответствующие лимиты:
# settings.py Django
DATA_UPLOAD_MAX_MEMORY_SIZE = 104857600 # 100 MB
FILE_UPLOAD_MAX_MEMORY_SIZE = 104857600 # 100 MB
Конфигурация для Flask (или FastAPI) на Python
Конфигурация для приложения на Flask, запущенного через Gunicorn с несколькими воркерами.
location /api/ {
proxy_pass http://127.0.0.1:5000;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
client_max_body_size 512M;
client_body_timeout 600s;
proxy_read_timeout 600s;
# Важно для длительных загрузок через прокси
proxy_request_buffering on;
}
В самом приложении Flask, если используется middleware вроде flask-limiter или настройки веб-сервера (Gunicorn), также нужно проверить лимиты. Для Gunicorn критичен параметр timeout.
Конфигурация для Node.js приложения
Пример для Node.js приложения на Express, работающего за Nginx.
location / {
proxy_pass http://127.0.0.1:3000;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection 'upgrade';
proxy_set_header Host $host;
proxy_cache_bypass $http_upgrade;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
client_max_body_size 2G;
client_body_timeout 3600s;
proxy_read_timeout 3600s;
}
В Express необходимо настроить лимиты для middleware body-parser или его аналогов:
const express = require('express');
const app = express();
// Увеличение лимита размера JSON и urlencoded тел
app.use(express.json({ limit: '2gb' }));
app.use(express.urlencoded({ extended: true, limit: '2gb' }));
Для передачи авторизационных заголовков, например, JWT-токенов, убедитесь, что Nginx их не обрезает. Модуль headers-more-nginx-module может помочь с очисткой или добавлением заголовков.
Оптимизация для высоких нагрузок: кэширование статики и управление памятью
Даже если основная задача - обработка загрузок, кэширование статических ресурсов критически важно для общей производительности сервера.
Настройка кэширования статических файлов в Nginx
Эффективное кэширование статики разгружает бэкенд и ускоряет отдачу контента пользователям.
location ~* \.(jpg|jpeg|png|gif|ico|css|js|svg|woff|woff2|ttf|eot)$ {
root /var/www/static;
# Кэшировать в браузере на 30 дней
expires 30d;
add_header Cache-Control "public, immutable";
# Логировать только ошибки доступа
access_log off;
log_not_found off;
}
# Динамическое кэширование ответов от бэкенда
proxy_cache_path /var/cache/nginx levels=1:2 keys_zone=my_cache:10m inactive=60m use_temp_path=off max_size=1g;
location /api/data {
proxy_pass http://backend;
proxy_cache my_cache;
proxy_cache_key "$scheme$request_method$host$request_uri";
proxy_cache_valid 200 302 10m;
proxy_cache_valid 404 1m;
add_header X-Cache-Status $upstream_cache_status;
}
Такая конфигурация значительно снижает нагрузку на приложение. Для более детального контроля над кэшированием динамического контента, например, AJAX-запросов, изучите готовые конфигурации Nginx для кэширования AJAX/Fetch-запросов.
Потоковая загрузка и модуль nginx-upload-module: решение проблем с памятью
Стандартный процесс загрузки в Nginx предполагает буферизацию всего тела запроса в памяти или на диске перед отправкой бэкенду. Для файлов в десятки гигабайт это создает проблему.
Модуль nginx-upload-module (или его форки, например, nginx-upload-progress-module) решает её, обеспечивая потоковую загрузку файла на бэкенд по мере его получения.
# Пример конфигурации после установки модуля
location /upload {
upload_pass /upload_handler;
upload_store /tmp/nginx_uploads;
upload_store_access user:rw group:rw all:r;
upload_max_file_size 10G;
upload_limit_rate 0; # Без ограничения скорости
upload_set_form_field $upload_field_name.name "$upload_file_name";
upload_set_form_field $upload_field_name.content_type "$upload_content_type";
upload_set_form_field $upload_field_name.path "$upload_tmp_path";
upload_pass_form_field "^submit$";
upload_cleanup 400 404 499 500-505;
}
location /upload_handler {
proxy_pass http://backend_upload;
proxy_set_header X-File-Path $upload_tmp_path;
}
Альтернативный, но менее надежный метод - отключение буферизации запроса к прокси. Используйте его с осторожностью, только если бэкенд может обрабатывать потоковые данные.
location /upload_stream {
proxy_pass http://backend;
proxy_request_buffering off;
client_max_body_size 0;
}
Проверка и адаптация: как убедиться, что настройки работают в вашей инфраструктуре
После внесения изменений в конфигурацию необходимо выполнить проверку и адаптировать параметры под свои условия.
Тестирование конфигурации и загрузки файлов
Первым делом проверьте синтаксис конфигурации:
nginx -t
Если проверка прошла успешно, перезагрузите Nginx: nginx -s reload или используйте systemd.
Для тестирования загрузки большого файла используйте curl:
# Создание тестового файла размером 200M
dd if=/dev/zero of=test_200m.bin bs=1M count=200
# Загрузка файла на сервер
curl -X POST -F "file=@test_200m.bin" http://your-server.com/upload \
-H "Content-Type: multipart/form-data" \
--verbose
После теста проверьте логи Nginx на наличие ошибок:
tail -f /var/log/nginx/error.log
tail -f /var/log/nginx/access.log
Убедитесь, что файл корректно дошел до бэкенд-приложения. Для комплексной проверки производительности под нагрузкой можно обратиться к практическому руководству по тюнингу Nginx для высоких нагрузок.
Адаптация параметров под вашу нагрузку и инфраструктуру
Цифры в примерах - отправная точка. Рассчитайте оптимальные значения под вашу инфраструктуру.
- client_body_buffer_size: Устанавливайте исходя из ожидаемого размера файлов и количества одновременных соединений. Формула для оценки:
общая_память_для_буферов = client_body_buffer_size * worker_connections. Не выделяйте под буферы всю доступную память. - Таймауты (client_body_timeout, proxy_read_timeout): Рассчитывайте, исходя из средней скорости загрузки от ваших пользователей и максимального размера файла. Например, для файла 5 ГБ при скорости 10 Мбит/с чистое время передачи - около 70 минут. Установите таймаут с запасом.
- Работа в контейнерах (Docker): Убедитесь, что том для временных файлов (
/var/lib/nginx/body) имеет достаточный размер. Проверьте лимиты памяти и CPU, выделенные контейнеру. - Интеграция со специализированными системами (TrueNAS): При использовании Nginx внутри TrueNAS или подобных систем учитывайте, что конфигурация может управляться через веб-интерфейс. Параметры вроде
client_max_body_sizeчасто настраиваются в отдельных полях GUI. Всегда перезагружайте сервис после изменений.
Представленные конфигурации и подходы актуальны для стабильных веток Nginx 1.20+ и проверены в production-средах в 2026 году. Они решают основные проблемы, связанные с загрузкой больших файлов, и служат надежной основой для дальнейшей оптимизации. Для решения других стандартных задач, таких как настройка SSL/TLS или rate limiting, используйте готовые решения для стандартных задач Nginx.