Select Page

在Nginx中支援 WordPress 的 Webp,Avif 圖檔

大前提你要先安裝有支援 webp, avif 的外掛,例如EWWW, Convert Media等等

在 Nginx 配置中加 map 指令

  • 在 Nginx 的主配置文件,通常在 /etc/nginx/nginx.conf
  • http {} 内、server {} 之前,加入以下内容:
map $http_accept $avif_suffix {
    default "";
    "~*avif" ".avif";
}
map $http_accept $webp_suffix {
    default "";
    "~*webp" ".webp";
}
  • 配置客户端的 Accept ,來定義 $avif_suffix$webp_suffix 變量,確認是否支持 AVIF 或 WebP 格式。

Nginx 讀取 AVIF 和 WebP 的 MIME Type

找到 /etc/nginx/mime.types

image/avif  avif;
image/webp  webp;

在站點配置中設定重導向

  • 找到 /etc/nginx/sites-available/yourdomain
  • server {} ,加入以下内容:
location ~* ^/wp-content/.+\.(jpe?g|png|gif)$ {
    add_header Vary Accept;
    add_header Cache-Control "private";
    expires 365d;
    try_files $uri$avif_suffix $uri$webp_suffix $uri =404;
}

作用是:

  • 匹配所有請求的 .jpg.jpeg.png.gif 文件。
  • Vary: Accept ,告訴缓存系統按照 Accept 來區分不同的響應。
  • 缓存控制和過期時間。
  • 使用 try_files 指令,會先試提供的 .avif 文件,如果不存在,則提供 .webp 文件,若仍不存在,則提供原始文件。

測試並且重新加載 Nginx 配置

sudo nginx -t
sudo systemctl reload nginx

這些配置假設您的 .avif.webp 文件與原始圖片文件位於相同的目錄,並具有相同的文件名,只是副檔名不同(例如,image.jpg 對應 image.jpg.avifimage.jpg.webp)。

此外,請確保您的伺服器上已經存在對應的 .avif.webp 文件,否則 Nginx 將返回 404 錯誤。

有關更多詳細資訊,您可以參考以下資源:

網站圖片無縫兼容 WebP/AVIF

在 Nginx 上提供 WebP 和 AVIF 圖片

圖片優化新選擇!WebP、AVIF 如何提升網站速度

Nginx 啟用 Brotli 壓縮模組

確認 Nginx 版本

安裝 Brotli 模組

有安裝的可以跳過這一步驟,但多數 nginx 是預設沒有安裝 brotli 模組的,下載 brotli 並且安裝

cd /path/to/nginx/source
./configure --add-module=/path/to/ngx_brotli
make
sudo make install

配置 Nginx 啟用 Brotli 壓縮

找到 nginx 的設定檔,通常位於 /etc/nginx/nginx.conf ,如果是自己編譯的通常位於 /usr/local/nginx/conf/nginx.conf

brotli on;
brotli_comp_level 6;
brotli_static on;
brotli_types text/plain text/css application/javascript application/json text/xml application/xml application/xml+rss text/javascript image/x-icon image/svg+xml;

brotli on;:啟用 Brotli 壓縮。

brotli_comp_level 6;:設定壓縮等級,範圍為 0(無壓縮)到 11(最高壓縮),建議值為 6。

brotli_static on;:允許查找預先壓縮的 .br 檔案。

brotli_types ...;:指定需要壓縮的 MIME 類型,可根據實際需求進行調整。

測試並重新載入 Nginx

sudo nginx -t
sudo systemctl reload nginx

驗證 Brotli 壓縮是否啟用

curl -I -H "Accept-Encoding: br" https://您的域名

如果回應頭中包含 Content-Encoding: br,則表示 Brotli 壓縮已成功啟用。

Brotli 壓縮的關鍵特性

高壓縮率

  • Brotli 使用自適應哈夫曼編碼和自定義字典來提高壓縮率,比 Gzip 通常高出 15% 至 25%。
  • 更高的壓縮率可以減少網頁資源的大小,從而提升網站的載入速度。

快速解壓

  • 雖然 Brotli 的壓縮過程稍慢,但解壓速度非常快,這對於瀏覽器端非常重要,因為解壓過程是即時進行的。

支援範圍廣泛

  • Brotli 已被主流的現代瀏覽器(如 Chrome、Firefox、Edge 和 Safari)支援,並且可與 Web 伺服器(如 Nginx 和 Apache)整合。

適合靜態和動態內容

  • Brotli 特別適合靜態資源(如圖片和腳本)壓縮,對動態生成的內容同樣表現出色。

Brotli 與 Gzip 的比較表

特性BrotliGzip
壓縮率高,壓縮比更優一般
解壓速度
壓縮速度較慢(高壓縮等級下)更快
支援的瀏覽器現代瀏覽器全部支援幾乎所有瀏覽器支援
靜態檔案優化優異一般

相關資源

WordPress – wp-rocket nginx 設定

如果你也是 wordpress 愛用 WP Rocket 的使用者,並且WEB SERVER是用 NGINX 架設的,那肯定要參考這個 GitHub 項目,來作為你 Nginx 以及伺服器上面的最佳設定

安裝

先從 github 中下載下來

cd /etc/nginx
git clone https://github.com/satellitewp/rocket-nginx.git

並且利用 PHP 產生預設的配置檔

cd rocket-nginx
cp rocket-nginx.ini.disabled rocket-nginx.ini
php rocket-parser.php

設定 Nginx

找到 nginx 的設定檔,通常在 /etc/nginx/sites-available ,並且加入設定

server {
  ...
  
  # Rocket-Nginx configuration
  include rocket-nginx/conf.d/default.conf;
  
  ...
}

項目位置

GitHub Rocket-nginx

清除 Nginx cache 的服務 – 使用NodeJS

如果你有用 Nginx 的快取服務,無論是 fastcgi or proxy cache,都會遇到很難有一套真正好用的清除工具,這邊示範一套自己開發的清除工具,也支援多伺服器使用

安裝必要的套件

你先需要有nodejs,沒有的人先去官網安裝下,安裝完畢的人,先建立一個目錄,並且輸入以下指令,安裝必要的套件

npm init -y
npm install express

建立一個 Node.js App

可以命名為 app.js,內容如下,會建立一個小型的伺服器,用來處理 http 的請求,並且刪除指定的目錄

const express = require('express');
const { exec } = require('child_process');
const fs = require('fs');

const app = express();
const PORT = 3000;

const logFile = 'application.log';

function log(message) {
    const timestamp = new Date().toISOString();
    fs.appendFileSync(logFile, `${timestamp} - ${message}\n`);
}

app.get('/delete-dir', (req, res) => {
    let dir = req.query.dir;

    if (!dir || /[^a-zA-Z0-9_\-\/]/.test(dir)) {
        log('提供的路徑不合法!');
        return res.status(400).send('提供的路徑不合法!');
    }

    const command = `sudo find /run/proxy_cache/${dir} -mindepth 1 -type d -exec rm -rf {} +`;

    exec(command, (error, stdout, stderr) => {
        if (error) {
            log(`执行错误: ${error}`);
            return res.status(500).send('删除子目錄失敗!');
        }
        log('子目錄删除成功!');
        res.send('子目錄删除成功!');
    });
});

app.listen(PORT, () => {
    log(`服务器正在运行于 http://localhost:${PORT}`);
});

其中我把能刪除的資料定義在只有這個目錄下的才行 /run/proxy_cache/ ,避免權限過大問題

配置 sudo 權限

打開 sudoers 文件

sudo visudo

加入指令,記得把 <username> 改成自己的名字,或是 www-data

<username> sudo find /run/proxy_cache/ -mindepth 1 -type d -exec rm -rf {} +

完成後的測試

可以利用 CURL 呼叫 API ,成功就會看到 “子目錄删除成功!” 的訊息

curl "http://localhost:3000/delete-dir?dir=cache_directory"

結論與注意事項

要記得別讓外部的人可以輕易地存取這項服務,防火牆要記得把port鎖好,執行權限要小心設定,這樣就可以搭配 Nginx Cache 使用,之後再來出對應的刪除功能。

開機時候自動執行

要讓 Node.js 應用在系統開機時由特定使用者(例如 www-data)啟動,需要配置一個 systemd 服務單元。在這個情況中,我們將創建一個服務單元文件來確保 Node.js 應用作為 www-data 使用者運行。

創建 systemd 服務文件

建立一個新的 systemd 服務文件。

sudo nano /etc/systemd/system/nodeapp.service

加入以下配置

[Unit] 
Description=Node.js Web Application 
After=network.target 

[Service] 
Type=simple 
User=www-data 
Group=www-data 
WorkingDirectory=/path/to/your/app 
ExecStart=/usr/bin/node /path/to/your/app/app.js 
Restart=on-failure 

[Install] 
WantedBy=multi-user.target

參數意思如下

Description: 服務的描述。

After: 這個單元應該在網絡服務可用之後啟動。

UserGroup: 指定運行此服務的使用者和組。

WorkingDirectory: 指定 Node.js 應用的工作目錄。

ExecStart: 指定啟動應用的命令。

Restart: 指定何時重新啟動服務,on-failure 表示只在程序異常退出時重啟。

啟用和啟動服務

重新加載 systemd 配置以讀取新的服務文件:

sudo systemctl daemon-reload

啟用剛創建的服務,使其在開機時自動啟動:

sudo systemctl enable nodeapp.service

啟動服務以檢查它是否運行正常:

sudo systemctl start nodeapp.service

檢查服務的狀態來確認一切正常:

sudo systemctl status nodeapp.service

讓 www-data 執行 SERVER 上的特定權限指令

sudoers 檔案控制了使用者及群組在使用 sudo 指令時的權限。為了安全編輯這個檔案,應該使用 visudo 指令,因為它會檢查語法錯誤,避免創建一個無法使用的 sudoers 檔案。

更新 sudoers 檔案的步驟:

開啟終端機

開啟你的伺服器的命令行介面。

使用 visudo 編輯 sudoers 檔案: 輸入以下指令以安全方式編輯 sudoers 檔案:

sudo visudo

新增規則

在編輯器中,新增一條規則,允許 www-data 使用者無需密碼執行特定指令。

www-data ALL=(ALL) NOPASSWD: /usr/bin/rm -rf /path/to/nginx/cache/*

指令的意義是:

www-data:指定的使用者。

ALL=(ALL):這表示 www-data 使用者可以從任何主機以任何使用者身份執行指令。

NOPASSWD:允許 www-data 使用者在執行指定的指令時不需要輸入密碼。

/usr/bin/rm -rf /path/to/nginx/cache/*:指定 www-data 使用者無密碼可以執行的指令。

儲存並退出編輯器

如果你使用的是 nano,按 Ctrl+X 來退出,然後按 Y 鍵儲存更改,最後按 Enter 鍵確認檔案名稱。

測試配置

為了確保設定正確無誤,可以用 www-data 份執行指令:

sudo -u www-data sudo /usr/bin/rm -rf /path/to/nginx/cache/*

如果不需要密碼且指令執行成功,代表 sudoers 檔案配置正確。

安全注意事項:

  • 最小權限原則:只授權必要的最小權限,避免給予 www-data 使用者太廣泛的權限。
  • 明確指令路徑:使用完整的指令路徑(如 /usr/bin/rm),避免安全風險。
  • 定期審計:定期檢查 sudoers 檔案,確保所有條目仍然符合組織的安全政策和操作需要。

Nginx proxy_cache 進階設定,放飛你的 wordpress 主機

定義 proxy cache path

先找到設定檔,通常在

sudo nano /etc/nginx/nginx.conf

找到 http ,在他的配置中設定

http {
    proxy_cache_path /path/to/cache levels=1:2 keys_zone=my_cache:10m max_size=10g inactive=60m use_temp_path=off;

    ...
}


緩存配置

  • 緩存文件儲存的路徑: /path/to/cache
  • 緩存目錄的層級: 1:2
  • 緩存區域的名稱和大小: my_cache:10m
    • 緩存區域名稱: my_cache
    • 緩存區域大小: 10MB
  • 緩存的最大大小: 10GB
  • 在指定的時間內沒有被訪問的緩存文件將被刪除: 60m
  • 直接在緩存路徑上操作,而不是使用臨時路徑: off

詳細說明

  • 緩存文件儲存的路徑

緩存文件將儲存在指定的目錄中。您可以根據您的需求設置此路徑。

  • 緩存目錄的層級

此設置控制緩存目錄的層級結構。例如,設置為 1:2 表示將使用兩個層級的目錄來儲存緩存文件。第一層級將包含 10 個子目錄,第二層級將包含 100 個子目錄。

  • 緩存區域的名稱和大小

此設置控制緩存區域的名稱和大小。緩存區域是緩存文件的分組。您可以根據您的需求設置多個緩存區域。

  • 緩存的最大大小

此設置控制緩存的最大大小。超過此大小時,最舊的緩存文件將被刪除。

  • 在指定的時間內沒有被訪問的緩存文件將被刪除

此設置控制在指定的時間內沒有被訪問的緩存文件將被刪除。

  • 直接在緩存路徑上操作,而不是使用臨時路徑

修改設定檔,配置 proxy cache

找到 config 中的 server ,在裡面添加相關設定

server {
    listen 80;
    server_name yourdomain.com;

    location / {
        proxy_pass http://your_backend_server;
        proxy_cache my_cache;
        proxy_cache_revalidate on;
        proxy_cache_min_uses 1;
        proxy_cache_use_stale error timeout updating http_500 http_502 http_503 http_504;
        proxy_cache_lock on;
        proxy_cache_valid 200 302 10m;
        proxy_cache_valid 404 1m;
    }
}

反向代理配置

  • 後端伺服器的地址: proxy_pass
    • 此設置指定後端伺服器的地址。後端伺服器是 Nginx 將請求轉發到的伺服器。
  • 使用之前定義的緩存區域: proxy_cache
    • 此設置指定要使用的緩存區域。緩存區域是 Nginx 用於儲存靜態內容的區域。
  • 啟用後,會在緩存過期時向後端伺服器驗證緩存內容是否仍然有效: proxy_cache_revalidate
    • 此設置控制是否在緩存過期時向後端伺服器驗證緩存內容是否仍然有效。默認情況下,Nginx 將在緩存過期時直接使用緩存內容。
  • 在緩存內容之前,請求必須達到指定的次數: proxy_cache_min_uses
    • 此設置控制在緩存內容之前,請求必須達到指定的次數。這可以防止頻繁更新的內容被緩存。
  • 在後端伺服器錯誤或超時時,使用舊的緩存數據: proxy_cache_use_stale
    • 此設置控制在後端伺服器錯誤或超時時是否使用舊的緩存數據。默認情況下,Nginx 將在後端伺服器錯誤或超時時向客戶端返回錯誤。
  • 在更新緩存內容時,防止多個請求同時向後端伺服器發送: proxy_cache_lock
    • 此設置控制在更新緩存內容時是否防止多個請求同時向後端伺服器發送。這可以防止後端伺服器過載。
  • 設定不同響應狀態碼的緩存時間: proxy_cache_valid
    • 此設置控制不同響應狀態碼的緩存時間。您可以根據您的需求設置不同的緩存時間。

重新開啟 Nginx 讓設定生效

sudo nginx -t
sudo systemctl reload nginx

快取的時間設定

Nginx 支持多種時間單位来指定 cache 的有效期,这包括:

  • s
  • m 分鐘
  • h 小時
  • d
  • w
  • M 月(30 天)
  • y 年(365 天)

舉例子

快取檔案 30 秒

proxy_cache_valid 200 302 30s;

刪除快取的方法

1.直接刪除快取檔案

找到你設定的路徑,直接刪除檔案即可

sudo rm -rf /path/to/cache/*

2.使用 Nginx Cache Purge

如果你在編譯 Nginx 有加入 cache purge ,就可以用下面的設定,如果你是用預設安裝,通常不包含 cache purge,可以看下我之前的安裝教學

location /purge_cache/ {
    proxy_cache_purge my_cache $scheme$host$request_uri;
}