axe-web/nginx.conf

70 lines
4.1 KiB
Nginx Configuration File
Raw Normal View History

# Отдача статики тестового веба.
# Роутинг у нас hash-based (#/tickets), но на всякий случай любой
# несуществующий путь ведём на index.html — случайный 404 мешает отладке.
# Зоны лимитов лежат здесь (файл подключается в http-контексте через
# conf.d): 10 запросов/сек на IP и до 20 одновременных соединений.
# Браузеру с запасом хватает, а зациклившийся retry фронта упрётся
# в потолок, а не будет долбить статику бесконечно.
limit_req_zone $binary_remote_addr zone=perip:1m rate=10r/s;
limit_conn_zone $binary_remote_addr zone=addr:1m;
server {
listen 80;
server_name _;
root /usr/share/nginx/html;
index index.html;
gzip on;
gzip_types text/css application/javascript application/json;
gzip_min_length 1024;
# HSTS: по HTTP браузер заголовок игнорирует, поэтому локально он
# безвреден, а с TLS (домен и сертификат — при деплое) заставит
# браузер держать сайт только по https. includeSubDomains — потому
# что на одном домене будут и API, и фото-прокси.
# ВНИМАНИЕ: add_header на уровне server перекрывается ЛЮБЫМ
# add_header внутри location — поэтому в location / заголовки
# продублированы явно.
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-Frame-Options "SAMEORIGIN" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
# burst — на пачку файлов при первой загрузке страницы (~5 запросов),
# сверх лимита — сразу 429, а не неопределённое ожидание.
limit_req zone=perip burst=30 nodelay;
limit_req_status 429;
limit_conn addr 20;
limit_conn_status 429;
# API на том же origin (BASE='' в js/api.js): проксируем API-пути
# бэкенда, остальное — статика. Regex-локация важнее prefix /.
# X-Forwarded-For ПЕРЕЗАПИСЫВАЕМ ($remote_addr), а не дополняем:
# gin берёт левый элемент и по нему считает лимиты и client_ip в
# логах — дописанный клиентом мусор останется левым элементом.
# local dev: бэкенд на хосту (host.docker.internal:8080);
# в проде адрес подставит app-nginx.prod.
location ~ ^/(auth|users|projects|objects|tickets|invitations|recurring|ping|db-ping|swagger)(/|$) {
proxy_pass http://host.docker.internal:8080;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Forwarded-Proto $scheme;
# Фотоотчёт: до 10 МБ + запас на multipart-обвязку.
client_max_body_size 12m;
}
location / {
try_files $uri $uri/ /index.html;
# Кэш мешает отладке: отдаём всегда свежее.
# add_header в этой локации перекрывает серверный (nginx не
# смешивает уровни) — заголовки дублируем здесь явно.
add_header Cache-Control "no-cache";
add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
add_header X-Content-Type-Options "nosniff" always;
add_header X-Frame-Options "SAMEORIGIN" always;
add_header Referrer-Policy "strict-origin-when-cross-origin" always;
}
}