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

PHP strip_tags() 嚴重 Bug:殘破標簽導致數據大量丟失及修復方案

     編輯:PHP 相關知識

strip_tags() 旨在移除 HTML/PHP 標簽,但官方文檔明確警告:**無法驗證 HTML 完整性,殘破標簽將導致更多數據被誤刪**。

Bug 復現

$str = '<div>string</div>string<string<b>hello</b><div>string</div>';
echo strip_tags($str, '<div>');

預期:保留 <div>,其餘標簽移除,文本保留

實際輸出:<div>string</div>string

原因:<string 中的孤立 < 被誤判為標簽開始,導致後續所有內容被吞噬。

修復函數:fixtags()

function fixtags($text) {
    $text = htmlspecialchars($text); // 先實體化所有特殊字符
    $text = preg_replace("/&quot;/", "&quot;\"", $text); // 還原引號
    
    // 匹配完整標簽結構並還原
    $tags = "/&lt;(!|)(\/|)(\w*)(\ |)(\w*)([\\\=]*)(?|(\")\"&quot;\"|)(?|(.*)?&quot;(\")|)([\ ]?)(\/|)&gt;/i";
    $replacement = "<$1$2$3$4$5$6$7$8$9$10$11>";
    $text = preg_replace($tags, $replacement, $text);
    
    $text = preg_replace("/=\"\"/", "=", $text);
    $text = preg_replace("/&quot;\"/", "\"", $text);
    return $text;
}

使用方法

strip_tags(fixtags($string), '<div>');

原理與代價

性能警示

大數據量慎用! 正則回溯在長文本中極其耗時,可能導致請求超時。建議:
  • 輸入長度 > 10KB 時拒絕處理或異步隊列
  • 優先使用 HTMLPurifier 等成熟庫
  • 前端輸入端攔截非法標簽

現代替代方案

  • HTMLPurifier:標準化、安全、可配置白名單
  • DOMDocument::loadHTML():原生解析樹操作,性能較好
  • Tidy 擴展:修復不規範 HTML 後再處理

strip_tags() 適合簡單、可信、短文本場景。面對複雜用戶生成內容,請選擇專業 HTML 清洗庫。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
步驟作用副作用
htmlspecialchars將 < > " 實體化所有標簽失效,純文本化
正則還原合法標簽按標準結構匹配並還原 <tag attr="val">極其複雜的正則,性能開銷大
清理殘留實體還原屬性值引號、等號可能誤傷合法文本中的實體