MIS 腳印 logo

MIS 腳印

記錄 IT 學習的軌跡

NGINX 搭配 PHP-FPM 配置 WordPress 多站點網站 for CentOS 8

在 CentOS Linux 8 使用 NGINX 網站伺服器搭配 PHP-FPM,建置多個獨立的 WordPress.ORG 多站點網站,並將相同邏輯可重複使用的 NGINX 設定檔分割,即可讓多站點網站個別的 NGINX 設定檔直調用。

WordPress.ORG

MariaDB

使用指令來建立 WordPress 須用的使用者帳號和資料庫,也可使用 phpMyAdmin 操作。

登入 MariaDB 資料庫:

mysql -u root -p
Enter password:
Welcome to the MariaDB monitor.  Commands end with ; or \g.
Your MariaDB connection id is 200
Server version: 10.3.17-MariaDB MariaDB Server

Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

MariaDB [(none)]>

建立資料庫和編碼與排序,自行替換 www_footmark_com_tw:

MariaDB [(none)]> CREATE DATABASE `www_footmark_com_tw` DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;
Query OK, 1 row affected (0.000 sec)

新增使用者帳號和密碼,自行替換帳號 my_user 和密碼 my_password :

MariaDB [(none)]> CREATE USER 'my_user'@'localhost' IDENTIFIED BY 'my_password';

授予帳號 my_user 在資料庫 www_footmark_com_tw 所有的權限:

MariaDB [(none)]> GRANT ALL PRIVILEGES ON `www_footmark_com_tw`.* TO 'my_user'@'localhost';
Query OK, 0 rows affected (0.001 sec)

WordPress

下載

開啟 WordPress.org Taiwan 正體中文點擊【取得 WordPress】。

複製【下載 .tar.gz】連結網址。

貼上連結網址下載檔案:

wget https://wordpress.org/latest.tar.gz

解壓縮檔案:

tar -zxv -f latest-zh_TW.tar.gz

移除壓縮檔案:

rm latest-zh_TW.tar.gz

將解壓縮後的 wordpress 目錄移動到欲命名的 NGINX 網站根目錄 (root),通常會依使用的網域名稱或子域名來命名目錄名稱:

mv wordpress/ /var/www/www.footmark.com.tw

目錄和檔案權限設定

遞迴更改網站目錄下,所有目錄的權限設定:

find /var/www/ -type d -exec chmod 2775 {} \;

遞迴更改網站目錄下,所有檔案的權限設定:

find /var/www/ -type f -exec chmod 664 {} \;

wp-config.php 設定

WordPress wp-config.php 設定請參考 Editing wp-config.php | WordPress.org

NGINX 設定

CentOS 8 的 NGINX 預設提供和自行新增的目錄和設定檔大致如下:

  • 綠色:目錄。
  • 藍色:連結。
  • 黑色:檔案。
tree /etc/nginx/
/etc/nginx                          # NGINX 設定檔目錄
├── conf.d                          # 獨立網站設定檔 (所有網站設定檔均建立在此)
│   ├── default.conf                # NGINX 網站預設設定檔
│   ├── php-fpm.conf                # PHP-FPM 設定檔
│   ├── phpmyadmin.conf             # phpMyAdmin 設定檔 (自行新增)
│   └── www.footmark.com.tw.conf    # 網站設定檔 (自行新增)
├── default.d
│   └── php.conf                    # PHP FastCGI 設定檔
├── fastcgi_params
├── global                          # 共用設定檔 (自行新增)
│   ├── no-cache.conf               # 不快取條件
│   ├── restrictions.conf           # 限制檔案
│   └── ssl.conf                    # TLS/SSL 憑證
├── koi-utf
├── koi-win
├── mime.types
├── modules -> ../../usr/lib64/nginx/modules    # 模塊路徑
├── nginx.conf                      # 主要設定檔 (進入點)
├── scgi_params
├── ssl                             # 存放 TLS/SSL 憑證 (自行新增)
│   └── footmark.com.tw
│       ├── cert.pem
│       └── key.pem
├── uwsgi_params
└── win-utf

主要設定檔

NGINX 的主要設定檔配置:

vim /etc/nginx/nginx.conf
user  nginx;
worker_processes auto;

error_log  /var/log/nginx/error.log warn;
pid        /var/run/nginx.pid;

# 載入 ngx_cache_purge 清除快取動態模塊 
load_module modules/ngx_http_cache_purge_module.so;

events {
    worker_connections  1024;
}

http {
    include       /etc/nginx/mime.types;
    default_type  application/octet-stream;

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

    access_log  /var/log/nginx/access.log  main;

    sendfile        on;
    #tcp_nopush     on;

    keepalive_timeout  65;
    client_max_body_size 13m;

    gzip  on;

    # 程式可執行的最長時間 (秒),需同步修改 PHP 設定檔 /etc/php.ini 的 max_execution_time 相同數值 (可排除 WordPress 安裝外掛時執行時間過久錯誤 "504 Gateway Time-out")
    fastcgi_read_timeout 300;


    #
    # 設定 FastCGI Cache 快取
    #

    # 自訂快取目錄路徑 (須自行建立此目錄,且擁有者須為 nginx)
    fastcgi_cache_path /var/run/nginx-cache levels=1:2 keys_zone=WORDPRESS:500m inactive=60m;

    fastcgi_cache_key "$scheme$request_method$host$request_uri";
    fastcgi_cache_use_stale error timeout invalid_header http_500;


    # 調用所有獨立網站設定檔
    include /etc/nginx/conf.d/*.conf;
}

獨立設定檔

如欲建立不同網域名稱 (Domain Name) 或子域名 (Subdomain) 的多站點網站,只需依下述所列設定對應的值即可,並將設定值 www.footmark.com.tw 替換為實際使用的網域名稱或子域名:

  • server_name
  • root
  • ssl_certificate
  • ssl_certificate_key
vim /etc/nginx/conf.d/www.footmark.com.tw.conf
server {
    listen 80;
    listen [::]:80;
    server_name footmark.com.tw www.footmark.com.tw *.footmark.com.tw;
    # 將 HTTP 資源永久導向至 HTTPS
    return 301 https://$server_name$request_uri;
}

server {
    # 使用 https 和 http/2 協定
    listen 443 ssl http2;
    # 上述的 IPv6 方式
    listen [::]:443 ssl http2;

    ## Your website name goes here.
    server_name footmark.com.tw www.footmark.com.tw *.footmark.com.tw;
    ## Your only path reference.
    root /var/www/www.footmark.com.tw;
    ## This should be in your http block and if it is, it's not needed here.
    index index.php;

    # 調用 PHP FastCGI 設定檔 (NGINX 預設提供)
    include             /etc/nginx/default.d/php.conf;
    # 調用共用設定檔 - 限制檔案
    include             /etc/nginx/global/restrictions.conf;
    # 調用共用設定檔 - 不快取條件
    include             /etc/nginx/global/no-cache.conf;


    #
    # 設定 ngx_cache_purge 清除快取動態模塊
    #
    location ~ /purge(/.*) {
        fastcgi_cache_purge WORDPRESS "$scheme$request_method$host$1";
    }	


    #
    # certs sent to the client in SERVER HELLO are concatenated in ssl_certificate
    #

    # SSL 憑證證書路徑
    ssl_certificate     /etc/nginx/ssl/footmark.com.tw/cert.pem;
    # 私鑰路徑
    ssl_certificate_key /etc/nginx/ssl/footmark.com.tw/key.pem;

    # 調用共用設定檔 - TLS/SSL 憑證
    include             /etc/nginx/global/ssl.conf;
}

PHP FastCGI 設定檔

開啟 NGINX 預設提供的 PHP FastCGI 設定檔,並增加設定 FastCGI Cache 快取:

vim /etc/nginx/default.d/php.conf
# pass the PHP scripts to FastCGI server
#
# See conf.d/php-fpm.conf for socket configuration
#
index index.php index.html index.htm;

location ~ \.php$ {
    try_files $uri =404;
    fastcgi_intercept_errors on;
    fastcgi_index  index.php;
    include        fastcgi_params;
    fastcgi_param  SCRIPT_FILENAME  $document_root$fastcgi_script_name;
    fastcgi_pass   php-fpm;

    # 設定 FastCGI Cache 快取
    fastcgi_cache_bypass $no_cache;
    fastcgi_no_cache $no_cache;

    fastcgi_cache WORDPRESS;
    fastcgi_cache_valid 200 60m;
}

共用設定檔

在 nginx 目錄下新建 global 目錄,用來放置相同邏輯可重複使用的設定檔:

mkdir /etc/nginx/global

限制檔案

限制僅允許哪些檔案能被讀取,提高網站安全性:

vim /etc/nginx/global/restrictions.conf
# Global restrictions configuration file.
# Designed to be included in any server {} block.
location = /favicon.ico {
    log_not_found off;
    access_log off;
}
 
location = /robots.txt {
    allow all;
    log_not_found off;
    access_log off;
}
 
# Deny all attempts to access hidden files such as .htaccess, .htpasswd, .DS_Store (Mac).
# Keep logging the requests to parse later (or to pass to firewall utilities such as fail2ban)
location ~ /\. {
    deny all;
}
 
# Deny access to any files with a .php extension in the uploads directory
# Works in sub-directory installs and also in multisite network
# Keep logging the requests to parse later (or to pass to firewall utilities such as fail2ban)
location ~* /(?:uploads|files)/.*\.php$ {
    deny all;
}

location / {
    # This is cool because no php is touched for static content.
    # include the "?$args" part so non-default permalinks doesn't break when using query string
    try_files $uri $uri/ /index.php?$args;
}

location ~* \.(js|css|png|jpg|jpeg|gif|ico)$ {
        expires max;
        log_not_found off;
}

TLS/SSL 憑證

設定 NGINX 的 TLS/SSL 憑證,讓網站支援 HTTPS 加密連線。

vim /etc/nginx/global/ssl.conf
# 快取有效期
ssl_session_timeout 1d;
# 快取憑證類型和大小
ssl_session_cache shared:SSL:50m;


#
# intermediate configuration. tweak to your needs.
#

# 使用的加密協定
ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
# 加密演算法,越前面的優先級越高
ssl_ciphers 'ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA:ECDHE-RSA-AES256-SHA384:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA:ECDHE-RSA-AES256-SHA:DHE-RSA-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-RSA-AES256-SHA256:DHE-RSA-AES256-SHA:ECDHE-ECDSA-DES-CBC3-SHA:ECDHE-RSA-DES-CBC3-SHA:EDH-RSA-DES-CBC3-SHA:AES128-GCM-SHA256:AES256-GCM-SHA384:AES128-SHA256:AES256-SHA256:AES128-SHA:AES256-SHA:DES-CBC3-SHA:!DSS';
# 交握過程使用 Server 的首選加演算法,這裡使用 Client 為首選
ssl_prefer_server_ciphers on;


#
# HSTS (ngx_http_headers_module is required) (15768000 seconds = 6 months)
#

# 增加 http header
add_header Strict-Transport-Security max-age=15768000;

不快取條件

設定哪些情況和網頁不快取:

vim /etc/nginx/global/no-cache.conf
# 啟用 FastCGI Cache 快取
set $no_cache 0;
 
# POST 請求和帶有查詢字串的網址不快取
if ($request_method = POST) {
    set $no_cache 1;
}
if ($query_string != "") {
    set $no_cache 1;
}   
 
# 以下 URI 不快取
if ($request_uri ~* "(/wp-admin/|/xmlrpc.php|/wp-(app|cron|login|register|mail).php|wp-.*.php|/feed/|index.php|wp-comments-popup.php|wp-links-opml.php|wp-locations.php|sitemap(_index)?.xml|[a-z0-9_-]+-sitemap([0-9]+)?.xml)") {
    set $no_cache 1;
}   
 
# 登入用戶或最近留言者不快取
if ($http_cookie ~* "comment_author|wordpress_[a-f0-9]+|wp-postpass|wordpress_no_cache|wordpress_logged_in") {
    set $no_cache 1;
}

# 加入快取資訊表頭 (除錯用)
add_header X-Cache $upstream_cache_status;

檢驗 NGINX 設定檔

使用這個指令可以檢驗 NGINX 的設定檔是否正確:

nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

為了讓設定生效,必須重啟 NGINX 服務:

systemctl restart nginx

參考

發表迴響