Regex,用于将文本链接转换为<;a href="">;标签在某个用例中中断


Regex for converting text links to <a href=""> tags breaks in a certain use case

我有这个正则表达式代码:

$hike_description = nl2br($hike_description);
//$hike_description = str_replace(array(''n',''r'),'',$hike_description);
//Convert all urls to links
$hike_description = preg_replace('#(['s|^])(www)#i', '$1http://$2', $hike_description);
$pattern = '#((http|https|ftp|telnet|news|gopher|file|wais):'/'/[^'s]+)#i';
$replacement = '<a href="$1" target="_blank">$1</a>';
$hike_description = preg_replace($pattern, $replacement, $hike_description);

它100%有效。。。。直到现在。

在这个页面中,代码第一次不起作用。具体来说,它没有把"放在链接的末尾,所以链接一直在页面的其余部分:

http://www.comehike.com/hikes/scheduled_hike.php?hike_id=209

你看到了从页面中间的链接是如何一直延伸到底部并且没有关闭的吗?

有什么线索可以解释为什么这次会发生而不是其他时候吗?

谢谢!

ps-这是最终出现在页面上的HTML:

<a href="http://maps.google.com/maps?um=1&ie=UTF-8&q=little+river+canyon+center&fb=1&gl=us&hq=little+river+canyon+center&hnear=0x888a614b2e7272e5%3A0x913a5fafeec714d6%2CCentre%2C+AL&ei=GBsFTtedF8vUgAfex6zNAQ&sa=X&oi=local_group&ct=image&ved=0CAQQtgM<br" target="_blank">http://maps.google.com/maps?um=1&ie=UTF-8&q=little+river+canyon+center&fb=1&gl=us&hq=little+river+canyon+center&hnear=0x888a614b2e7272e5%3A0x913a5fafeec714d6%2CCentre%2C+AL&ei=GBsFTtedF8vUgAfex6zNAQ&sa=X&oi=local_group&ct=image&ved=0CAQQtgM<br</a> />

正则表达式要求URL包含下一个空格字符之前的所有字符。紧跟在URL后面的是一个html <br />标记,正则表达式看到的下一个空格是该标记中/>之前的空格。因此,它认为URL在该标签的开头也包含了<br。当添加结束</a>时,它被放置在<br />标签内,因此无效。

为了快速解决这个特定问题,请尝试更改正则表达式以查找<字符以及作为URL终止符的空格:

$pattern = '#((http|https|ftp|telnet|news|gopher|file|wais):'/'/[^<'s]+)#i';
                                                         --------^^^----

编辑我认为这才是问题的真正根源:

另一种可能性是在进行文本替换之后而不是之前调用nl2br()。该<br />标记可能事先是换行符。换行符会被正则表达式解释为空格,正则表达式的替换也不会阻塞。

尝试将您的模式更改为:

$pattern = '#((http|https|ftp|telnet|news|gopher|file|wais):'/'/[^'s<.]+)#i';

问题是,正则表达式假设链接在遇到空格时结束,但在这种特殊情况下,它以左尖括号结束,左尖括号是
标记

的开始

链接以<br结束。这启动了一个标签,但你永远不会关闭它。它还"吃掉"了本应关闭打开的<a></a>。在将输入放到页面之前,您需要对其进行转义。

请注意,您可能想要转义其他字符,例如&。你可能想检查这个问题的答案:

  • PHP中的Html编码

具体来说,这个页面:

  • http://php.net/manual/function.htmlentities.php