Интересная ситуация с Nginx + php-fpm

S
На сайте с 17.11.2010
Offline
73
13234

Установил связку Nginx + php-fpm (через сокеты). Положил простенький файл на сервер (текстовый), сделал тестирование с другого сервера:

ab -n 10000 -c 1000 http://site.ru/text.txt

все отлично: все запросы успешные, скорость большая. Теперь тестирую РНР-файл с кодом:

<?php echo mt_rand();

Данный код выводит случайное число и больше ничего не делает.

ab -n 10000 -c 1000 http://site.ru/text.php

Теперь все плохо: около половины запросов - failed, время тратится иногда много, но в основном, мало на обработку всех запросов.

В логе /var/log/nginx/error.log:

connect() to unix:/var/run/php5-fpm.sock failed (11: Resource temporarily unavailable) while connecting to upstream, client: 1.1.1.1, server: site.ru, request: "GET /2.php HTTP/1.0", upstream: "fastcgi://unix:/var/run/php5-fpm.sock:", host: "site.ru"

Гугл говорит, что нужно увеличить backlog в php-fpm (не помогло) или отказаться от сокетов. Я от них отказался, но ничего не поменялось: также примерно половина запросов отваливается. Лог ошибок Nginx почему-то пустой, хотя раньше была ошибка (не сохранил), типа fpm не отвечает.

Гуглил-гуглил, одни говорят, что это таймауты Nginx, другие что это не таймауты но что именно они не знают. Помогите советом люди добрые.

Отчет ab:



Server Software: nginx
Server Hostname: site.ru
Server Port: 80

Document Path: /test.php
Document Length: 9 bytes

Concurrency Level: 1000
Time taken for tests: 4.577 seconds
Complete requests: 10000
Failed requests: 5807
(Connect: 0, Receive: 0, Length: 5807, Exceptions: 0)
Write errors: 0
Total transferred: 1594846 bytes
HTML transferred: 94846 bytes
Requests per second: 2185.05 [#/sec] (mean)
Time per request: 457.654 [ms] (mean)
Time per request: 0.458 [ms] (mean, across all concurrent requests)
Transfer rate: 340.31 [Kbytes/sec] received

Connection Times (ms)
min mean[+/-sd] median max
Connect: 0 48 25.2 50 122
Processing: 15 249 493.0 76 3339
Waiting: 4 230 496.1 56 3339
Total: 32 297 497.8 127 3418

Percentage of the requests served within a certain time (ms)
50% 127
66% 157
75% 173
80% 208
90% 1088
95% 1136
98% 1834
99% 3103
100% 3418 (longest request)

Nginx.conf

user www-data;

worker_processes 6; (в машине 6 ядер)
timer_resolution 100ms;
worker_rlimit_nofile 8192;
worker_priority -5;

pid /var/run/nginx.pid;

events {
worker_connections 2048;
}

http {
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
types_hash_max_size 2048;
include /etc/nginx/mime.types;
default_type application/octet-stream;
access_log /var/log/nginx/access.log;
error_log /var/log/nginx/error.log;
include /etc/nginx/conf.d/*.conf;
include /etc/nginx/sites-enabled/*;
}


Натсройка Nginx для сайта

server {

server_name site.ru;
listen 1.1.1.1:80;
root /var/www/site.ru;
index index.php;
server_tokens off;
client_max_body_size 100m;
client_body_buffer_size 128k;

location ~* \.php$ {
send_timeout 100s;
proxy_connect_timeout 50s;
proxy_send_timeout 60s;
proxy_read_timeout 60s;
client_body_timeout 60s;
fastcgi_index index.php;
fastcgi_pass 127.0.0.1:8127;
fastcgi_connect_timeout 600s;
fastcgi_send_timeout 300s;
fastcgi_read_timeout 300s;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_param SCRIPT_NAME $fastcgi_script_name;
}
}

www.conf для php-fpm

user = www-data

group = www-data
listen = 127.0.0.1:8127
listen.backlog = 65536
pm = dynamic
pm.max_children = 5
pm.start_servers = 2
pm.min_spare_servers = 1
pm.max_spare_servers = 3
;pm.process_idle_timeout = 10s;
pm.max_requests = 1000
slowlog = /var/log/$pool.log.slow (пусто)
request_slowlog_timeout = 1s
php_admin_value[error_log] = /var/log/fpm/error.log (пусто)

Интересно, если заменяю echo mt_rand(); на echo '123'; то ошибок нет или бывает 1-2 ошибки.

VK
На сайте с 29.12.2011
Offline
42
#1

pm = dynamic

pm.max_children = 50

pm.start_servers = 20

pm.min_spare_servers = 10

pm.max_spare_servers = 20

Поиграйтесь с этими настройками, в зависимости от мощности сервера и требований Ваших скриптов.

S
На сайте с 17.11.2010
Offline
73
#2
V2NEK:
pm = dynamic
pm.max_children = 50
pm.start_servers = 20
pm.min_spare_servers = 10
pm.max_spare_servers = 20

Поиграйтесь с этими настройками, в зависимости от мощности сервера и требований Ваших скриптов.

Поставил:

pm = dynamic  (ставил тут и static)
pm.max_children = 5000 (ставил тут и 50)
pm.start_servers = 20
pm.min_spare_servers = 10
pm.max_spare_servers = 20

Ничего не изменилось, 40-60% запросов в fail, при этом время выполнения всех запросов в ab разное: примерно от 3 до 20 секунд.

Сервер относительно мощный, ресурсов не жалко, главное чтобы не было таких вот проблем.

VK
На сайте с 29.12.2011
Offline
42
#3

shastox, возможно имеет смысл pm.start_servers, min_spare_servers поставить побольше.

5000 children ставить не рекомендую, пока Вы отчетливо не понимаете что делаете.

Читайте документацию на тему настройки системы под Ваши требования, либо обратитесь к тем, кто уже прочитал эту документацию (отдельный форум с отзывами чуть ниже этого)

J
На сайте с 20.02.2014
Offline
120
jkm
#4


<?php echo mt_rand();

С таким кодом длина ответа будет переменная и утилита ab всегда покажет ошибки.


Failed requests: 5807
(Connect: 0, Receive: 0, Length: 5807, Exceptions: 0)

Следует делать постоянное число знаков


<?php echo mt_rand(100000, 999999);
S
На сайте с 17.11.2010
Offline
73
#5

2 jmk

Спасибо! Вы абсолютно правы! Вчера понял, что дело в mt_rand();, но не понимал, почему именно.

P
На сайте с 08.03.2007
Offline
250
#6
jkm:

<?php echo mt_rand();

С таким кодом длина ответа будет переменная и утилита ab всегда покажет ошибки.

Failed requests: 5807
(Connect: 0, Receive: 0, Length: 5807, Exceptions: 0)


Следует делать постоянное число знаков

<?php echo mt_rand(100000, 999999);

ab не боится переменной длины. И это не объясняет, почему nginx пишет в логи "Resource temporarily unavailable".

C
На сайте с 06.10.2009
Offline
69
#7
Pilat:
ab не боится переменной длины. И это не объясняет, почему nginx пишет в логи "Resource temporarily unavailable".

Тут еще стоит проверить и увеличить sysctl net.core.netdev_max_backlog, оно почти везде по дефолту 1000. Можно поднять до 2000. Думаю, что этот лимит на уровне программы и отдельных сокетов не регулируется.

H
На сайте с 03.02.2010
Offline
115
#8

Попробуйте покрутить конфиг сетевого стека ОС

sysctl net.core.***

"Тролль: Прочитал, обосрал, в бан. Прочитал, обосрал, в бан. Романтика." (с)
Andreyka
На сайте с 19.02.2005
Offline
822
#9

Сервер при недостатке ресурсов может работать в двух режимах:

1) Быстро обработать часть запросов

2) Медленно обрабатывать все запросы

По умолчанию идет первый вариант

Не стоит плодить сущности без необходимости

Авторизуйтесь или зарегистрируйтесь, чтобы оставить комментарий