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

PHP 正則解析 DedeCMS 模板標籤:支持無限嵌套、屬性提取、函數調用的完整實現

     編輯:PHP 綜合知識

目標標籤格式

{dede:tag attr='val' attr2="val2"} ... {/dede:tag}
{dede:tag attr='val' /}  
{dede:global.name /}
{dede:field.name function='html2text(@me)' /}
{dede:include filename='header.htm' /}

核心正則(支持遞歸嵌套)

$pattern = '/
    (                                   # 整體捕獲組 1
        \{dede:                         # 起始標記
        [^{}]*                          # 標籤名+屬性(不含大括號)
        (?:                             # 非捕獲組:兩種結束方式
            \/                          # 自閉合 />
          |                             # 或
            \}                          # 閉合 > 進入內容
            (?:                         # 內容部分(遞歸)
                [^{}]*                  # 非標籤文本
              |                         # 或
                (?R)                    # 遞歸匹配整個模式(嵌套標籤)
            )*
            \{/dede:                    # 結束標記
            [^{}]*                      # 標籤名
            \}
        )
    )
/x';
preg_match_all($pattern, $template, $matches);

解析邏輯(提取標籤名、屬性、函數、內容)

function parse_dede_tags(string $tpl): array {
    $tags = [];
    $pattern = '/\{dede:([^}\s\/]+)\s*([^}]*)\}(.*?)\{\/dede:\\1\}|\{dede:([^}\s\/]+)\s*([^}]*)\/\}/s';
    // 簡化版,實際建議用上述遞歸正則
    preg_match_all($pattern, $tpl, $m, PREG_SET_ORDER);
    foreach ($m as $match) {
        if (!empty($match[1])) { // 雙標籤
            [$full, $tag, $attrs, $content] = [$match[0], $match[1], $match[2], $match[3]];
        } else { // 自閉合
            [$full, $tag, $attrs] = [$match[0], $match[4], $match[5]];
            $content = '';
        }
        $attrArr = [];
        preg_match_all('/(\w+)\s*=\s*([\'"])(.*?)\\2/', $attrs, $am, PREG_SET_ORDER);
        foreach ($am as $a) {
            $attrArr[$a[1]] = $a[3];
            if ($a[1] === 'function') $func = $a[3];
        }
        $tags[] = [
            'raw' => $full,
            'tag' => $tag,
            'attrs' => $attrArr,
            'function' => $func ?? null,
            'content' => $content,
        ];
    }
    return $tags;
}

輸出示例

[
  'raw' => "{dede:list pagesize='10'}{dede:field.title/}{/dede:list}",
  'tag' => 'list',
  'attrs' => ['pagesize' => '10'],
  'function' => null,
  'content' => "{dede:field.title/}"
]

注意事項

  • 正則性能:極大模板(>1MB)遞歸正則可能回溯過深,建議分塊解析或用狀態機/解析器生成器(如 PHP-Parser 改造)。
  • 屬性值含引號轉義:function='html2text(@me)' 內單引號需處理。
  • 編碼統一:模板文件讀取時指定 mb_convert_encoding($tpl, 'UTF-8', 'GBK')。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved