Nginx第二虛擬主機FastCGI-Cache設定

在文章中 如何減少nginx+wordpress+mysql架設在windows裡伺服器回應的等待時間(TTFB) 說明如何使用 FastCGI Cache 來減少 TTFB。

當在同一個 Nginx 環境中增加第二個虛擬主機(vhost)https://second.polinwei.com,並複製了相同的 location ~ \.php$ 快取設定,卻看不到 X-FastCGI-Cache 標頭,最核心的原因在於 Nginx 的 add_header 指令繼承機制限制

在 Nginx 中,如果子區塊(例如 location)內部或外面同時存在其他 add_header 指令(像是 Cloudflare 的憑證防護或全域標頭),Nginx 會直接覆蓋掉這一個 location 裡的 add_header X-FastCGI-Cache ...,導致它完全不顯示。

請依序透過以下 3 個步驟進行排查與修正,即可立刻讓第二個子網域看到快取狀態:

1. 檢查 add_header 是否被繼承規則覆蓋(最常見)

Nginx 的規則是:「如果子區塊內有定義任何 add_header,它就會完全忽略父區塊的所有 add_header
請檢查您的 second.polinwei.com 區塊,是否在 server 區塊中放了其他的標頭(例如 HSTS 網路安全標頭:add_header Strict-Transport-Security ...)?

  • 修正方法:請確保 add_header X-FastCGI-Cache $upstream_cache_status; 這一行,是單獨且確實地躺在 location ~ \.php$ 區塊內部

2. 快取變數獨立性:必須為新網站補上專屬的 $custom_skip_cache2

Nginx 的變數範圍(Scope)是跟著請求跑的。如果您在新的 server 區塊中,忘記複製一整套完整的排除邏輯,或者使用了與第一個網站一模一樣的變數名稱而發生衝突,新網站就會因為變數混淆而完全不啟動快取。

請確保新網站 second.polinwei.comserver 區塊內,也有一套完全獨立的變數宣告(建議將變數名稱微調,例如改為 $skip_cache_second),如下所示:

Nginx
server {
    listen       443 ssl;
    server_name  second.polinwei.com;
    root         html/second; # 確保新站路徑正確
    
    # 針對新網站的獨立快取排除邏輯
    set $skip_cache_second 0;

    if ($request_method = POST) { set $skip_cache_second 1; }   
    if ($query_string != "") { set $skip_cache_second 1; }   
    if ($request_uri ~* "/wp-admin/|/xmlrpc.php|wp-.*.php|/feed/|index.php|sitemap(_index)?.xml|/wp-json/") {
        set $skip_cache_second 1;
    }   
    if ($http_cookie ~* "comment_author|wordpress_[a-f0-9]+|wp-postpass|wordpress_no_cache|wordpress_logged_in") {
        set $skip_cache_second 1;
    }

    # ... 您的 SSL 憑證與靜態檔案設定 ...

    location ~ \.php$ {            
        include        fastcgi.conf;
        include        fastcgi_params;
        fastcgi_pass   127.0.0.1:9000;
        fastcgi_index  index.php;
        fastcgi_param  SCRIPT_FILENAME  $document_root$fastcgi_script_name;
        
        # 1. 使用相同的全域快取空間 WORDPRESS
        fastcgi_cache WORDPRESS;
        
        # 2. 【關鍵】套用新網站專屬的排除變數
        fastcgi_cache_bypass $skip_cache_second;
        fastcgi_no_cache $skip_cache_second;
        
        fastcgi_cache_valid 200 301 302 1d;
        fastcgi_cache_valid 404 1m;			
        fastcgi_ignore_headers Cache-Control Expires Set-Cookie;
        fastcgi_cache_use_stale error timeout invalid_header http_500 http_503;

        # 3. 強制加上標頭,並確保這個 location 內沒有其他 add_header 互相干擾
        add_header X-FastCGI-Cache $upstream_cache_status;
        
        fastcgi_read_timeout 60s;
        fastcgi_connect_timeout 60s;	
    }
}

3. 多網站的 Redis 物件快取衝突(如果新站也有用 Redis)

如果這個新網站 second.polinwei.com 也是 WordPress,且您直接啟用了 Redis Object Cache,那麼它會和您的主站 polinwei.com 搶奪同一個 Redis 記憶體空間,這會導致全站判定混亂(Nginx 會頻繁回報 MISS 或標頭消失)。

  • 重要修正:請立刻打開新網站的 wp-config.php,將它的 WP_CACHE_KEY_SALT 改成專屬的名稱:
PHP
// 新網站專屬的前置詞,绝对不能跟主站一模一樣!
define( 'WP_CACHE_KEY_SALT', 'baikuder_prod_' );

請完成上述修改後,打開 Windows CMD 執行 taskkill /f /im nginx.exe 隨後 start nginx 徹底重啟。

CMake
#關閉 nginx
taskkill /f /im nginx.exe 或 nginx -s stop

#重啟 nginx
start /b "nginx" nginx.exe

發佈留言

發佈留言必須填寫的電子郵件地址不會公開。 必填欄位標示為 *


內容索引