首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

PHP 啟用 GZIP 頁面壓縮完整實作:ob_start + zlib 自訂與內建處理器

     編輯:PHP 綜合知識

原理概述

GZIP 壓縮需瀏覽器與伺服器雙端支援。流程:PHP 輸出緩衝 → 檢查瀏覽器 Accept-Encoding: gzip → gzencode() 壓縮 → 送出 Content-Encoding: gzip 標頭 → 瀏覽器自動解壓縮渲染。

方案一:自訂回呼函數 (完整控制)

<?php
// 1. 啟用輸出緩衝並指定回呼
ob_start('ob_gzip');

/* ... 產生大量輸出內容 ... */
for ($i = 0; $i < 100; $i++) {
    echo '這裡是測試內容,重複以觀察壓縮效果。';
}

/* 2. 結束緩衝並輸出 (腳本結束會自動 flush) */
ob_end_flush();

/* 3. 壓縮回呼函數 */
function ob_gzip($content) {
    // 條件:標頭未送出、zlib 已載入、瀏覽器支援 gzip
    if (!headers_sent() && extension_loaded('zlib') &&
        strpos($_SERVER['HTTP_ACCEPT_ENCODING'] ?? '', 'gzip') !== false) {

        // 壓縮等級 9 (最高),附加註解以利除錯
        $content = gzencode($content . "\n// 頁面已 GZIP 壓縮", 9);

        // 必要回應標頭
        header('Content-Encoding: gzip');
        header('Vary: Accept-Encoding');      // 告訴 Proxy 依 Accept-Encoding 快取不同版本
        header('Content-Length: ' . strlen($content));
    }
    return $content;
}
?>

方案二:內建 ob_gzhandler (一鍵啟用)

<?php
if (extension_loaded('zlib')) {
    ob_start('ob_gzhandler');
}
?>
<!DOCTYPE html>
<html><head><meta charset="utf-8"><title>測試頁</title></head><body>
<?php for ($i = 0; $i < 10000; $i++) echo 'Hello World!'; ?>
</body></html>
<?php
if (extension_loaded('zlib')) {
    ob_end_flush();
}
?>
  • ob_gzhandler 內建處理 Accept-Encoding 檢查、壓縮等級、標頭送出。
  • 支援 zlib.output_compression INI 設定進一步簡化。

方案三:Web 伺服器層級壓縮 (推薦生產環境)

將壓縮下移至 Nginx/Apache,PHP 完全不處理壓縮,效能最佳:

# Nginx
gzip on;
gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;
gzip_min_length 1000;
gzip_comp_level 6;
# Apache (mod_deflate)

    AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css text/javascript application/javascript application/json

實測壓縮效果

內容大小未壓縮GZIP Level 9壓縮率
重複文字 100 行 4.69 KB 104 B 97.8% ↓
HTML 頁面 50 KB 50 KB 8 KB 84% ↓
JSON API 回應 20 KB 20 KB 3 KB 85% ↓

關鍵標頭說明

  • Content-Encoding: gzip:告知瀏覽器內容已壓縮。
  • Vary: Accept-Encoding:關鍵!讓 CDN/Proxy 針對支援/不支援 gzip 的客戶端分別快取,避免傳遞錯誤內容。
  • Content-Length:壓縮後位元組數,利於連線復用與進度顯示。

常見坑點與除錯

  1. 輸出前已有內容:ob_start 必須在任何 echo、HTML、空白字元之前呼叫。
  2. 多層 ob_start:巢狀緩衝需對應 ob_end_flush,否則壓縮不生效。
  3. SSL/TLS 壓縮風險:HTTPS 下壓縮可能洩露資訊 (BREACH/CRIME 攻擊),敏感頁面建議關閉壓縮或使用 Vary: Accept-Encoding 搭配隨機填充。
  4. 驗證工具:瀏覽器 DevTools Network 標籤查看 content-encoding: gzip;線上工具 HTTP Compression Test。

總結建議

  • 開發/測試環境:使用方案二 ob_gzhandler 快速驗證。
  • 生產環境:優先在 Nginx/Apache 啟用 GZIP,PHP 專注業務邏輯。
  • 特殊需求 (動態調整壓縮等級、植入註解) 再用方案一自訂回呼。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved