【问题标题】:Regex match multiple occurrence of a js function between <script.* and </script> tag正则表达式匹配 <script.* 和 </script> 标记之间多次出现的 js 函数
【发布时间】:2020-05-02 12:55:46
【问题描述】:

我希望有人可以帮助我...我不是正则表达式专家,我正在寻找处理文本替换的解决方案。

我有一个这样的 HTML 代码:

<script>
...something here...
</script>

<script type="text/javascript">
...something here...
</script>

...something here...

<script type="text/javascript">
1st occurrence
...something here...
fbq(...something here...)
...something here...
</script>

...something here...

<script type="text/javascript">
2nd occurrence
...something here...
fbq(...something here...)
</script>

...something here...

我需要找到 ' 之间包含函数 fbq 的所有字符串。所以在我的例子中,我需要:

组 1:

<script type="text/javascript">
//1st occurrence
...something here...
fbq(...something here...)
...something here...
</script>

组2:

<script type="text/javascript">
2nd occurrence
...something here...
fbq(...something here...)
</script>

如果出现次数更多,依此类推。我认为有更多的比赛而不是更多的组也很好。

注意事项:我的代码中可能有很多 &lt;script 字符串不包含 'fbq' 函数,我无法确定它们的位置以及是否在换行符中。

我尝试了许多正则表达式代码,但找不到有效的方法。

即通过使用

(?:^.*)(<script.*fbq.*<\/script>)(?:.*$)

.*(<script.*fbq.*<\/script>).*

我只能找到 fbq 的最后一次出现(在我的示例中只有第二次出现)。

我也尝试过加入团体,但没有成功。

然后我需要在 PHP 代码中使用这个正则表达式,使用 preg_replace 进行替换

非常欢迎任何建议

提前致谢!

【问题讨论】:

  • Nonono - 改用适当的解析器(例如DOMDocument)。
  • 从未使用过 DOMDocument 但是是的......这似乎是一个更好的解决方案。我正在查看有关该功能的文档

标签: php regex


【解决方案1】:

您必须解析 HTML,找到想要的元素并使用正则表达式来获取元素内容。 HTML 代码中的文本搜索(来自其他来源)是非常随机的游戏。试试 DOMDocument 和 DOMXPath

        $doc = new \DOMDocument;
        $doc->preserveWhiteSpace = 0;
        $doc->strictErrorChecking = 0;
        libxml_use_internal_errors(true);

        $doc->loadHTML($html);

        $xpath = new \DOMXPath($doc);
        // search all script element as nodeList
        $nodeList = $xpath->query('//script');
        foreach ($nodeList as $node) {

            $node->nodeValue = 'Hello, world!'; // or some text changes,
            // but remember that comments are special nodes in DOM
            $node->parentNode->replaceChild($node, $node);
        }

        print $doc->saveHTML();

【讨论】:

  • 你可以使用类似//script[contains(., "fbq")]的东西来表示脚本标签必须包含文本fbq
  • @NigelRen 谢谢,我确认它在包含添加的情况下也可以正常工作!
  • @Pavel Musil 你知道是否也可以更改
  • @Fabio - 当然,只需使用$node-&gt;setAttribute('attr_name', 'attr_value');
  • 如果你想创建新元素,那么使用$newNode = $doc-&gt;createElement('element_name', 'element_text_value'); replaceChild把它放到dom结构中。
【解决方案2】:

也许将来对某人有用,这是我的最终代码:

function fix_iubenda_pixelWoocommerce( $buffer ) {
        $doc = new \DOMDocument;
        $doc->preserveWhiteSpace = 0;
        $doc->strictErrorChecking = 0;
        libxml_use_internal_errors(true);

        $doc->loadHTML($buffer);

        $xpath = new \DOMXPath($doc);
        $nodeList = $xpath->query('//script[contains(., "fbq(")]');
        foreach ($nodeList as $node) {
                $node->nodeValue = $node->nodeValue ;
                $node->setAttribute('type', 'text/plain');
                $node->setAttribute('class', '_iub_cs_activate-inline');
        }

        $buffer = $doc->saveHTML();
        return $buffer;
}

再次感谢 Pavel 和 Nigel 帮助我!

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-09-19
    • 2012-02-24
    • 1970-01-01
    • 2021-02-19
    • 1970-01-01
    • 1970-01-01
    • 2016-10-14
    • 1970-01-01
    相关资源
    最近更新 更多