RTFM.WIKI

Ordnung muß sein. Ordnung über alles (18+)

Инструменты пользователя

Инструменты сайта


Stylesheet conf/userstyle.css not found, please contact the developer of "dokuwiki_2024" template.
linux:nginx:nginx_tnt

Различия

Показаны различия между двумя версиями страницы.

Ссылка на это сравнение

Предыдущая версия справа и слеваПредыдущая версия
Следующая версия
Предыдущая версия
linux:nginx:nginx_tnt [2021/11/01 17:12] dxlinux:nginx:nginx_tnt [2022/08/04 14:12] (текущий) dx
Строка 1: Строка 1:
 +====== nginx: tips & howto ======
  
 +===== Генератор конфига =====
 +
 +  * https://nginxconfig.io
 +  * https://nginxbeautifier.com / https://github.com/vasilevich/nginxbeautifier
 +  * https://github.com/1connect/nginx-config-formatter
 +  * https://git.blindage.org/21h/nginx-formatter
 +
 +Отдельно хочу отметить утилиту [[https://github.com/yandex/gixy|gixy]] для провеки конфига на наличие разного рода ошибок.\\
 +
 +===== Конфиги сниппеты =====
 +
 +  * https://github.com/h5bp/server-configs-nginx/tree/master/h5bp
 +  * https://github.com/gulch/Trickz-Snipz/blob/master/nginx/NGINX-GCONF/nginx.conf
 +  * https://github.com/gulch/Trickz-Snipz/tree/master/nginx/NGINX-GCONF/templates
 +  * https://github.com/david-rahrer/nginx-opencart/blob/master/nginx/sites-available/example.com-le.vhost
 +
 +===== Редиректы =====
 +
 +==== Редирект всех запросов на определенный файл ====
 +
 +<code>
 +root /var/www/foobar.com;
 +index index.php;
 +
 +location / {
 +    try_files $uri $uri/ @redirect;
 +}
 +location ~ \.php$ {
 +    try_files $uri @redirect;
 +    ...
 +}
 +location @redirect {
 +    return 301 /index.php;
 +}
 +</code>
 +
 +Works like a charm, как говорится.
 +
 +==== Перенаправление на SSL-адрес (HTTPS) с нестандартным портом ====
 +
 +via http://www.f-notes.info/nginx:ssl_non-stadard_port
 +
 +<code>error_page 497 https://$server_name:8443$request_uri;</code>
 +
 +==== Редирект на https://foobar.com ====
 +
 +<code>
 +server {
 +    listen 80;
 +    server_name foobar.com www.foobar.com
 +    return 301 https://www.foobar.com$request_uri;
 +}
 +server {
 +    listen 443 ssl;
 +    server_name foobar.com;
 +
 +    ssl_certificate     /etc/nginx/ssl/www.foobar.com.crt;
 +    ssl_certificate_key /etc/nginx/ssl/www.foobar.com.key;
 +
 +    return 301 https://www.foobar.com$request_uri;
 +}
 +
 +server {
 +    listen 443 ssl;
 +    server_name www.foobar.com;
 +    root /var/www/html
 +
 +    ssl_certificate     /etc/nginx/ssl/www.foobar.com.crt;
 +    ssl_certificate_key /etc/nginx/ssl/www.foobar.com.key;
 +}
 +</code>
 +
 +==== Еще примеры ====
 +
 +  * https://pai-bx.com/wiki/nginx/2332-useful-redirects-in-nginx/
 +  * 
 +
 +===== Банхаммер3000 =====
 +
 +==== Блокируем через geoip ====
 +
 +http://blog.ls20.com/optimizing-nginx-config-for-your-website-or-blog/
 +
 +Начиная с версии [[https://www.nginx.com/blog/dynamic-modules-nginx-1-9-11/|1.9.11]] введена поддержка динамических модулей
 +
 +Примеры использования модуля - http://nginx.org/en/docs/http/ngx_http_geoip_module.html
 +
 +<code>
 +yum install nginx-module-geoip
 +apt-get install nginx-module-geoip  
 +</code>
 +
 +Добавляем в самое начало файла ''/etc/nginx/nginx.conf'' перед блоком **http {}**
 +
 +<code>
 +load_module "modules/ngx_http_geoip_module.so";
 +</code>
 +
 +Коды названий стран
 +
 +[[https://dev.maxmind.com/geoip/legacy/codes/iso3166/|ISO 3166 Country Codes]]
 +
 +В блок **http {}** перед **include** добавить
 +
 +<code>
 +    geoip_country /usr/share/GeoIP/GeoIP.dat;
 +    map $geoip_country_code $allowed_country {
 +        default yes;
 +        RU no;
 +        UA no;
 +        BY no;
 +        CN no;
 +    }
 +</code>
 +
 +Для блокировки нужно добавить в **server {}**
 +
 +<code>
 +    if ($allowed_country = no) {
 +        return 444;
 +</code>
 +
 +444 - закрыть соединение без отправки ответа клиенту.
 +
 +FIXME почитать про GeoIP2
 +  * https://medium.com/@karljohnson/geoip-discontinuation-upgrade-to-geoip2-with-nginxon-centos-c2a3dbcf8fd
 +  * 1
 +
 +==== Блокируем поисковых ботов ====
 +
 +  * https://github.com/mitchellkrogza/nginx-ultimate-bad-bot-blocker
 +  * https://github.com/mariusv/nginx-badbot-blocker
 +
 +<code>
 +map $http_user_agent $bad_bot {
 +    default 0;
 +    ~(?i)(alexa.com|AltaVista|ApacheBench|Aport|Ahrefs|AhrefsBot|Baiduspider|BLEXBot|CCBot|CommentReader|Copier|Crowsnest|DISCo|discobot|ExpertSearch|ExpertSearchSpider|FairShare|FeedFetcher|FlaxCrawler|FastSeek|FlappyBot|FlashGet|GetRight|GetWeb!|Grabber|g00g1e|HTTrack|ia_archiver|LeechFTP|LeechGet|Linguee|LinkBot|MauiBot|MJ12|MJ12bot|netvampire|Offline|PycURL|Python|QuerySeekerSpider|Ruby|Seopult|Semrush|SEMrushBot|SputnikBot|spbot|SputnikFaviconBot|SputnikImageBot|Sogou|TalkTalk|Teleport|uTorrent|urllib|Vampire|vkShare|WebCopy|WebCopier|WebCollector|WebSpider|WebStripper|WebWhacker|Yeti|YottosBot) 1;
 +}
 +</code>
 +
 +В **server {}** добавить в нужное место
 +
 +<code>if ($bad_bot = 1) { return 403; }</code>
 +
 +Для проверки представимся ahrefsom
 +
 +<code>curl http://localhost -H 'User-Agent: Ahrefs' -I</code>
 +
 +==== Блокируем реферальный спам ====
 +1
 +Добавляес в ''http {}'' спам домены
 +
 +<code>
 +map $http_referer $bad_referer {
 +    hostnames;
 +    default                           0;
 +    "~*best\-seo\-solutions\.com"     1;
 +    "~*buy\-cheap\-online\.net"       1;
 +    "~*get\-free\-traffic\-now\.biz"  1;
 +}
 +</code>
 +
 +Добавляес в ''server {}'' для нужного сайта
 +
 +<code>
 +server {
 + if ($bad_referer) {
 + return 444;
 + }
 +}
 +</code>
 +
 +Можно использовать [[https://github.com/Stevie-Ray/referrer-spam-blocker|готовый черный список]] через include
 +
 +<code>
 +http {
 + include referral-spam.conf;
 +}
 +</code>
 +
 +В этом нам поможет [[http://nginx.org/en/docs/http/ngx_http_map_module.html|ngx_http_map_module]]
 +
 +===== PHP-FPM =====
 +
 +==== ondemand или dynamic ====
 +
 +  * [[https://www.linux.org.ru/forum/web-development/13089187?lastmod=1482082470587#comment-13089427|Как быть с пулами в php-fpm, если сайтов больше 2-x?]]
 +  * [[https://ma.ttias.be/a-better-way-to-run-php-fpm/|A better way to run PHP-FPM]]
 +  * [[https://hcbogdan.com/php/2016/09/16/php-fpm-dynamic/|Настраиваем php-fpm / hcbogdan]]
 +
 +//Во-первых пул это просто набор процессов. Это не какой-то отдельный процесс.\\
 +При политике ondemand воркеры создаётся только тогда когда приходит запрос. Через несколько секунд (задаётся в настройках) после завершения обработки запроса (если не поступит нового запроса который можно передать воркеру) воркер убивается.\\
 +При dynamic демон всегда поддерживает некоторое заданное количество воркеров в пуле, и распределяет запросы между ними. Если для обработки запросов не хватает воркеров то демон создаёт дополнительных (вплоть до некоторого конфигурируемого значения). Когда потребность в дополнительных воркерах отпадает демон убивает лишние, так что-бы осталось нужное количество.\\
 +Профит от повторного использования воркеров в том что не тратится время на повторное создание процесса. Но если у тебя тормозной код то на его фоне ты этого времени всё-равно не заметишь.\\
 +На сколько я понимаю это происходит как-то так.
 +
 +Попаболь в том что воркеры не особо спешат освобождать память использованную для обработки запроса (кстати я не в курсе баг это или какая-то непонятная фича). По этому если твоё приложение на обработку каждого запроса тратит (например) 100 мб памяти и у тебя есть 3 воркера, каждый из которых за свою жизнь получил хотя-бы один запрос, то у тебя в системе будет висеть три процесса каждый из которых выжирает по 100 мб памяти, даже если запросов в тот пул сейчас нет вообще. Побаболь наступает тогда когда у тебя есть куча малопосещаемых сайтов с жадным до памяти кодом.
 +
 +У меня используется dynamic для пулов которые без запросов не остаются, и ondemand для малопосещаемых сайтов.//
 +
 +==== Калькулятор max_children ====
 +
 +cli
 +  * [[https://myshell.co.uk/blog/2012/07/adjusting-child-processes-for-php-fpm-nginx/|Adjusting child processes for PHP-FPM (Nginx)]]
 +  * https://tresnet.ru/archives/1313
 +
 +ui calc
 +  * https://cmorrell.com/php-fpm/
 +  * [[https://chrismoore.ca/2018/10/finding-the-correct-pm-max-children-settings-for-php-fpm/|Finding the correct pm.max_children settings for PHP-FPM]] / https://spot13.com/pmcalculator/ / https://github.com/spot13/pmcalculator
 +
 +==== Разное FPM ====
 +
 +  * [[https://www.getpagespeed.com/server-setup/nginx/no-input-file-specified|NGINX vs PHP-FPM: No input file specified]]
 +  * [[https://www.vennedey.net/resources/3-Secure-webspaces-with-NGINX-PHP-FPM-chroots-and-Lets-Encrypt|Secure webspaces with NGINX, PHP-FPM chroots and Let's Encrypt]] / [[https://www.vennedey.net/jailspaces|Jailspaces]]
 +  * [[https://publications.jbfavre.org/web/php-fpm-apps-server-nginx.en|PHP-FPM, application server made by PHP]]
 +  * [[http://docs.mirocow.com/doku.php?id=system:php:chroot|php-fpm в chroot и некоторые трудности]]
 +  * [[http://mailman.nginx.org/pipermail/nginx-ru/2013-June/051221.html|Re: Проблема с chroot в связке Nginx + PHP-FPM]]
 +  * https://blog.programs74.ru/how-to-installing-and-configuring-server-for-web-hosting/
 +  * [[https://haydenjames.io/php-fpm-tuning-using-pm-static-max-performance/|PHP-FPM tuning: Using ‘pm static’ for max performance]]
 +
 +
 +==== Дебаг PHP-FPM с помощью strace ====
 +
 +  * [[https://shubhamjain.co/2015/09/10/debugging-stuck-php-fpm-process-with-strace/|Debugging Stuck PHP-FPM Process With Strace]]
 +  * [[https://www.bggofurther.com/2015/04/using-strace-with-multiples-pids|Using strace with multiples PIDs]]
 +  * [[https://blog.sleeplessbeastie.eu/2019/10/14/how-to-strace-php-fpm-processes/|How to strace PHP-FPM processes / blog.sleeplessbeastie.eu]]
 +  * [[https://stackoverflow.com/questions/33643131/how-strace-php-fpm-process|how strace php-fpm process?]]
 +  * [[https://medium.com/@nickpeirson/analyse-running-php-processes-with-free-open-source-tools-538ae18f5fe1|Inspecting rogue PHP processes]]
 +
 +===== Разное =====
 +
 +==== Ограничение доступа для групп адресов ====
 +
 +''/etc/nginx/includes/admin-ips''
 +
 +<code>
 +allow 1.2.3.4/32;
 +allow 1.2.3.8/32;
 +</code>
 +
 +''/etc/nginx/includes/private-ips''
 +
 +<code>
 +allow 10.0.0.0/8;
 +allow 172.16.0.0/12;
 +allow 192.168.0.0/16;
 +</code>
 +
 +''/etc/nginx/includes/testing-ips''
 +
 +<code>
 +allow 4.5.6.7;
 +allow 8.9.10.11;
 +</code>
 +
 +''/etc/nginx/conf.d/foobar.conf''
 +
 +<code>
 +location ^~ /admin/ {
 +    include includes/admin-ips;
 +    deny all;
 +}
 +
 +location ^~ /beer/ {
 +    include includes/admin-ips;
 +    include includes/testing-ips;
 +    include includes/private-ips;
 +    deny all;
 +}
 +
 +location ^~ /vodka/ {
 +    include includes/admin-ips;
 +    include includes/testing-ips;
 +    deny all;
 +}
 +</code>
 +
 +==== Как работает SNI ====
 +
 +  * https://www.itsfullofstars.de/2020/12/server-name-indication/
 +
 +==== Что такое CORS ====
 +
 +  * [[https://ibnrubaxa.medium.com/nginx-vs-cors-7a63029d9a34|NGINX vs. CORS]]
 +  * [[https://enable-cors.org/server_nginx.html|CORS on Nginx]]
 +  * [[https://evilinside.ru/nastrojka-cors-v-nginx/|Настройка CORS в Nginx]]
 +
 +==== Отключить кэширование для директории ====
 +
 +Например есть такое
 +
 +<code>
 +location /static {
 +    alias /var/www/foobar.com/static;
 +    add_header Pragma "cache";
 +    add_header Cache-Control "public";
 +}
 +</code>
 +
 +И есть апишечка где кэш очень вреден
 +
 +
 +<code>
 +location /api/ping-pong {
 +    add_header Pragma "no-cache";
 +    add_header Cache-Control "private, max-age=0, no-cache, no-store";
 +}
 +</code>
 +
 +==== X509_check_private_key:key values mismatch ====
 +
 +Нарушен порядок в crt/pem файле.
 +
 +<code>
 +-----BEGIN CERTIFICATE-----
 +Сертификат_сервера
 +-----END CERTIFICATE-----
 +-----BEGIN CERTIFICATE-----
 +Сертификат корневого центра сертификации (CA)
 +-----END CERTIFICATE-----
 +-----BEGIN CERTIFICATE-----
 +СЕРТИФИКАТ ПРОМЕЖУТОЧНОГО ЦЕНТРА СЕРТИФИКАЦИИ
 +Сертификат промежуточного центра сертификации (Intermediate)
 +-----END CERTIFICATE-----
 +</code>
 +
 +==== HTTPOnly и Secure Cookie ====
 +
 +  * https://rdevelab.ru/blog/no-category/post/samesite-cross-domain-cookies
 +  * https://itgala.xyz/nginx-httponly-and-secure-cookie/
 +
 +==== favicon.ico ====
 +
 +По стандарту, "картинка (иконка) сайта" должна быть. Поэтому в еррлоги активно пишется на каждый запрос, что favicon.ico not found.
 +Можно для nginx создать секцию
 +<code>
 +location /favicon.ico {
 +    root ...
 +    log_not_found off;
 +    access_log off;
 +}
 +</code>
 +
 +Есть опция **empty_gif**
 +<code>
 +location /favicon.ico {
 +    empty_gif;
 +    access_log off;
 +}
 +</code>
 +
 +Таким образом будет отдаваться прозрачный гиф 1х1px на все запросы иконки.
 +
 +А теперь объединим.
 +
 +<code>
 + location /favicon.ico {
 +    access_log off;
 +    try_files $uri @emptygif;
 +}
 +location @emptygif {
 +    internal;
 +    empty_gif;
 +}
 +</code>
 +
 +via
 +  * http://nginx.org/en/docs/http/ngx_http_empty_gif_module.html
 +  * http://dragonflybsd.blogspot.ru/2012/10/nginx-faviconico.html
 +
 +==== Закрываем сайт на обслуживание ====
 +
 +**Варианты**
 +
 +**1) в location /**
 +
 +<code>
 +## System Maintenance (Service Unavailable)
 +if (-f $document_root/system_maintenance.html ) {
 +error_page 503 /system_maintenance.html;
 +return 503;
 +}
 +</code>
 +
 +(if нежелателен - там куча ограничений, нюансов и оно довольно сильно грузит сервер, [[http://wiki.nginx.org/IfIsEvil|IfIsEvil]])
 +
 +**2) try_files closed.html @apache =503;**\\
 +(проблема в том, что в таком варианте код ответа при обслуживании будет 200). Хотя можно сделать отдельный location closed.html и в нем выставить код ответа 503, по желанию оттуда же отдать и саму страницу.
 +Можно написать как
 +<code>try_files /maintenance.html $uri $uri/ @wordpress;</code>
 +но если индекса нет и апач перекидывает на какую-то внутреннюю страницу с рядом опций - могут быть проблемы, если такой файл вдруг появится, а это не предусмотрено системой. Плюс, если была встроенная фильтрация на бэкенде - так ее можно обойти. Ну и 2 лишние проверки получаем.
 +
 +С другой стороны, для простых движков этот вариант будет быстрее и если вся статика не вынесена по отдельным location, автоматом начнётся раздача статики. Но снова безопасность, надо тогда создавать location на потенциально опасные места и там запрещать, обязательно. В частности на .ht, .svn, .git, служебные области. В общем, лучше первая версия этого варианта.
 +
 +**3) через переменную и if**
 +<code>
 +set $Maintenance = off;
 +if ($Maintenance = 'on') ...
 +но см выше про if.
 +</code>
 +
 +**4) выделить блок, закрывающий сайт на обслуживание в отдельный файл maint.conf**, сделать 2 файла maint-on.conf и maint-off.conf, и вешать симлинк на нужную версию файла с именем maint.conf и потом делать reload. Можно не симлинком а копированием. Самый быстрый способ, но требует немного кодинга.
 +
 +via http://dragonflybsd.blogspot.ru/2012/10/nginx.html
 +
 +==== Как убедиться, что работает gzip_static ====
 +
 +Нашёл здесь - https://stackoverflow.com/questions/2460821/how-can-i-check-that-the-nginx-gzip-static-module-is-working
 +
 +Находим PID
 +
 +<code>
 +# ps ax | grep nginx
 + 1071 ?        Ss     0:01 nginx: master process /usr/sbin/nginx -c /etc/nginx/nginx.conf
 +17947 pts/0    S+     0:00 grep --color=auto nginx
 +18315 ?        S      0:25 nginx: worker process
 +</code>
 +
 +Запускаем trace
 +
 +<code>
 +# strace -p 18315 2>&1 | grep gz
 +open("/home/admin/web/foobar.com/public_html/uploads/posts/2017-01/1485714800-275451094.jpg.gz", O_RDONLY|O_NONBLOCK|O_LARGEFILE) = 34
 +open("/home/admin/web/foobar.com/public_html/uploads/posts/2017-01/1485714801-2083693483.jpg.gz", O_RDONLY|O_NONBLOCK|O_LARGEFILE) = 34
 +open("/home/admin/web/example.com/public_html/uploads/posts/2016-11/thumbs/1480346913_09b7vuxzf2vgwqd.jpg.gz", O_RDONLY|O_NONBLOCK|O_LARGEFILE) = -1 ENOENT (No such file or directory)
 +</code>
 +
 +==== monit ====
 +
 +https://mmonit.com/wiki/Monit/Nginx
 +
 +<code>
 +server {
 +  listen 80;
 +  server_name monit.domain.com;
 +  location / {
 +    proxy_pass 127.0.0.1:2812;
 +    proxy_set_header Host $host;
 +  }
 +}
 +</code>
 +
 +==== Много соединений в TIME_WAIT ====
 +
 +Apache (backend) nginx (frontend). В netstat сотни/тысячи коннектов в состоянии TIME_WAIT. В итоге система упирается в количество доступных сетевых сокетов, что приводит к невозможности устанавливать новые соединения.
 +
 +Скорее всего это нормально если включён keepalive. Если устанавливается много новых подключений и быстро разрываются, то образуется очередь из TIME_WAIT.
 +
 +Решением было установить для параметров ядра **TCP_TW_RECYCLE** и **TCP_TW_REUSE** значение **1**, по-умолчанию **0**
 +
 +Применять с осторожностью
 +
 +<code>
 +echo 1 > /proc/sys/net/ipv4/tcp_tw_recycle
 +echo 1 > /proc/sys/net/ipv4/tcp_tw_reuse
 +</code>
 +
 +Или добавить в ''/etc/sysctl.conf''
 +
 +<code>
 +net.ipv4.tcp_tw_reuse=1
 +net.ipv4.tcp_tw_recycle=1
 +net.ipv4.tcp_fin_timeout=15
 +net.ipv4.ip_local_port_range = 10240 65000
 +</code>
 +
 +  * TCP_TW_RECYCLE Description: Enables fast recycling of TIME_WAIT sockets. Use with caution and ONLY in internal network where network connectivity speeds are “faster”.
 +  * TCP_TW_REUSE Description: Allows for reuse of sockets in TIME_WAIT state for new connections, only when it is safe from the network stack’s perspective.
 +
 +**Обновлено**
 +
 +Ошибка **sysctl: cannot stat /proc/sys/net/ipv4/tcp_tw_recycle: No such file or directory**
 +
 +net.ipv4.tcp_tw_recycle [[https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=4396e46187ca5070219b81773c4e65088dac50cc|был удалён из ядра]] Linux 4.12 в 2017.
 +
 +<hidden>
 +The tcp_tw_recycle was already broken for connections
 +behind NAT, since the per-destination timestamp is not
 +monotonically increasing for multiple machines behind
 +a single destination address.
 +
 +After the randomization of TCP timestamp offsets
 +in commit 8a5bd45f6616 (tcp: randomize tcp timestamp offsets
 +for each connection), the tcp_tw_recycle is broken for all
 +types of connections for the same reason: the timestamps
 +received from a single machine is not monotonically increasing,
 +anymore.
 +
 +Remove tcp_tw_recycle, since it is not functional. Also, remove
 +the PAWSPassive SNMP counter since it is only used for
 +tcp_tw_recycle, and simplify tcp_v4_route_req and tcp_v6_route_req
 +since the strict argument is only set when tcp_tw_recycle is
 +enabled.
 +</hidden>
 +
 +Почитать
 +  * https://www.speedguide.net/articles/linux-tweaking-121
 +  * http://web.archive.org/web/20140616114533/http://performancewiki.com/linux-tuning.html
 +
 +==== TCP_CORK/TCP_NOPUSH и TCP_NODELAY ====
 +
 +Игорь Сысоев / http://sysoev.ru
 +
 +Да, в Линкусе TCP_CORK (tcp_nopush) и TCP_NODELAY взаимоисключающие, но
 +nginx проявляет недюженный интеллект, пытаясь совместить преимущества
 +обеих опций.
 + 
 +"tcp_nopush on" полезно для sendfile(), он в этом случае выводит данные
 +полными пакетами. После того, как весь запрос обработан, TCP_CORK/TCP_NOPUSH
 +выключается, что приводит в сбросу последнего неполного пакета.
 + 
 +"tcp_nodelay on" полезно для keep-alive. nginx включает TCP_NODELAY только
 +по окончании запроса, после которого соединение переходит в состоянии
 +keep-alive. До этого nginx выводит данные вызовами writev() достаточно
 +большими порциями для заполнения пакета ("postpone_output 1460"), поэтому
 +данные должны уходить без задержек и TCP_NODELAY не нужен. А вот с последним
 +неполным пакетом может случится небольшая задержка, если соединение не
 +закрывается. Для этого и нужно включить TCP_NODELAY.
 + 
 +В Линуксе обработка этих двух опций
 +
 +<code> 
 +     tcp_nopush       on;
 +     tcp_nodelay      on;
 +</code>
 +
 +такова:
 + 
 +1) если данные будут выводить комбинацией writev(заголовок)/sendfile(),
 +то проверяется, не было ли уже включен TCP_NODELAY. Если было, то
 +TCP_NODELAY выключается и включается TCP_CORK. По окончании передачи TCP_CORK
 +выключается. Включать TCP_NODELAY не нужно, так как выключание TCP_CORK
 +сбрасывает данные.
 + 
 +2) если при переходе в keep-alive TCP_CORK не была включена, то включается
 +TCP_NODELAY, чтобы сбросить неполный пакет.
 + 
 +Кстати, возможно, для "proxy_buffering off" имеет смысл включать TCP_NODELAY
 +до отдачи ответа.
 +
 +==== Как определить количество рабочих процессов, задаваемых параметром worker_processes? ====
 +
 +via http://www.httpd.kiev.ua/tips/nginx/number-of-worker-processes/
 +
 +Ответ автора nginx Игоря Сысоева:
 +
 +//Если весь сайт помещается в память сервера, к диску обращений нет, и это выделенный сервер для nginx, то 1. Не будет лишних переключений контекста. Если нужно ходить на диск, то 5-10 - это позволит обрабатывать соединения процессами, незаблокироваными на диске.
 +//
 +
 +Кроме этого необходимо понаблюдать за состоянием процессов nginx в работе в часы пик. Командой ps посмотреть состояние рабочих процессов (worker process):
 +
 +<code>
 +# ps ax -o %cpu,vsz,wchan,command | grep "nginx\|PID"
 +
 +%CPU   VSZ WCHAN  COMMAND
 +0,0  1428 pause  nginx: master process /usr/local/nginx/sbin/nginx
 +0,0  2284 -      nginx: worker process (nginx)
 +0,0  2128 kqread nginx: worker process (nginx)
 +</code>
 +
 +Если один из рабочих процессов находится в состоянии ожидания "kqread" в колонке "WCHAN", то значит их количество достаточно. Ну а если уж все они постоянно находятся в этом состоянии, то их количество можно сократить до одного. 
 +
 +И не забывайте контролировать логи ошибок nginx, если количество соединений превысит значение, которое в может обслужить nginx текущим количеством процессов, то в логах это будет соответствующее сообщение. 
 +
 +==== Правильная отдача заголовков при технических работах на сайте ====
 +
 +(via http://www.zagirov.name/correct-return-header-on-service)
 +
 +Есть ситуация: проводятся какие-то технические работы на сайте и нужно сайт правильно закрыть. Это нужно чтобы поисковики знали, что сайт не доступен, а не добавляли страницы в индекс или помечали страницы как удалённые.
 +
 +<code>
 +server {
 +    listen 80 default;
 +    server_name _;
 +    root /var/www/default/www;
 +    charset utf-8;
 +    error_page 404 403 =503 /503.html;
 +    location = /503.html {
 +        add_header Retry-After "Sun, 27 Feb 2011 23:59:59";
 +    }
 +}
 +</code>
 +
 +Строка error_page **404 403 =503 /503.html** означает, что перенаправляем все запросы с ошибками 404 и 403 на файл 503.html, попутно меняя код ответа на 503. И при запросе файла 503.html отдаём заголовок Retry-After, чтобы поисковики знали, когда можно опять запросить страницу. Вместо даты можно указать количество секунд перед следующей попыткой. В файле 503.html можно написать что-нибудь осмысленное для пользователей и даже встроить флэш-игру, чтобы не было скучно.
 +
 +==== Схема frontend-backend ====
 +
 +  * http://blog.korphome.ru/2010/12/31/centos-nginx-%D0%B2-%D0%BA%D0%B0%D1%87%D0%B5%D1%81%D1%82%D0%B2%D0%B5-frontend%D0%B0-%D0%BA-apache/
 +
 +===== Кэширование =====
 +
 +  * [[http://wiki.enchtex.info/practice/nginx/cache|Настройка кеширования в nginx]]
 +  * [[http://debian-help.ru/web-servers/nastroika-keshirovaniya-statiki-s-pomoshyu-nginx-v-debian/|Настройка кэширования статики с помощью nginx в Debian]]
 +  * [[http://habrahabr.ru/post/253121/|Гид по заголовкам кэширования HTTP для начинающих]]
 +  * [[https://angristan.xyz/ghost-nginx-cache/|Caching Ghost with Nginx]]
 +  * [[https://nystudio107.com/blog/static-caching-with-craft-cms|Static Page Caching with Craft CMS]]
 +
 +===== Разное =====
 +
 +  * http://kevin.deldycke.com/2011/09/nginx-php-fpm-mysql-configuration/
 +  * http://kbeezie.com/view/nginx-configuration-examples/
 +  * http://wiki.rsu.edu.ru/index.php/Nginx
 +  * http://tweaked.io/guide/nginx/
 +  * [[http://slonik-v-domene.livejournal.com/141951.html|Apache vs Nginx: Расставим точки над ё.]]
 +  * [[https://www.kinamo.be/en/kb/determining-the-correct-number-of-child-processes-for-php-fpm-on-nginx|Determining the correct number of child processes for PHP-FPM on NGinx]]
 +  * [[https://nls.io/blog/optimize-nginx-and-php-fpm-max_children|Optimize nginx and PHP-FPM (max_children)]]
 +  * [[https://www.getpagespeed.com/server-setup/nginx-try_files-is-evil-too|try_files is evil too]]
 +  * [[https://medium.com/southbridge/nginx-as-reverse-proxy-a62815edd8c1|Nginx как обратный прокси на Docker]]
 +  * [[https://tech.geekjob.ru/nginx-tips-tricks/|Выгружаем конфиг из памяти]]
 +  * [[https://blog.serverdensity.com/troubleshoot-nginx/|Troubleshoot Nginx: 10 typical errors]]
 +  * https://blog.blakeerickson.com/block-referral-spman-nginx
 +  * https://github.com/mitchellkrogza/nginx-ultimate-bad-bot-blocker/blob/master/deny.d/deny.conf
 +  * [[https://github.com/trimstray/nginx-admins-handbook|Nginx Admin's Handbook]]
 +  * [[https://github.com/jukbot/setup-nginx-webserver|Setup a perfect webserver on CentOS/Redhat 7.x guide with understanding]]
 +  * [[https://github.com/kalyabin/kalyabin-ru/wiki/(debian)-Установка-и-настройка-php-fpm|(debian) Установка и настройка php fpm kalyabin-ru]]