php-fpm with apache

最後更新: 2019-01-25

介紹

 

PHP-FPM (FastCGI Process Manager)

https://php-fpm.org/

 

PHP-FPM 的改進

定制

ability to start workers with different uid/gid/chroot/environment, listening on different ports and using different php.ini

(no more messing around with suphp or suexec - or, indeed, mod_php. )

"slowlog" - logging scripts

not just their names, but their PHP backtraces too,

using ptrace and similar things to read remote process' execute_data) that are executed unusually slow;

目錄

  • Apache 2.2 Config
  • Apache 2.4 Config
  • Install
  • Number of socket limit
  • php-fpm config
  • php getallheaders() function
  • ius package
  • Check php-fpm Status (By cli - fcgi)
  • Enable slowlog
  • opcache

 


Apache 2.2 Config

 

vhosts.conf

<VirtualHost *:80>
    Servername example.com
    DirectoryIndex index.php

    SuexecUserGroup someuser someuser

    AddHandler fcgid-script .php
    FcgidWrapper /var/www/fcgi-bin/someuser/php.fcgi .php

    <Directory /home/someuser/public_html/>
        Options +ExecCGI
    </Directory>
</VirtualHost>

mkdir /var/www/fcgi-bin/

mkdir /var/www/fcgi-bin/someuser/

chown -R someuser:someuser /var/www/fcgi-bin/someuser/

chmod a+x /var/www/fcgi-bin/someuser/php.fcgi

File: /var/www/fcgi-bin/someuser/php.fcgi

#!/bin/bash
exec /usr/bin/php-cgi

 


Apache 2.4 Config

 

用 proxy module 去 connect php-fpm

Centos 7

/etc/httpd/conf.modules.d/00-proxy.conf

LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_fcgi_module modules/mod_proxy_fcgi.so

* mod_proxy_fcgi now supports unix sockets since 2.4.9

Test:

apachectl -M | grep proxy

 proxy_module (shared)
 proxy_fcgi_module (shared)

vhosts.conf

SetHandler

...
<Directory /var/www/datahunter.org/web>
    # Proxy via handler
    <FilesMatch ".+\.php$">
        SetHandler application/x-httpd-php
        SetHandler "proxy:fcgi://127.0.0.1:9000"
    </FilesMatch>
    ...
</Directory>
...

OR

ProxyPassMatch

ProxyPassMatch ^/(.*\.php[345]?(/.*)?)$ fcgi://127.0.0.1:9000/var/www/clients/client3/web4/web/$1

Notes:

如無必要, 勿包住它

<IfModule mod_proxy_fcgi.c>
    ...
</IfModule>

 

當 php-fpm 死了時, Browser 會見到

503 - Service Unavailable

 


Install php-fpm

 

# -v Version number

/opt/php70/sbin/php-fpm -v

PHP 7.0.27 (fpm-fcgi) (built: Jan 25 2018 17:29:45)
Copyright (c) 1997-2017 The PHP Group
Zend Engine v3.0.0, Copyright (c) 1998-2017 Zend Technologies

# -i PHP information

/opt/php70/sbin/php-fpm -i

phpinfo()
PHP Version => 7.0.27

System => Linux vm.laddermission.hk 3.10.0-693.2.2.el7.x86_64 #1 SMP Tue Sep 12 22:26:13 UTC 2017 x86_64
Build Date => Jan 25 2018 17:27:39
Configure Command =>  './configure'

...

# -m how compiled in modules

[PHP Modules]
bcmath
bz2
calendar
cgi-fcgi
Core
...

# Debug

/opt/php70/sbin/php-fpm -t

[26-Jan-2018 10:52:13] NOTICE: configuration file /opt/php70/etc/php-fpm.conf test is successful

-F, --nodaemonize                   force to stay in foreground

# start it manually with

php-fpm -y /path/to/php-fpm.conf -c /path/to/custom/php.ini

 

 


Number of socket limit

 

php-fpm using too many sockets will cause apache to give a "Cannot assign requested address: error."

This means your operating system is not allowing new sockets to be created.

 


php-fpm config

 

/opt/php70/etc/php-fpm.conf

...
include=/opt/php70/etc/php-fpm.d/*.conf

# Default Pool File

/opt/php70/etc/php-fpm.d/www.conf

; pool name ('www' here)
[www]

; Per pool prefix
; It only applies on the following directives:
; 'access.log' 'slowlog' 'listen' (unixsocket) 'chroot' 'chdir' 'php_values' 'php_admin_values'
; Note: This directive can also be relative to the global prefix.
; $pool Folder 要建立好
prefix = var/run/pools/$pool

user = apache
group = apache

;listen = 127.0.0.1:9000
;listen.allowed_clients = 127.0.0.1

listen = $pool
listen.owner = apache
listen.group = apache
listen.mode = 0660

; static  - a fixed number (pm.max_children) of child processes;
; dynamic - pm.max_children, pm.start_servers, pm.min_spare_servers, pm.max_spare_servers
pm = dynamic

pm.max_requests = 500

; ulimit -n
; ulimit -u
rlimit_files = 1024
rlimit_core = 0

; Redirect worker stdout and stderr into main error log.
; Note: on highloaded environement, this can cause some delay in the page
; Default Value: no
;catch_workers_output = yes


; Limits the extensions of the main script FPM will allow to parse.
; Default Value: .php
security.limit_extensions = .php

; php ini setting
php_admin_value[sendmail_path] = /usr/sbin/sendmail -t -i -f www@mydomain
php_flag[display_errors] = off
php_admin_value[error_log] = /var/log/fpm-php.www.log
php_admin_flag[log_errors] = on
php_admin_value[memory_limit] = 256M
php_admin_value[short_open_tag] = on
php_admin_value[max_execution_time] = 120

# upload
php_admin_value[upload_max_filesize] = 10M
php_admin_value[post_max_size]       = 20M

# 重啟 php-fpm script

/root/scripts/restart-php-fpm

#!/bin/bash

killall php-fpm
sleep 3
killall -9 php-fpm
/opt/php70/sbin/php-fpm

迷你設定檔 web4.conf  

[web4]

listen = 127.0.0.1:9013
listen.allowed_clients = 127.0.0.1

user = web4
group = client3

pm = dynamic
pm.max_children = 8
pm.start_servers = 2
pm.min_spare_servers = 2
pm.max_spare_servers = 5
pm.max_requests = 0

chdir = /

 


php getallheaders() function

 

php-fpm 沒有 getallheaders function, 所以我地要人手加上去

index.php

require_once(__DIR__."/function/function.php");

function/function.php

<?

if (!function_exists('getallheaders')) {
    function getallheaders() {
    $headers = [];
    foreach ($_SERVER as $name => $value) {
        if (substr($name, 0, 5) == 'HTTP_') {
            $headers[str_replace(' ', '-', ucwords(strtolower(str_replace('_', ' ', substr($name, 5)))))] = $value;
        }
    }
    return $headers;
    }
}

?>

 


ius package

 

yum list | grep php70u-fpm

php70u-fpm.x86_64                        7.0.26-1.ius.el7               ius

rpm -ql php-fpm

/etc/php-fpm.conf
/etc/php-fpm.d/www.conf

 


remi Package

 

/opt/remi/php56/root/etc/php-fpm.d

 


Check php-fpm Status (By cli - fcgi)

 

Tools: cgi-fcgi (CLI)

# epel

yum install fcgi

fcgi 說明

ping/pong

www.conf

# Default 沒有此設定, 所以訪問 /ping 沒有 pong 回應
ping.path = /ping
ping.response = pong

Test

port=9000
SCRIPT_NAME=/ping SCRIPT_FILENAME=/ping REQUEST_METHOD=GET \
cgi-fcgi -bind -connect 127.0.0.1:$port

Output

Content-type: text/plain;charset=UTF-8
Expires: Thu, 01 Jan 1970 00:00:00 GMT
Cache-Control: no-cache, no-store, must-revalidate, max-age=0

pong

Short / Full Status

www.conf

; Default Value: not set
pm.status_path = /status

Short status

Full status

Exampe

short

SCRIPT_NAME=/status SCRIPT_FILENAME=/status REQUEST_METHOD=GET \
cgi-fcgi -bind -connect 127.0.0.1:9000

full

SCRIPT_NAME=/status SCRIPT_FILENAME=/status QUERY_STRING=full REQUEST_METHOD=GET \
cgi-fcgi -bind -connect 127.0.0.1:9000

Output

pool:                 www
process manager:      dynamic
start time:           26/Jan/2018:15:43:14 +0800
start since:          39
accepted conn:        1
listen queue:         0
max listen queue:     0
listen queue len:     128
idle processes:       1
active processes:     1
total processes:      2
max active processes: 1
max children reached: 0
slow requests:        0

說明

listen queue

the number of request in the queue of pending connections (see backlog in listen(2));

max listen queue

the maximum number of requests in the queue of pending connections since FPM has started;

 


Proxy Timout

 

Log

[..] [proxy_fcgi:error] [pid 29806] (70007)The timeout specified has expired:
  [client r.r.r.r:p] AH01075: Error dispatching request to :

Fix

<Proxy "fcgi://127.0.0.1:9000">
   ProxySet timeout=180
</Proxy>

<FilesMatch ".+\.php$">
        SetHandler application/x-httpd-php
        SetHandler "proxy:fcgi://127.0.0.1:9000"
</FilesMatch>

 


Enable slowlog

 

www.conf

slowlog = log/$pool.log.slow
request_slowlog_timeout = 10

 


opcache

 

沒有 opcache 時, php-fpm 會有大量 RAED

Total DISK READ :      10.98 M/s | Total DISK WRITE :     149.32 K/s
Actual DISK READ:      10.73 M/s | Actual DISK WRITE:       4.97 M/s
  TID  PRIO  USER     DISK READ  DISK WRITE  SWAPIN     IO>    COMMAND
  989 be/4 web4     1799.66 K/s    0.00 B/s  0.14 % 80.91 % php-fpm: pool web4
  517 be/4 web4      624.77 K/s    0.00 B/s  0.00 % 76.37 % php-fpm: pool web4
 1119 be/4 web4      895.90 K/s    0.00 B/s  0.49 % 76.22 % php-fpm: pool web4
  526 be/4 web4      919.48 K/s    0.00 B/s  2.63 % 74.94 % php-fpm: pool web4
 1134 be/4 web4     1296.70 K/s    0.00 B/s  2.02 % 74.94 % php-fpm: pool web4
 1194 be/4 web4      546.19 K/s    0.00 B/s  0.10 % 74.05 % php-fpm: pool web4
  475 be/4 web4     1807.52 K/s    0.00 B/s  4.82 % 73.06 % php-fpm: pool web4
 1227 be/4 web4      609.06 K/s    0.00 B/s  0.60 % 72.82 % php-fpm: pool web4
  464 be/4 web4     1583.55 K/s    0.00 B/s  5.14 % 72.37 % php-fpm: pool web4
 1144 be/4 web4     1159.17 K/s    0.00 B/s  4.43 % 70.42 % php-fpm: pool web4

Install

yum install php70-php-opcache

vim /etc/opt/remi/php70/php.d/10-opcache.ini

service php70-php-fpm restart

 


Doc

 

 

 

Creative Commons license icon Creative Commons license icon