Дек 09
2008Тесты: Apache vs. php-fpm
Рубрики: (nginx, php, Апаче (не вертолет)) Автор: polkila 09 Дек 2008
Теги : apache, nginx, php-fpm, статистика
Что имеем: FreeBSD 7.0-STABLE на машине Duron 600MHz с памятью 512Mb (заяц). Такая слабая машина выбрана умышленно, чтобы тесты проходили заметнее, а VPS, кстати, предоставляют с похожей конфигурацией. Сеть 100Mb или даже 10Mb, не помню, да и не важно — максимальная нагрузка не превышала 700 Kbit/s.
Нагрузку создаем утилитой ApacheBench. Предварительно выключаем на волке фаервол/антивирус через msconf и перезагружаем, чтобы никто не ограничивал траффик и коннекты, а эти добрые молодцы, как выяснилось на практике, еще напрягаются сами, даже когда все прозрачно и запреты сняты.
Итак, прежде всего замечу, что конфигурация nginx (1 w., 512 c.) не влияла на результаты тестов. Увеличение количества воркеров или коннектов не давало прироста производительности. Это говорит, что nginx имеет подходящую настройку под конфигурацию машины. (Есть другое мнение, почему worker_connections нужно выставлять очень большим.) Касательно модулей, установлены были только необходимые, ничего лишнего.
PHP-скрипт выбран с таким расчетом, чтобы повторить работу какого-нибудь движка (за вычетом запросов в базу MySQL, их исключаем, чтобы не испортить результаты тестов). В индексе инклудим 5-6 классов, разбираем путь (/module/test) и инклудим еще один скрипт.
В первой схеме имеем nginx, настроенный в качестве реверс-прокси, и Apache20 + mod_php. Наверное, вы спросите, зачем здесь нужен nginx, ведь тестируем только производительность Apache20? Затем он и нужен, что в боевых условиях наш заяц будет работать только с nginx, без него при первом же скачке посещаемости Apache подавится количеством соединений и, подыхая, задушит MySQL, захватив память своими беспощадными воркерами. Здесь будет задействован mod_rewrite с одним-двумя правилами:
RewriteRule ^images/ - [NC,L]
RewriteRule .* index.php [NC,QSA]
Во второй схеме заменяем Apache20 на php-fpm. Настраиваем соединение между ним и nginx через сокет. Тут еще проще — не потребуется даже rewrite:
# Main location
location / {
fastcgi_pass unix:/tmp/php-fpm.sock;
fastcgi_param SCRIPT_FILENAME /home/test.dev/www/site1/public_html/index.php;
include fastcgi_params;
}
# Static
location ~* ^.+\.(ico|gif|jpe?g|png|bmp|swf|css|js|html|xml|txt|doc|rtf|xls|pdf|tar|zip|t?gz|bz2|rar)$ {
if ($request_uri ~* "\?[0-9]+$"){
expires max;
}
root /usr/home/test.dev/www/site1/public_html;
}
location ~ /\.ht {
deny all;
}
(Это не значит, что не нужно включать модуль rewrite, он всегда пригодится, к тому же директива if тоже обрабатывается им.)
blue — apache efficiency (requests per second)
green — php-fpm efficiency (requests per second)
Test #1: 3 workers, eAccelerator is off
| req\con | 1 | 2 | 3 | 4 | 5 | 10 | 25 | 50 |
|---|---|---|---|---|---|---|---|---|
| 1000 | 18.82 19.72 |
18.44 19.77 |
18.52 19.85 |
18.87 19.83 |
18.72 19.78 |
18.88 19.81 |
18.82 19.82 |
18.87 19.85 |
| 5000 | 18.61 19.14 |
18.87 19.80 |
18.82 19.86 |
18.87 19.87 |
18.83 19.84 |
18.85 19.85 |
18.85 19.93 |
18.86 19.91 |
| 10000 | 18.63 19.80 |
18.87 19.83 |
18.84 19.89 |
18.90 19.85 |
18.92 19.82 |
18.91 19.82 |
18.92 19.86 |
18.92 19.87 |
Test #2: 5 workers, eAccelerator is off
| req\con | 1 | 2 | 3 | 4 | 5 | 10 | 25 | 50 |
|---|---|---|---|---|---|---|---|---|
| 1000 | 18.68 19.55 |
18.86 19.88 |
18.40 19.79 |
18.76 19.88 |
18.74 19.86 |
18.76 19.83 |
18.81 19.83 |
18.73 19.80 |
| 5000 | 18.77 19.76 |
18.82 19.83 |
18.82 19.81 |
15.21 19.83 |
17.96 19.83 |
18.86 19.85 |
18.85 19.85 |
18.88 19.82 |
| 10000 | 18.85 19.74 |
18.90 19.84 |
18.84 19.84 |
18.80 19.81 |
18.82 19.82 |
18.85 19.82 |
18.84 19.81 |
18.84 19.79 |
Test #3: 3 workers, eAccelerator is on
| req\con | 1 | 2 | 3 | 4 | 5 | 10 | 25 | 50 |
|---|---|---|---|---|---|---|---|---|
| 1000 | 107.02 125.74 |
94.96 130.61 |
109.97 131.42 |
100.00 131.69 |
115.11 133.06 |
112.87 130.08 |
98.92 130.88 |
112.48 130.35 |
| 5000 | 106.45 123.27 |
111.42 129.87 |
113.88 133.84 |
114.41 133.84 |
113.43 134.12 |
113.56 129.45 |
112.01 130.67 |
112.01 131.52 |
| 10000 | 101.67 123.53 |
112.91 131.42 |
112.38 134.14 |
114.76 135.65 |
114.06 135.28 |
114.35 133.70 |
112.66 133.14 |
112.30 132.48 |
Test #4: 5 workers, eAccelerator is on
| req\con | 1 | 2 | 3 | 4 | 5 | 10 | 25 | 50 |
|---|---|---|---|---|---|---|---|---|
| 1000 | 103.73 122.14 |
112.28 133.61 |
103.23 131.96 |
113.07 135.02 |
113.07 133.61 |
114.49 131.96 |
112.87 137.63 |
112.28 132.51 |
| 5000 | 101.91 119.67 |
111.19 132.67 |
112.60 135.54 |
113.15 138.17 |
112.72 137.87 |
115.94 137.52 |
113.48 135.88 |
114.08 138.29 |
| 10000 | 104.03 119.74 |
111.85 131.71 |
112.50 136.08 |
114.41 137.93 |
113.80 138.92 |
115.57 138.80 |
112.42 137.46 |
112.52 137.87 |
Из выводов:
- преимущество php-fpm очевидно. Всегда раздражал громоздкий Apache, теперь есть стимул от него избавиться.
- в php-fpm увеличение количества воркеров с 10-и до 20-и уменьшало количество невыполненных запросов в среднем с 80-и до 2-х, но не увеличивало произодительность из-за нехватки мощности процессора. Во время выполнения любого из тестов idle зайца был около 0%.
Кому интересно посмотреть подробные логи о необработанных запросах, времени выполнения тестов и пр. — пожалуйста.
Всея ПЫХА
adw0rd
Мавр
ГО
Irinax