我运行一个托管在github上的开源项目。我目前正准备发布一个在PHP 7上运行的新版本。这是我需要帮助的地方。我对大多数PHP函数都相当强大,同样对mysqli
感到满意,但在我运行项目时,我从未使用过正则表达式。我有两种模式,现在已经失效的/e
修饰符正在使用中,并且不知道如何修复它们,所以我希望通过在这里提出问题来实际学习并解决我的问题。
问题一来自preg_replace
我用于代码标记的Geshi语法高亮显示。
// [php]code[/php]
if (stripos($s, '[php]') !== false) {
$s = preg_replace("#\[(php|sql|html)\](.+?)\[\/\\1\]#ise", "source_highlighter('\\2','\\1')", $s);
}
第二个处理媒体标签,如liveleak等:
if (stripos($s, '[media=') !== false) {
$s = preg_replace("#\[media=(youtube|liveleak|GameTrailers|vimeo|imdb)\](.+?)\[/media\]#ies", "_MediaTag('\\2','\\1')", $s);
}
两者都无效并抛出此错误:
PHP警告:preg_replace():不再支持/ e修饰符,而是使用preg_replace_callback。
麻烦是我不知道如何使用正则表达式,我在过去几周尝试过使用教程但仍然不太了解它,任何帮助都会非常感激。
答案 0 :(得分:2)
PHP手册以这种方式描述修饰符:(强调我的)
如果设置了此deprecated修饰符,
preg_replace()
会正常 替换替换字符串中的反向引用,eval
s 作为PHP代码(!!),并使用结果替换搜索字符串。 单引号,双引号,反斜杠()和NULL字符将是 在替代后向引用中被反斜杠转义。
首先,这个修饰符的概念始终是 evil。它包含一个eval
案例到源代码中,其存在通常被忽略,因此很容易被利用
在线PHP文档...... http://php.net/manual/en/reference.pcre.pattern.modifiers.php ...非常广泛地讨论了这个修饰符,为什么它是邪恶的,特别是如何使用preg_replace_callback()
来替换它。
让我们来看看你的第一个正则表达式,即“Geshi语法”:
$s = preg_replace(
"#\[(php|sql|html)\](.+?)\[\/\\1\]#ise",
"source_highlighter('\\2','\\1')",
$s);
这可以用以下内容代替:
$s = preg_replace_callback(
"#\[(php|sql|html)\](.+?)\[\/\\1\]#ise",
function($subs) {
return source_highlighter($subs[2], $subs[1]);
},
$s);
在针对字符串评估正则表达式并且已识别匹配组(如果有)之后,将数组传递给回调。 (该数组看起来像是正常匹配返回的数组。)回调返回的值是最终的替换字符串。
现在,可执行子程序的存在是显式的, 和,聪明的L33T H4X0R
不可能影响它的组成或注入任意代码。
此外,它更灵活。毕竟,您可以插入整个子例程。 (它可以是匿名的,如图所示,也可以是对多次使用的子程序的引用。)
坦率地说,/e
修饰符是错误的想法,不会错过。 。 。回调做同样的事情,还有更多。