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

PHP htmlentities() 函數完整指南:參數詳解、編碼選項、實戰範例

     編輯:PHP 相關知識

PHP htmlentities() 深度解析:防 XSS 輸出編碼、旗標組合、字元集處理

htmlentities() 將所有可轉換字元轉為 HTML 實體,是輸出端防 XSS 的核心函數。本文詳細說明四個參數、旗標組合策略、字元集選擇、與 htmlspecialchars() 差異、實戰最佳實踐。

函數簽名與參數

htmlentities(
    string $string,
    int $flags = ENT_COMPAT | ENT_HTML401,
    ?string $encoding = null,
    bool $double_encode = true
): string

旗標常數完整對照表

分類常數值說明
引號處理ENT_COMPAT2預設。僅轉換雙引號 "
ENT_QUOTES3轉換雙引號 " 和單引號 ' (推薦)
ENT_NOQUOTES0不轉換任何引號
無效編碼ENT_IGNORE4忽略無效編碼 (不安全,避免使用)
ENT_SUBSTITUTE8無效編碼替換為 U+FFFD (推薦)
ENT_DISALLOWED128文檔類型不允許的碼位替換為 U+FFFD
文檔類型ENT_HTML4010預設。HTML 4.01 實體表
ENT_HTML516HTML5 實體表 (更完整,推薦現代專案)
ENT_XML132XML 1 實體表
ENT_XHTML64XHTML 實體表

字元集參數 (encoding)

  • 預設:PHP 5.6+ 為 UTF-8,舊版為 ISO-8859-1
  • 常用值:UTF-8、ISO-8859-1、ISO-8859-15、GB2312、BIG5
  • 強烈建議顯式指定 'UTF-8' 避免版本差異

推薦預設旗標組合

// 現代 Web 專案 (HTML5、UTF-8、雙引號單引號皆轉、錯誤替換)
$defaultFlags = ENT_QUOTES | ENT_SUBSTITUTE | ENT_HTML5;

// 使用範例
$safe = htmlentities($userInput, $defaultFlags, 'UTF-8');

htmlentities() vs htmlspecialchars()

實戰範例

<?php
$input = "Tom & Jerry's \"Adventure\" bold café naïve résumé";

// 1. 基本防 XSS (推薦)
echo htmlentities($input, ENT_QUOTES | ENT_SUBSTITUTE | ENT_HTML5, 'UTF-8');
// 輸出: Tom & Jerry's "Adventure" <b>bold</b> café naïve résumé

// 2. 僅轉換必要字元 (htmlspecialchars 足夠)
echo htmlspecialchars($input, ENT_QUOTES | ENT_SUBSTITUTE | ENT_HTML5, 'UTF-8');
// 輸出: Tom & Jerry's "Adventure" <b>bold</b> café naïve résumé

// 3. 雙重編碼控制
$alreadyEncoded = '<script>alert(1)</script>';
echo htmlentities($alreadyEncoded, ENT_QUOTES, 'UTF-8', true);  // 預設雙重編碼
// &lt;script&gt;alert(1)&lt;/script&gt;
echo htmlentities($alreadyEncoded, ENT_QUOTES, 'UTF-8', false); // 保留現有實體
// <script>alert(1)</script>

// 4. 不同文檔類型
echo htmlentities('©®™', ENT_QUOTES, 'UTF-8', true, ENT_HTML401);
// ©®™ (HTML4.01 有定義)
echo htmlentities('©®™', ENT_QUOTES, 'UTF-8', true, ENT_HTML5);
// ©®™ (HTML5 同)
echo htmlentities('→←', ENT_QUOTES, 'UTF-8', true, ENT_HTML401);
// →← (HTML4.01 無定義,保留原字)
echo htmlentities('→←', ENT_QUOTES, 'UTF-8', true, ENT_HTML5);
// →← (HTML5 有定義)

常見錯誤與陷阱

  • 雙重編碼:已編碼字串再次編碼 → &amp;lt;。解決:double_encode = false 或統一在輸出層編碼
  • 字元集不匹配:GBK 字串用 UTF-8 編碼 → 亂碼/空字串。解決:iconv('GBK', 'UTF-8', $str) 先轉碼
  • ENT_IGNORE 導致資料遺失:無效編碼直接刪除。解決:改用 ENT_SUBSTITUTE
  • JavaScript 內容輸出:htmlentities 不足。需 json_encode() 或專用 JS 跳脫

現代框架整合模式

// Laravel Blade: {{ $var }} 自動 htmlspecialchars (非 htmlentities)
// CI4: esc($var) → htmlspecialchars
// Symfony Twig: {{ var|escape('html') }}
// 原生 PHP 模板建議封裝:
function e(string $str, int $flags = ENT_QUOTES | ENT_SUBSTITUTE | ENT_HTML5): string {
    return htmlspecialchars($str, $flags, 'UTF-8');
}

// 視圖中使用
<div class="user-input"><?= e($comment) ?></div>

效能微優化

  • 大量輸出時,htmlspecialchars 比 htmlentities 快 ~20%
  • 靜態內容模板預編譯階段預先編碼
  • 使用 opcache 加速函數呼叫

掌握旗標組合、字元集指定、雙重編碼控制,並根據專案類型選擇 htmlspecialchars (現代 HTML5) 或 htmlentities (舊系統/XML),能構建堅固的輸出端 XSS 防線。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
特性htmlentities()htmlspecialchars()
轉換範圍所有有 HTML 實體的字元 (含 accented chars、符號等)僅 & < > " ' 五個字元
輸出大小較大 (如 é → é)較小 (保留原字元)
適用場景舊系統、需純 ASCII 輸出、XML 文檔現代 HTML5 專案首選
效能稍慢較快