You are currently viewing Openresty + php-fpm 安裝及設定

Openresty + php-fpm 安裝及設定

一、 簡介

在開始介紹如何安裝前,先介紹一下什麼是 Openresty。

OpenResty® 是一個基於 Nginx 與 Lua 的高性能 Web 平台,其內部集成了大量精良的 Lua 庫、第三方模塊以及大多數的依賴項。用於方便地搭建能夠處理超高並發、擴展性極高的動態 Web 應用、Web 服務和動態閘道 ( gateway )。

簡單來說就是在 Nginx 上匯集了方便進行開發的 LUA。因此可以使用 LUA 語言針對 Nginx 開發一些而外的特殊功能。

本篇介紹的就是 Openresty with http2 & brotli + PHP-FPM 的編譯安裝以及設定方式。

※ PS : PHP 的部分請參考 Apache + PHP 編譯安裝及設定 中針對 PHP 來進行編譯參數並多加上 –enable-fpm 來進行安裝


二、Openresty 編譯安裝

先安裝編譯的相依性需求 :

yum install zlib zlib-devel libuuid-devel unzip git pcre-devel -y
yum groupinstall "development tools"

下載 openssl : https://www.openssl.org/source/

cd /usr/local/src
wget https://www.openssl.org/source/openssl-1.0.2o.tar.gz
tar zxvf openssl-1.0.2o.tar.gz

下載 Openresty : https://openresty.org/cn/download.html

cd /usr/local/src
wget https://openresty.org/download/openresty-1.13.6.2.tar.gz
tar zxvf openresty-1.13.6.2.tar.gz

下載 brotli : https://github.com/google/ngx_brotli.git

git clone https://github.com/google/ngx_brotli.git
cd ngx_brotli
git submodule update --init --recursive

開始編譯安裝 :

cd /usr/local/src/openresty-1.13.6.2
./configure --prefix=/usr/local/openresty \
            --user=nobody --group=nobody \
            --with-http_secure_link_module \
            --with-http_stub_status_module \
            --with-http_realip_module \
            --with-ipv6 \
            --with-http_ssl_module \
            --with-openssl=../openssl-1.0.2o \
            --with-http_v2_module \
            --with-http_secure_link_module \
            --with-http_mp4_module \
            --with-http_flv_module \
            --with-http_gzip_static_module \
            --add-module=/usr/local/src/ngx_brotli
gmake & gmake install

三、設定

Openresty 設定 :

user  nobody;
worker_processes  2;
# 更改worker進程的最大打開文件數限制。如果沒設置的話,這個值為操作系統的限制。
worker_rlimit_nofile 16384;

#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

pid /usr/local/openresty/nginx/logs/nginx.pid;

events {
    # 設置可由一個worker進程同時打開的最大連接數。如果設置了上面提到的worker_rlimit_nofile,我們可以將這個值設得很高。
    worker_connections   5000;
    # epoll 用在 Linux 上, kqueue 用在 bsd 上
    use epoll;
}

http {
    # 關閉在錯誤頁面中的 nginx 版本
    server_tokens off;
    include       mime.types;
    default_type  application/octet-stream;
    # 設置用戶端請求正文的最大允許大小
    client_max_body_size    128m;
    # 設置請求 header 和請求 body (各自)的逾時時間
    client_body_timeout    300;
    client_header_timeout 300;
    #access_log  logs/access.log  main;
    access_log off;

    log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                      '$status $body_bytes_sent "$http_referer" '
                      '"$http_user_agent" "$http_x_forwarded_for"';

    # 可以在磁盤和 TCP socket 之間互相拷貝數據
    #sendfile        on;
    #tcp_nopush     on;
    pagespeed unplugged;

    keepalive_timeout  65;

    brotli on;
    brotli_static on;
    brotli_min_length    1;
    brotli_buffers    16 8k;
    brotli_comp_level 4;
    brotli_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript application/javascript application/vnd.ms-fontobject application/x-font-ttf font/opentype image/svg+xml image/x-icon application/x-httpd-fastphp application/x-httpd-php ;

    # gzip 設定
    # 使用 gzip 壓縮的形式發送數據。這將會減少我們發送的數據量。
    gzip  on;
    # 設置對數據啟用壓縮的最少字節數
    gzip_min_length    384;
    # 設置數據的壓縮等級。這個等級可以是1-9之間的任意數值,9是最慢但是壓縮比最大的。我們設置為4,這是一個比較折中的設置。
    gzip_comp_level    4;
    # 和 http header 有關系,加個 vary header,給代理服務器用的
    gzip_vary on;
    # 為指定的客戶端禁用 gzip 功能。我們設置成IE6或者更低版本以使我們的方案能夠廣泛兼容
    gzip_disable "MSIE [1-6]\.";
    # Nginx作為反向代理的時候啟用,開啟或者關閉後端服務器返回的結果,匹配的前提是後端服務器必須要返回包含"Via"的 header頭。
    gzip_proxied any;
    # 識別 http 的協議版本 (1.0/1.1)
    gzip_http_version 1.1;
    # 設置系統獲取幾個單位的緩存用於存儲gzip的壓縮結果數據流。 例如 4 4k 代表以4k為單位,按照原始數據大小以4k為單位的4倍申請內存。
    # 如果沒有設置,默認值是申請跟原始數據相同大小的內存空間去存儲gzip壓縮結果。
    gzip_buffers  16 8k;
    # 設置需要壓縮的數據格式
    gzip_types text/plain text/css application/json application/x-javascript text/xml application/xml application/xml+rss text/javascript application/javascript application/vnd.ms-fontobject application/x-font-ttf font/opentype image/svg+xml image/x-icon application/x-httpd-fastphp application/x-httpd-php ;

    # 以下是 file cache 設定,如使用 nginx 作為代理伺服器請勿使用此設定
    # 指定快取最大數目,以及快取的時間。
    #open_file_cache max=100000 inactive=60s;
    # 指定檢測的間隔時間
    #open_file_cache_valid 30s;
    # 設置由 open_file_cache 指令的非活動參數配置的期間內的最小檔訪問數
    #open_file_cache_min_uses 2;
    # 是否快取錯誤訊息
    #open_file_cache_errors on;

    # 代理伺服器設定
    # 定義從代理伺服器讀取回應(reading a response)的逾時時間 ?
    proxy_read_timeout 150;
    # 定義與代理伺服器建立連接的逾時時間 ?
    proxy_connect_timeout  150;
    # 設置用於從代理伺服器讀取回應的緩衝區的數目和大小
    proxy_buffers  32 32k;
    # 設置用於讀取從代理伺服器接收第一部分回應的緩衝區大小。此部分通常包含一個小的 response header。
    proxy_buffer_size  128k;
    proxy_busy_buffers_size  128k;
    # 允許對傳遞給代理伺服器的 request header 重新定義或追加欄位。
    proxy_set_header Host $host;
    proxy_set_header   X-Forwarded-For $remote_addr;

    server {
        listen       80;
        server_name    nginx.beck.idv.tw;
        charset    UTF-8;
        access_log  /home/wordpress/tmp/$host.access.log  main;
        root    /home/wordpress/public_html/;
        index  index.html index.htm index.php;

        location / {
    root    /home/wordpress/public_html/;
        index  index.html index.htm index.php;
        }

        location ~ \.php$ {
            fastcgi_pass    unix:/home/wordpress/tmp/wordpress.sock;
            fastcgi_index    index.php;
            include    fastcgi.conf;
            fastcgi_buffer_size    128k;
            fastcgi_buffers    256 16k;
            client_body_buffer_size 4096k;
        }

        # redirect server error pages to the static page /50x.html
        error_page   500 502 503 504  /50x.html;
        location = /50x.html {
            root   html;
        }
    }

    server {
        listen 443 ssl http2;
        server_name $host;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $remote_addr;
        ssl on;
        ssl_certificate /usr/local/openresty/nginx/ssl/nginx.beck.idv.tw.crt;
        ssl_certificate_key /usr/local/openresty/nginx/ssl/nginx.beck.idv.tw.key;
        ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
        ssl_ciphers "ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA256:ECDHE-RSA-AES256-SHA:ECDHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES128-SHA256:DHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES256-GCM-SHA384:AES128-GCM-SHA256:AES256-SHA256:AES128-SHA256:AES256-SHA:AES128-SHA:DES-CBC3-SHA:HIGH:!aNULL:!eNULL:!EXPORT:!DES:!MD5:!PSK:!RC4";
    ssl_session_cache shared:SSL:10m;
        ssl_prefer_server_ciphers on;
        ssl_dhparam /usr/local/openresty/nginx/ssl/dhparams.pem;

        access_log  /home/wordpress/tmp/$host.access.log  main;

        location / {
                proxy_pass https://$server_addr:28443;
        }

        # redirect server error pages to the static page /50x.html
        error_page   500 502 503 504  /50x.html;
        location = /50x.html {
            root   html;
        }
    }
}

變更 nginx fastcgi script 設定檔 :

fastcgi_param  QUERY_STRING       $query_string;
fastcgi_param  REQUEST_METHOD     $request_method;
fastcgi_param  CONTENT_TYPE       $content_type;
fastcgi_param  CONTENT_LENGTH     $content_length;

fastcgi_param  SCRIPT_NAME        $fastcgi_script_name;
fastcgi_param  REQUEST_URI        $request_uri;
fastcgi_param  DOCUMENT_URI       $document_uri;
fastcgi_param  DOCUMENT_ROOT      $document_root;
fastcgi_param  SCRIPT_FILENAME    $document_root$fastcgi_script_name;
fastcgi_param  SERVER_PROTOCOL    $server_protocol;
fastcgi_param  PATH_INFO          $fastcgi_script_name;
fastcgi_param  HTTPS              $https if_not_empty;

fastcgi_param  GATEWAY_INTERFACE  CGI/1.1;
fastcgi_param  SERVER_SOFTWARE    nginx/$nginx_version;

fastcgi_param  REMOTE_ADDR        $remote_addr;
fastcgi_param  REMOTE_PORT        $remote_port;
fastcgi_param  SERVER_ADDR        $server_addr;
fastcgi_param  SERVER_PORT        $server_port;
fastcgi_param  SERVER_NAME        $server_name;

# PHP only, required if PHP was built with --enable-force-cgi-redirect
fastcgi_param  REDIRECT_STATUS    200;

php-fpm pool 設定 :

; Start a new pool named 'www'.
; the variable $pool can be used in any directive and will be replaced by the
; pool name ('www' here)
[wordpress]

; 啟動進程的用戶和用戶組,如果沒有設置,則默認用戶的組被使用。
user = wordpress
group = wordpress

; fpm 監聽端口,即 nginx 中 php 處理的地址,一般默認值即可。
; 可用格式為: 'ip:port', 'port', '/path/to/unix/socket'. 每個進程池都需要設置。
listen = '/home/wordpress/tmp/wordpress.sock'

; 允許訪問此 FastCGI 進程的用戶
listen.owner = nobody
listen.group = nobody
listen.mode = 0660

; Choose how the process manager will control the number of child processes.
; Possible Values:
;   static  - a fixed number (pm.max_children) of child processes;
;   dynamic - the number of child processes are set dynamically based on the
;             following directives. With this process management, there will be
;             always at least 1 children.
;             pm.max_children      - the maximum number of children that can
;                                    be alive at the same time.
;             pm.start_servers     - the number of children created on startup.
;             pm.min_spare_servers - the minimum number of children in 'idle'
;                                    state (waiting to process). If the number
;                                    of 'idle' processes is less than this
;                                    number then some children will be created.
;             pm.max_spare_servers - the maximum number of children in 'idle'
;                                    state (waiting to process). If the number
;                                    of 'idle' processes is greater than this
;                                    number then some children will be killed.
;  ondemand - no children are created at startup. Children will be forked when
;             new requests will connect. The following parameter are used:
;             pm.max_children           - the maximum number of children that
;                                         can be alive at the same time.
;             pm.process_idle_timeout   - The number of seconds after which
;                                         an idle process will be killed.
; Note: This value is mandatory.
pm = dynamic

; 子進程最大數
pm.max_children = 50
; 啟動時的進程數,默認值為: min_spare_servers + (max_spare_servers - min_spare_servers) / 2
pm.start_servers = 5
; 保證空閑進程數最小值,如果空閑進程小於此值,則創建新的子進程
pm.min_spare_servers = 5
; 保證空閑進程數最大值,如果空閑進程大於此值,此進行清理
pm.max_spare_servers = 20

pm.process_idle_timeout = 300s;

# 設置每個子進程重生之前服務的請求數。
;pm.max_requests = 5000

# FPM狀態頁面的網址。
pm.status_path = /status
# FPM 監控頁面的 ping 網址。
ping.path = /ping

; Default: not set
;access.log = log/$pool.access.log

; The access log format.
; The following syntax is allowed
;  %%: the '%' character
;  %C: %CPU used by the request
;      it can accept the following format:
;      - %{user}C for user CPU only
;      - %{system}C for system CPU only
;      - %{total}C  for user + system CPU (default)
;  %d: time taken to serve the request
;      it can accept the following format:
;      - %{seconds}d (default)
;      - %{miliseconds}d
;      - %{mili}d
;      - %{microseconds}d
;      - %{micro}d
;  %e: an environment variable (same as $_ENV or $_SERVER)
;      it must be associated with embraces to specify the name of the env
;      variable. Some exemples:
;      - server specifics like: %{REQUEST_METHOD}e or %{SERVER_PROTOCOL}e
;      - HTTP headers like: %{HTTP_HOST}e or %{HTTP_USER_AGENT}e
;  %f: script filename
;  %l: content-length of the request (for POST request only)
;  %m: request method
;  %M: peak of memory allocated by PHP
;      it can accept the following format:
;      - %{bytes}M (default)
;      - %{kilobytes}M
;      - %{kilo}M
;      - %{megabytes}M
;      - %{mega}M
;  %n: pool name
;  %o: output header
;      it must be associated with embraces to specify the name of the header:
;      - %{Content-Type}o
;      - %{X-Powered-By}o
;      - %{Transfert-Encoding}o
;      - ....
;  %p: PID of the child that serviced the request
;  %P: PID of the parent of the child that serviced the request
;  %q: the query string
;  %Q: the '?' character if query string exists
;  %r: the request URI (without the query string, see %q and %Q)
;  %R: remote IP address
;  %s: status (response code)
;  %t: server time the request was received
;      it can accept a strftime(3) format:
;      %d/%b/%Y:%H:%M:%S %z (default)
;      The strftime(3) format must be encapsuled in a %{<strftime_format>}t tag
;      e.g. for a ISO8601 formatted timestring, use: %{%Y-%m-%dT%H:%M:%S%z}t
;  %T: time the log has been written (the request has finished)
;      it can accept a strftime(3) format:
;      %d/%b/%Y:%H:%M:%S %z (default)
;      The strftime(3) format must be encapsuled in a %{<strftime_format>}t tag
;      e.g. for a ISO8601 formatted timestring, use: %{%Y-%m-%dT%H:%M:%S%z}t
;  %u: remote user
;
; Default: "%R - %u %t \"%m %r\" %s"
access.format = "%R - %u %t \"%m %r%Q%q\" %s %f %{mili}d %{kilo}M %C%%"
slowlog = log/$pool.log.slow

; The timeout for serving a single request after which a PHP backtrace will be
; dumped to the 'slowlog' file. A value of '0s' means 'off'.
; Available units: s(econds)(default), m(inutes), h(ours), or d(ays)
; Default Value: 0
;request_slowlog_timeout = 0

; The timeout for serving a single request after which the worker process will
; be killed. This option should be used when the 'max_execution_time' ini option
; does not stop script execution for some reason. A value of '0' means 'off'.
; Available units: s(econds)(default), m(inutes), h(ours), or d(ays)
; Default Value: 0
;request_terminate_timeout = 0

; Set open file descriptor rlimit.
; Default Value: system defined value
;rlimit_files = 1024

; Set max core size rlimit.
; Possible Values: 'unlimited' or an integer greater or equal to 0
; Default Value: system defined value
;rlimit_core = 0

; 啟動時的 Chroot 目錄,所定義的目錄需要是絕對路徑。
;chroot =

; Chdir to this directory at the start.
; Note: relative path can be used.
; Default Value: current directory or / when chroot
;chdir = /var/www

;php_admin_value[sendmail_path] = /usr/sbin/sendmail -t -i -f [email protected]
;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] = 32M

四、新增服務設定檔

Openresty 服務設定檔 :

vi /usr/lib/systemd/system/openresty.service

[Unit]
Description=openresty-nginx - high performance web application server
Documentation=http://openresty.org
After=network.target remote-fs.target nss-lookup.target

[Service]
Type=forking
PIDFile=/usr/local/openresty/nginx/logs/nginx.pid
ExecStartPre=/usr/local/openresty/nginx/sbin/nginx -t -c /usr/local/openresty/nginx/conf/nginx.conf
ExecStart=/usr/local/openresty/nginx/sbin/nginx -c /usr/local/openresty/nginx/conf/nginx.conf
ExecReload=/bin/kill -s HUP $MAINPID
ExecStop=/bin/kill -s QUIT $MAINPID
PrivateTmp=true

[Install]
WantedBy=multi-user.target

php-fpm 系統啟動檔 :

vi /usr/lib/systemd/system/php-fpm.service

[Unit]
Description=php7.2 fpm service
Documentation=http://php.net/manual/zh/install.fpm.php
After=network.target

[Service]
Type=forking
PIDFile=/opt/alt/php72/var/run/php-fpm.pid
ExecStart=/opt/alt/php72/sbin/php-fpm --fpm-config /opt/alt/php72/etc/php-fpm.conf --daemonize
ExecStop=/bin/pkill -9 php-fpm
ExecReload=/bin/kill -USR2 $MAINPID
PrivateTmp=false

[Install]
WantedBy=multi-user.target

五、效能測試

這裡使用指令 ab -n 500 -c 10 http://nginx.beck-yeh.idv.tw/ 測試 wordpress 網站

12345
CPU Loading4.913.384.904.454.15
Memory Usage121Mb129Mb128Mb126Mb128Mb
Requests per second15.7615.5815.9016.2616.13

將 pool 的 pm 模式更改為 ondemand 並使用指令 ab -n 10 -c 10 http://nginx.beck-yeh.idv.tw/ 在測試一次

12345
Requests per second7.427.867.627.717.42

Beck Yeh

熱愛學習於 Linux 與 程式設計 在網站中分享各式各樣學習到的新知識

發佈留言

這個網站採用 Akismet 服務減少垃圾留言。進一步了解 Akismet 如何處理網站訪客的留言資料