萬盛學電腦網

您现在的位置: 萬盛學電腦網 >> 程式設計 >  >> 網路程式設計 >> PHP 程式設計

PHP 正則解析 HTML 表單:提取所有 form、input、select、textarea 元素屬性完整實作

需從任意 HTML 頁面提取所有表單結構 (action、method、input/select/textarea 的 name/type/value/options) 以建立自動化測試、爬蟲或安全掃描器。本文提供完整正則解析器實作,逐層拆解 form → 元素 → 屬性。

目標 HTML 範例 (含兩個 form、多種元素類型)

<form action="register.php" method="post">
  <input type="hidden" name="cookie" value="SJKjki80KJ8jkl2" />
  <input type="text" name="name" required />
  <input name="password" type="password" required="required" />
  <input name="age" value="22" required />
  <input type="radio" name="sex" value="1" /> 男
  <input type="radio" name="sex" value="0" /> 女
  <select name="area">
    <option value="jiangsu">江蘇</option>
    <option value="shandong">山東</option>
  </select>
  <textarea name="summary">個人簡介</textarea>
  <input type="submit" name="register" value="註冊" />
</form>

<form action="login.php" method="post">
  <input type="text" name="name" required />
  <input name="password" type="password" />
  <textarea name="remark">2</textarea>
  <input type="submit" name="register" value="登入" />
</form>

解析器核心架構:分層正則 + 陣列組裝

<?php
function parse_forms($html) {
    $forms = [];
    // 1. 擷取所有 
...
區塊 (s 單行模式讓 . 匹配換行) if (!preg_match_all('/(.*?)<\/form>/si', $html, $m)) return $forms; for ($i = 0; $i < count($m[0]); $i++) { $formAttrs = $m[1][$i]; // form 標籤屬性字串 $formInner = $m[2][$i]; // form 內部 HTML $forms[$i]['action'] = attr($formAttrs, 'action'); $forms[$i]['method'] = attr($formAttrs, 'method') ?: 'get'; // 2. 解析 input if (preg_match_all('/]*>/si', $formInner, $im)) { foreach ($im[0] as $inp) { $forms[$i]['inputs'][] = [ 'name' => attr($inp, 'name'), 'type' => attr($inp, 'type') ?: 'text', 'value' => attr($inp, 'value'), ]; } } // 3. 解析 textarea if (preg_match_all('/]*>(.*?)<\/textarea>/si', $formInner, $tm)) { foreach ($tm[0] as $idx => $tag) { $forms[$i]['textarea'][] = [ 'name' => attr($tag, 'name'), 'value' => $tm[1][$idx], // 內容在捕獲組 1 ]; } } // 4. 解析 select + options if (preg_match_all('/(.*?)<\/select>/si', $formInner, $sm)) { foreach ($sm[0] as $idx => $tag) { $select = ['name' => attr($sm[1][$idx], 'name'), 'options' => []]; // 解析 option if (preg_match_all('/]*value=["\']([^"\']*)["\'][^>]*>/si', $sm[2][$idx], $om)) { $select['options'] = $om[1]; } $forms[$i]['select'][] = $select; } } } return $forms; } // 通用屬性提取輔助函數 function attr($tag, $name) { if (preg_match('/' . $name . '\s*=\s*(["\'])(.*?)\1/i', $tag, $m)) { return $m[2]; } return null; } // 使用範例 $html = file_get_contents('1.html'); $forms = parse_forms($html); print_r($forms);

輸出結構範例

Array
(
    [0] => Array
        (
            [action] => register.php
            [method] => post
            [inputs] => Array
                (
                    [0] => Array ( [name] => cookie [type] => hidden [value] => SJKjki80KJ8jkl2 )
                    [1] => Array ( [name] => name [type] => text [value] => )
                    ...
                )
            [textarea] => Array ( [0] => Array ( [name] => summary [value] => 個人簡介 ) )
            [select] => Array
                (
                    [0] => Array ( [name] => area [options] => Array ( [0] => jiangsu [1] => shandong ) )
                )
        )
    [1] => Array ( ... login form ... )
)

正則局限與進階建議

  • HTML 非正則語言:巢狀標籤、屬性含 `>`、註解、CDATA、動態屬性 (Vue/React 模板) 皆會導致正則失效或誤匹配。
  • 生產環境請用 DOMDocument / DOMXPath:
$dom = new DOMDocument();
@$dom->loadHTML($html); // 抑制 HTML5 標籤警告
$xpath = new DOMXPath($dom);
$forms = $xpath->query('//form');
foreach ($forms as $form) {
    $action = $form->getAttribute('action');
    $inputs = $xpath->query('.//input', $form);
    // ... 結構化提取,健壯度遠超正則
}
  • 安全性** (重要)**:解析不可信 HTML 時,`loadHTML` 可能執行惡意實體/腳本,建議配合 `libxml_disable_entity_loader(true)` (PHP 8.0+ 預設關閉) 並移除 `
  • copyright © 萬盛學電腦網 all rights reserved