一、壓縮功能
實驗目的:通過啟用 Nginx 的 Gzip 壓縮功能,對傳輸的文件(如 HTML、日志等)進行壓縮,減少網絡傳輸數據量,提升用戶訪問速度(尤其適用于帶寬有限的場景),同時通過參數優化平衡壓縮效率與服務器 CPU 消耗。
壓縮功能的核心價值
在 Web 服務中,客戶端(如瀏覽器)與服務器之間傳輸的文件(HTML、CSS、JS、日志等)通常體積較大,會占用較多帶寬并延長加載時間。Gzip 壓縮的原理是:
-
服務器在發送文件前,先對其進行壓縮(類似 ZIP 壓縮);
-
客戶端接收到壓縮文件后,自動解壓并渲染內容。
這種機制的核心優勢:
-
減少傳輸數據量:文本類文件(如 HTML、日志)壓縮率可達 50%-70%,大幅降低帶寬消耗;
-
提升加載速度:相同帶寬下,壓縮后的文件傳輸時間更短,用戶體驗更流暢;
-
節省服務器帶寬成本:尤其對高流量網站,可顯著降低帶寬費用。
vim /usr/local/nginx/conf/nginx.conf # 編寫主配置文件
########
http {
...gzip on; # 開啟 Gzip 壓縮功能gzip_comp_level 4; # 設置 Gzip 壓縮級別(1-9)# 4/5 為平衡壓縮率和 CPU 消耗的常用值# 級別越高,壓縮率越高(文件越小)# 但消耗 CPU 資源越多gzip_disable "MSIE [1-6]\."; # 對 IE 6 及以下版本瀏覽器禁用 Gzip 壓縮# 原因:舊版 IE 對 Gzip 壓縮的支持存在缺陷# 可能導致內容解析錯誤gzip_min_length 4k; # 設置觸發 Gzip 壓縮的最小文件大小(4KB)gzip_http_version 1.1; # 僅壓縮大小 ≥4KB 的文件# gzip_buffers number size; # 設置壓縮時使用的緩沖區# number 為緩沖區數量,size 為單個緩沖區大小# 默認由 Nginx 自動計算# 一般無需手動配置,故注釋保留# gzip_type mime-type text/html; # 指定需要壓縮的 MIME 類型#(如 text/html、application/json 等)# 默認已包含 text/html 等常見類型gzip_vary on; # 開啟 Vary 響應頭,適配代理服務器# 告知代理服務器:同一資源可能有壓縮/未壓縮兩種版本# 需根據客戶端的 Accept-Encoding 頭選擇返回# 避免代理服務器錯誤地將壓縮版本返回給不支持壓縮的客戶端gzip_static on; # 啟用靜態預壓縮文件支持# 若存在與源文件同名的 .gz 預壓縮文件# 直接返回預壓縮文件,無需實時壓縮,減少 CPU 消耗
...
}
########
?
echo small > /usr/local/nginx/html/small.html
cp /usr/local/nginx/logs/zyz.org.access /usr/local/nginx/html/big.html
?
ll /usr/local/nginx/html/ -h
#######
-rw-r--r-- 1 root root 23K Jul 26 14:31 big.html # 超過 4k 將會被壓縮
-rw-r--r-- 1 root root ?14 Jul 24 10:09 index.html
-rw-r--r-- 1 root root ? 6 Jul 26 14:31 small.html # 未超過 4k 不會被壓縮
#######
?
nginx -t
systemctl restart nginx
curl --head --compressed 192.168.67.10/big.html
curl --head --compressed 192.168.67.10/small.html
用 curl --head --compressed 查看響應頭,判斷文件是否被壓縮
測試:結果表示文件大小大于 4k 的文件顯示已被壓縮,格式為 gzip。文件大小小于 4k 的文件未被壓縮。
為什么這樣配置?核心優化邏輯
-
平衡性能與資源:
-
壓縮級別選 4,避免高級別(如 9)過度消耗 CPU;
-
設置最小壓縮閾值(4KB),避免小文件浪費資源。
-
-
兼容性優先:
-
禁用舊版 IE 壓縮,避免解析錯誤;
-
限制 HTTP/1.1 協議,減少協議兼容問題。
-
-
提升效率:
-
啟用 gzip_static 利用預壓縮文件,降低實時壓縮的 CPU 負載;
-
開啟 gzip_vary 確保代理服務器正確處理壓縮內容。
-
適用場景與擴展
-
Gzip 壓縮對文本類文件(HTML、CSS、JS、日志、JSON 等)效果顯著(壓縮率高),對二進制文件(圖片、視頻等,已自帶壓縮算法)效果差甚至反增體積,因此實際配置中可通過 gzip_type 精確指定需壓縮的文件類型(如 gzip_type text/html text/css application/json;)。
-
適合場景:所有需要優化加載速度、節省帶寬的 Web 服務,尤其是靜態資源較多的網站(如博客、文檔站)。
-
通過配置 Gzip 壓縮,Nginx 能在可控的 CPU 消耗下,大幅減少傳輸數據量,顯著提升用戶訪問速度,是 Web 服務性能優化的基礎且高效的手段。
二、反向代理緩存功能
實驗目的:在反向代理架構中,通過配置 Nginx 緩存功能,將后端服務器返回的重復請求資源(如靜態頁面)存儲在代理服務器本地,當后續有相同請求時直接從緩存返回,無需再次訪問后端,從而縮短響應時間、減少后端服務器負載,優化整體服務性能。
緩存的核心原理
Nginx 反向代理緩存的本質是 “本地存儲 + 按需復用”:
-
客戶端首次請求資源(如 www.haha.org/index.html)時,代理服務器轉發請求到后端服務器(RS1),獲取響應后,將資源副本存儲在本地緩存目錄;
-
當相同客戶端(或其他客戶端)再次請求該資源時,代理服務器直接從本地緩存讀取并返回,跳過 “轉發到后端” 的步驟;
-
緩存會按規則自動過期(如超過設定時間未訪問)或更新(后端資源變化時),確保數據有效性。
核心價值:減少后端服務器的重復處理工作(尤其對靜態、低頻更新的資源),同時通過 “本地讀取” 大幅提升響應速度。
關鍵參數解析:
# 主配置文件添加
vim /usr/local/nginx/conf/nginx.conf
##########
http {...proxy_cache_path /usr/local/nginx/cache levels=1:2:2 keys_zone=proxycache:20m inactive=120s max_size=1g;...
}
##########
-
/usr/local/nginx/cache:緩存文件的實際存儲路徑(代理服務器本地目錄,需確保 Nginx 有權限讀寫)。
-
levels=1:2:2:緩存目錄的層級結構(避免單目錄文件過多導致的性能問題)。
-
含義:將緩存鍵(資源唯一標識)的哈希值按 “1 位:2 位:2 位” 拆分,創建多級目錄(如哈希值前 5 位為 a1b2c,則目錄為 cache/a/1b/2c/...);
-
作用:分散文件存儲,提升緩存文件的讀寫效率(單目錄文件過多會導致查找緩慢)。
-
-
keys_zone=proxycache:20m:定義內存中的緩存元數據區域。
-
proxycache:區域名稱(后續在 location 中引用);
-
20m:區域大小(20MB),用于存儲緩存鍵、有效期等元數據(不存儲實際資源內容);
-
作用:快速判斷資源是否在緩存中,避免每次都去磁盤查找,提升緩存命中效率。
-
-
inactive=120s:非活動緩存的過期時間(120 秒)。
-
含義:若某緩存資源 120 秒內無任何請求訪問,自動從磁盤刪除;
-
作用:清理長期閑置的緩存,釋放磁盤空間,避免無效緩存堆積。
-
-
max_size=1g:緩存的最大磁盤占用(1GB)。
-
含義:當緩存總大小超過 1GB 時,Nginx 會自動刪除最久未使用的緩存(LRU 算法);
-
作用:防止緩存無限制增長,避免占用過多磁盤資源影響服務器其他功能。
-
# 子配置文件添加
vim /usr/local/nginx/conf.d/haha.conf
##########
server {listen ?80;server_name www.haha.org;
?location / { # 靜態請求緩存配置proxy_pass http://192.168.67.10; # 轉發到后端靜態服務器(RS1)proxy_cache proxycache; # 啟用緩存,關聯主配置中定義的內存區域proxy_cache_key string; # 定義緩存鍵proxy_cache_valid 200 302 10m; # 對 200(成功)、302(重定向)響應,緩存10分鐘proxy_cache_valid 404 1m; # 對 404(未找到)響應,緩存1分鐘}
?location ~ \.(php|jsp|js)$ {proxy_pass http://192.168.67.20;}
##########
?
systemctl restart nginx
測試:
通過 ab 工具分別在 “無緩存” 和 “有緩存” 狀態下測試訪問速度:
-
無緩存:首次請求需轉發到后端 RS1,響應時間約 281ms;
-
有緩存:重復請求直接從代理服務器本地緩存返回,響應時間降至約 151ms。
結論:緩存生效,顯著提升了重復請求的響應速度,同時減少了后端服務器的請求量(無需重復處理相同請求)。
為什么這樣配置?核心優化邏輯
-
分層存儲提升效率:內存(keys_zone)存元數據、磁盤存實際資源,兼顧 “快速判斷” 和 “大容量存儲”;
-
目錄結構避免瓶頸:levels 多級目錄防止單目錄文件過多,確保緩存讀寫高效;
-
過期策略平衡資源:inactive 清理閑置緩存、max_size 限制總大小,避免資源浪費;
-
按需緩存精準控制:靜態資源緩存(有效期長)、動態資源不緩存(避免過時),適配不同資源特性。
適用場景
-
緩存功能特別適合:
-
靜態資源服務(HTML、圖片、CSS 等,內容穩定、更新頻率低);
-
高并發、重復請求多的場景(如熱門頁面、活動頁面);
-
后端服務器性能有限的場景(通過緩存分擔壓力)。
-
三、實現 FastCGI
FastCGI 是一種用于 Web 服務器與動態內容處理程序(如 PHP、Python 腳本解釋器)之間的通信協議,核心目的是解決傳統 CGI 協議的性能瓶頸,提升動態網頁的處理效率和并發能力。
傳統 CGI 協議的問題在于:每次處理請求都需創建新進程 / 線程,處理完后立即銷毀。這會導致頻繁的進程創建 / 銷毀開銷(CPU、內存資源浪費),無法應對高并發場景。
FastCGI 的改進在于:
-
常駐進程模型: 啟動時預先創建一批獨立的工作進程(Worker Process),由 FastCGI 進程管理器(Process Manager) 統一管理。這些進程啟動后不會銷毀,而是持續等待并處理新請求。
-
協議通信流程:
-
① Web 服務器(如 Nginx、Apache)接收客戶端 HTTP 請求,解析出動態內容請求(如
.php
文件)。 -
② Web 服務器通過 FastCGI 協議(基于 TCP 或 Unix 套接字),將請求數據(如 URL、參數、HTTP 頭)發送給 FastCGI 進程管理器。
-
③ 進程管理器從空閑的工作進程中分配一個,處理請求(如執行 PHP 腳本、訪問數據庫)。
-
④ 工作進程處理完成后,將結果(如 HTML 內容)通過 FastCGI 協議返回給 Web 服務器。
-
⑤ 工作進程處理完后不銷毀,回到 “空閑” 狀態,等待下一次分配。
-
FastCGI 主要用于 Web 服務器與動態腳本解釋器之間的高效協作,解決傳統 CGI 的性能問題,具體價值包括:
-
降低資源開銷: 避免了 CGI 中 “一次請求創建一個進程” 的低效模式,通過常駐進程減少進程創建 / 銷毀的 CPU 和內存消耗。
-
支持高并發: 進程管理器可根據負載動態調整工作進程數量(如 PHP-FPM 的
pm.max_children
配置),同時處理多個請求,提升系統并發能力。 -
語言無關性: 兼容多種動態語言(PHP、Python、Perl 等),只需對應語言的 FastCGI 處理程序(如 PHP 的 PHP-FPM、Python 的 flup)。
-
分離 Web 服務器與處理程序: Web 服務器專注于靜態資源處理(如 HTML、CSS、圖片)和請求轉發,動態內容交給獨立的 FastCGI 進程處理,職責分離更靈活(甚至可部署在不同服務器)。
yum install -y bzip2 systemd-devel libxml2-devel sqlite-devel libpng-devel libcurl-devel oniguruma-devel # 注:oniguruma-devel 需要先更新 oniguruma 再安裝 oniguruma-devel
?
./configure \--prefix=/usr/local/php \ # PHP 安裝路徑--with-config-file-path=/usr/local/php/etc \ ?# php.ini 配置文件路徑--enable-fpm \ # 核心:啟用 PHP-FPM(FastCGI 進程管理器)--with-fpm-user=nginx \ # PHP-FPM 工作進程用戶(與 Nginx 一致,避免權限問題)--with-fpm-group=nginx \ # PHP-FPM 工作進程組--with-curl \ # 啟用 curl 擴展(支持 HTTP 請求)--with-iconv \ # 啟用字符編碼轉換--with-mhash \ # 啟用加密哈希算法--with-zlib \ # 啟用 zlib 壓縮--with-openssl \ # 啟用 SSL 支持--enable-mysqlnd \ # 啟用 MySQL 原生驅動--with-mysqli \ # 啟用 mysqli 擴展(MySQL 交互)--with-pdo-mysql \ # 啟用 PDO MySQL 擴展--disable-debug \ # 禁用調試模式(生產環境優化)--enable-sockets \ # 啟用 sockets 擴展(網絡通信)--enable-soap \ # 啟用 SOAP 服務支持--enable-xml \ # 啟用 XML 擴展--enable-ftp \ # 啟用 FTP 支持--enable-gd \ # 啟用 GD 庫(圖片處理)--enable-exif \ # 啟用 EXIF 圖片元數據處理--enable-mbstring \ # 啟用多字節字符串支持--enable-bcmath \ # 啟用數學計算擴展--with-fpm-systemd # 支持 systemd 管理 PHP-FPM 服務
?
?
cd /usr/local/php/etc
cp php-fpm.conf.default php-fpm.conf # 復制默認配置為正式配置文件
?
vim php-fpm.conf
##########
pid = run/php-fpm.pid # 取消注釋,指定 PHP-FPM 進程 ID 文件路徑(便于 systemd 管理)
##########
?
cd php-fpm.d/
cp www.conf.default www.conf # 復制默認工作池配置
?
vim www.conf
##########
listen = 0.0.0.0:9000 # PHP-FPM 監聽 9000 端口(Nginx 會通過此端口轉發請求)# 生產環境中通常使用 127.0.0.1:9000(僅本地訪問)更安全,此處用 0.0.0.0:9000 便于測試
##########
?
cd /root/php-8.3.9/
cp php.ini-production /usr/local/php/etc/php.ini # 復制生產環境配置模板
?
vim /usr/local/php/etc/php.ini
###########
[Date]
; Defines the default timezone used by the date functions
; https://php.net/date.timezone
date.timezone = Asia/Shanghai # 配置 PHP 時區為上海(避免時間相關函數報錯)
###########
?
cd /root/php-8.3.9/
cp sapi/fpm/php-fpm.service /lib/systemd/system/ # 復制服務文件到 systemd 目錄
vim /lib/systemd/system/php-fpm.service
#########
# ProtectSystem=full # 注釋此行(避免系統權限限制 PHP-FPM 訪問所需文件)
#########
?
systemctl daemon-reload
systemctl start php-fpm.service
systemctl enable --now php-fpm.service
?
netstat -antlupe | grep php
vim /usr/local/nginx/html/index.php
##########
<?phpphpinfo();
?>
##########
?
vim /usr/local/nginx/conf.d/haha.conf
##########
server {listen ?80;server_name www.haha.org;
?root /usr/local/nginx/html; location ~ \.php$ {fastcgi_pass 127.0.0.1:9000; # 轉發請求到 PHP-FPM 的監聽地址(9000 端口)fastcgi_index index.php; # 默認 PHP 首頁include fastcgi.conf; # 引入 Nginx 預定義的 FastCGI 變量配置# 如:$document_root 傳遞網站根目錄# $request_uri 傳遞請求路徑# 確保 PHP 能正確解析請求}
}
##########
?
systemctl restart nginx
測試:
瀏覽器訪問 http://www.haha.org/index.php,若顯示 PHP 信息頁(包含配置、擴展等信息),說明 Nginx 與 PHP-FPM 通過 FastCGI 協議正常協作。
添加環境變量
將 Nginx(/usr/local/nginx/sbin)和 PHP(/usr/local/php/bin、/usr/local/php/sbin)的可執行文件路徑加入系統 PATH,可直接在命令行使用 nginx、php、php-fpm 命令(無需輸入完整路徑),提升操作效率。
vim ~/.bash_profile
########
export PATH=$PATH:/usr/local/nginx/sbin:/usr/local/php/bin:/usr/local/php/sbin
########
?
source ~/bash_profile
核心價值與優勢
-
高性能:FastCGI 常駐進程模型避免了傳統 CGI 的進程創建 / 銷毀開銷,PHP-FPM 可通過配置(如 pm.max_children)調整工作進程數量,支持高并發請求;
-
職責分離:Nginx 專注處理靜態資源(HTML、CSS、圖片)和請求轉發,PHP-FPM 專注執行 PHP 腳本,分工明確提升整體效率;
-
擴展性強:通過 PHP 擴展支持多種功能(數據庫、圖片處理等),滿足復雜動態頁面需求;
-
易管理:PHP-FPM 提供進程監控、性能統計功能,結合 systemd 可便捷管理服務生命周期。
四、memcache 緩存
實驗目的:通過配置 PHP 的 Memcache 擴展與 Memcached 服務,實現動態內容(如數據庫查詢結果、頻繁訪問的頁面數據)的內存緩存。利用 Memcache 高速讀寫的特性,減少重復計算或數據庫訪問,提升頁面響應速度,降低 Web 服務器和后端服務的負載。
Memcache 緩存的核心價值
Memcache 是一種分布式內存緩存系統,核心作用是將頻繁訪問的數據(如用戶信息、商品列表、API 響應)存儲在內存中,而非每次從數據庫或磁盤讀取。其優勢在于:
-
速度快:內存讀寫速度遠高于磁盤(數據庫通常依賴磁盤),可將毫秒級響應降至微秒級;
-
降低后端壓力:減少對數據庫或業務邏輯的重復請求(如同一商品信息被 thousands 次訪問,只需查詢一次數據庫,后續從緩存讀取);
-
支持高并發:內存并發讀寫能力強,適合高流量場景(如電商秒殺、熱門資訊)。
本實驗通過 PHP 連接 Memcached 服務,實現動態內容的緩存,再結合 Nginx 作為 Web 服務器,構建 “前端 - 緩存 - 后端” 的高效架構。
添加 memcache 模塊
tar zxf memcache-8.2.tgz # 解壓 Memcache 擴展源碼包
cd memcache-8.2/ # 進入源碼目錄
yum install autoconf -y # 安裝 autoconf(用于生成 PHP 擴展的編譯配置腳本)
phpize # 生成 PHP 擴展編譯所需的配置文件(基于當前 PHP 環境)
./configure && make && make install # 檢查系統環境,生成 Makefile(適配當前 PHP 版本和系統)
?
?
vim /usr/local/php/etc/php.ini
##########
;extension=zip
extension=memcache # 啟用 Memcache 擴展(告訴 PHP 加載該模塊)# extension=memcache 是讓 PHP 啟用 Memcache 擴展的關鍵配置,只有加載該擴展,PHP 腳本才能通過 memcache 類與 Memcached 服務通信(如存儲、讀取緩存數據)。
;zend_extension=opcache
##########
?
systemctl restart php-fpm
php -m | grep mem
Memcached 是獨立的緩存服務進程,負責管理內存中的緩存數據,提供 TCP 接口供客戶端(如 PHP)讀寫數據,默認監聽 11211 端口。
yum install -y memcached.x86_64
?
vim /etc/sysconfig/memcached
#########
OPTIONS="-l 0.0.0.0,::1" # 允許所有網絡接口訪問(默認可能僅監聽 127.0.0.1)
#########
?
systemctl start memcached.service
systemctl enable --now memcached.service
netstat -antlup | grep memcached
?
cd /mnt/memcache-8.2/ # 回到 Memcache 擴展源碼目錄(包含示例腳本)
cp example.php memcache.php /usr/local/nginx/html/ # 將示例腳本復制到 Nginx 網站根目錄(便于通過瀏覽器訪問)
-
example.php:模擬緩存使用場景(如存儲 / 讀取數據,展示緩存命中效果);
-
memcache.php:Memcached 管理界面(展示緩存命中率、存儲數據量、服務器狀態等)。
vim /usr/local/nginx/html/memcache.php
########
define('ADMIN_USERNAME','zyz'); ? ? // Admin Username # 定義用戶名
define('ADMIN_PASSWORD','zyz'); ? ? // Admin Password # 定義密碼
#$MEMCACHE_SERVERS[] = 'mymemcache-server1:11211'; // add more as an array # 注釋此行
$MEMCACHE_SERVERS[] = '127.0.0.1:11211'; // add more as an array # 添加本地 Memcached 服務器
########
?
ab -n 1000 -c 100 www.haha.org/example.php # 壓測,查看 memcache 緩存效果
example.php 會模擬 “從緩存讀取數據,若未命中則從‘后端’(模擬數據庫)獲取并寫入緩存” 的過程。高并發壓測可觸發緩存機制:首次請求緩存未命中(從后端獲取),后續請求從緩存讀取,驗證緩存是否有效降低后端負載。
通過管理界面查看緩存狀態
瀏覽器訪問 www.haha.org/memcache.php,輸入配置的用戶名(zyz)和密碼(zyz),查看緩存統計信息:
-
命中率(Hit Rate):壓測后命中率顯著提升(如從 50% 升至 100%),說明大部分請求從緩存讀取,而非后端;
-
存儲數據量:顯示緩存中存儲的鍵值對數量,驗證數據是否被正確緩存;
-
服務器狀態:確認 Memcached 服務正常運行,內存使用情況等。
核心配置與緩存原理解析
-
PHP 擴展與 Memcached 服務的關系:
-
Memcache 擴展是 PHP 的 “客戶端”,提供 memcache_connect()、memcache_set()、memcache_get() 等函數,用于與 Memcached 服務通信;
-
Memcached 服務是 “服務器端”,負責管理內存中的緩存數據,接收客戶端的讀寫請求。
-
-
緩存工作流程(以 example.php 為例):
-
① 客戶端請求 example.php,Nginx 轉發給 PHP-FPM;
-
② PHP 腳本嘗試從 Memcached 讀取數據(memcache_get());
-
③ 若緩存命中(數據存在),直接返回緩存數據;
-
④ 若緩存未命中,從 “后端”(如數據庫)獲取數據,寫入 Memcached(memcache_set()),再返回數據;
-
⑤ 后續請求重復步驟②-③,優先使用緩存。
-
-
命中率的意義: 命中率 = 緩存命中次數 / 總請求次數。命中率越高,說明緩存越有效(如 90% 命中率表示 90% 的請求無需訪問后端),大幅降低后端服務(如數據庫)的壓力。
適用場景與優勢
Memcache 緩存適合以下場景:
-
頻繁訪問的靜態化動態內容:如商品詳情頁(數據不常變,但訪問量大);
-
數據庫查詢結果緩存:如用戶信息列表、熱門文章;
-
會話存儲:存儲用戶登錄狀態(替代文件存儲,提升并發能力)。
相比直接訪問后端,其優勢在于:
-
響應速度提升 10-100 倍(內存 vs 磁盤);
-
后端服務負載降低 50% 以上(減少重復請求);
-
支持分布式擴展(多臺 Memcached 服務器協同工作,應對更大緩存需求)。
五、memcache 前置
實驗目的:通過配置 Nginx 直接與 Memcached 交互(即 “Memcache 前置”),實現 “Nginx 優先查詢緩存,未命中再轉發給 PHP” 的架構。相比傳統 “PHP 查緩存” 的模式,可減少 PHP 處理的請求量,解決 PHP 成為性能瓶頸的問題,提升整體架構的并發能力和響應速度。
Memcache 前置的核心價值(對比傳統架構)
傳統架構中,客戶端請求的處理流程是:
-
客戶端 → Nginx → PHP → Memcached(查緩存)→ 數據庫(未命中時)
問題:無論緩存是否命中,請求都必須經過 PHP,導致 PHP 成為瓶頸(尤其高并發時,PHP 進程可能被占滿,無法處理新請求)。
Memcache 前置架構的流程是:
-
客戶端 → Nginx → Memcached(查緩存,命中則直接返回)→ 未命中 → PHP → 處理后存入 Memcached → 返回
優勢:Nginx 直接與 Memcached 交互,緩存命中時無需經過 PHP,僅未命中時才調用 PHP,大幅減少 PHP 的請求量,降低其負載,提升整體吞吐量。
下圖:沒設置 memcache 前置時,壓測訪問后端 php 頁面,每次都會經過 php,會造成一定數據的丟失。
memcache 前置的配置如下:
準備 Memcache 前置所需的 Nginx 模塊
Nginx 本身不支持直接與 Memcached 交互,需依賴兩個第三方模塊:
-
memc-nginx-module:提供 Nginx 訪問 Memcached 的核心功能(如讀寫緩存數據);
-
srcache-nginx-module:實現 “先查緩存,未命中再轉發到后端” 的邏輯(緩存獲取與存儲的調度)。
cd /mnt/
tar xzf memc-nginx-module-0.20.tar.gz # memc 模塊負責與 Memcached 通信
tar xzf srcache-nginx-module-0.33.tar.gz # srcache 模塊負責控制緩存的 “查詢 - 轉發 - 存儲” 流程
?
cd /mnt/nginx-1.26.1/ # 重新編譯 Nginx(集成新模塊)
?
make clean./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --with-http_ssl_module --with-http_v2_module --with-http_realip_module --with-http_stub_status_module --with-http_gzip_static_module --with-pcre --with-stream --with-stream_ssl_module --add-module=/mnt/echo-nginx-module-0.63 --add-module=/mnt/memc-nginx-module-0.20 --add-module=/mnt/srcache-nginx-module-0.33
?
make # make 僅編譯生成新的 nginx 二進制文件(在 objs/ 目錄),不覆蓋現有配置。
?
cd objs/ # 進入編譯生成的目標文件目錄
systemctl stop nginx # 停止運行中的 Nginx(需替換二進制文件)
cp nginx /usr/local/nginx/sbin/nginx # 替換舊的 Nginx 執行文件
cd /usr/local/nginx/sbin
systemctl start nginx # 啟動新的 Nginx
nginx -V # 查看模塊是否添加成功
新編譯的 nginx 已集成 memc 和 srcache 模塊,替換后 Nginx 可支持直接與 Memcached 交互的指令(如 memc_pass、srcache_fetch)。
配置 Memcache 前置規則(核心配置)
編輯 /usr/local/nginx/conf.d/haha.conf,實現 Nginx 直接查緩存的邏輯:
vim /usr/local/nginx/conf.d/haha.conf
############
upstream memcache { # 定義 Memcached 服務器組(供 Nginx 直接連接)server 127.0.0.1:11211; # 指向本地 Memcached 服務(11211 端口)keepalive 512; # 保持 512 個長連接,減少連接建立/關閉的開銷
}
?
server {listen ?80;server_name www.haha.org;
?root /usr/local/nginx/html;
?location /memc { # 內部緩存操作接口(禁止外部直接訪問)internal; # 僅允許 Nginx 內部訪問,禁止外部直接訪問該路徑memc_connect_timeout 100ms; # 連接超時(100ms)memc_send_timeout 100ms; # 發送數據超時(100ms)memc_read_timeout 100ms; # 讀取數據超時(100ms)set $memc_key $query_string; # 緩存鍵(key)設為 URL 查詢參數(由調用者傳遞)set $memc_exptime 300; # 緩存過期時間(300 秒,5 分鐘)memc_pass memcache; # 轉發緩存操作到上面定義的 memcache 服務器組}location ~ \.php$ { # 處理 PHP 請求:優先查緩存,未命中再調用 PHPset $key $uri$args; # 定義緩存鍵:URL 路徑($uri)+ 查詢參數($args),確保唯一標識請求srcache_fetch GET /memc $key; # 第一步:查緩存。用 GET 方法調用 /memc 接口,以 $key 為鍵查緩存srcache_store PUT /memc $key; # 第三步:存緩存。PHP 處理后,用 PUT 方法調用 /memc 接口,以 $key 為鍵存緩存fastcgi_pass 127.0.0.1:9000; # 第二步:未命中緩存時,轉發給 PHP 處理fastcgi_index index.php; # 默認首頁include fastcgi.conf; # 引入 FastCGI 配置}
}
############
?
nginx -t
systemctl restart nginx
ab -n 1000 -c 100 www.haha.org/index.php
相比傳統架構(無前置),壓測無數據包丟失(PHP 被訪問的次數減少,負載降低);
通過 Memcached 管理界面(memcache.php)可觀察到緩存命中率顯著提升,說明多數請求由 Nginx 直接從緩存返回,未經過 PHP。
為什么這樣配置?核心優化邏輯
-
減少 PHP 瓶頸:Nginx 直接查緩存,命中則無需調用 PHP,PHP 僅處理 “緩存未命中” 的請求,負載降低 50% 以上;
-
提升響應速度:Nginx 與 Memcached 的交互效率高于 PHP 與 Memcached(減少 PHP 進程調度開銷),緩存命中時響應更快;
-
長連接優化:upstream memcache 中的 keepalive 減少 TCP 連接建立 / 關閉的開銷,適合高并發場景;
-
安全隔離:internal 配置防止外部直接操作緩存,避免緩存被惡意篡改或刪除;
-
超時控制:嚴格的超時設置(100ms)確保 Memcached 故障時不會阻塞 Nginx 進程(超時后直接轉發給 PHP,保證服務可用性)。
適用場景
Memcache 前置特別適合:
-
動態內容但更新不頻繁的場景(如商品詳情頁、新聞文章);
-
高并發讀場景(如秒殺活動、熱門資訊);
-
PHP 性能成為瓶頸的系統(通過減少 PHP 調用提升整體吞吐量)。
通過 Memcache 前置配置,Nginx 從 “單純的轉發者” 轉變為 “智能緩存代理”,大幅減少 PHP 處理的請求量,顯著提升架構的并發能力和響應速度,是高流量動態網站性能優化的關鍵手段。