安全地解析Markdown风格链接

时间:2014-07-27 20:48:41

标签: php regex xss markdown

我编写了一些代码来匹配和解析这种风格的Markdown链接:

[click to view a flower](http://www.yahoo.com/flower.html)

我有这个代码用于提取链接文本,然后是网址本身,然后将它们粘贴在A HREF链接中。我很担心,也许我错过了某人注射XSS的方法,因为我要留下相当数量的角色。这样安全吗?

$pattern_square = '\[(.*?)\]';
$pattern_round  = "\((.*?)\)";

$pattern = "/".$pattern_square.$pattern_round."/";

preg_match($pattern, $input, $matches);
$words = $matches[1];
$url   = $matches[2];

$words = ereg_replace("[^-_@0-9a-zA-Z\.]", "", $words);
$url   = ereg_replace("[^-A-Za-z0-9+&@#/%?=~_|!:.]","",$url);

$final = "<a href='$url'>$words</a>";

它似乎工作正常,确实排除了一些包含分号和反斜杠的愚蠢网址,但我并不关心这些网址。

1 个答案:

答案 0 :(得分:2)

如果您已通过htmlspecialchars 正在做什么?)传递了输入,那么链接已经无法包含任何内容可能导致XSS的字符。

如果你还没有通过htmlspecialchars传递输入,那么在解析链接时你所做的过滤并不重要,因为你已经搞砸了,因为一个人可以简单地包含任意内容HTML或XSS 外部链接。

此功能可以在文本上应用htmlspecialchars时安全地解析Markdown链接:

function doMarkdownLinks($s) {
    return preg_replace_callback('/\[(.*?)\]\((.*?)\)/', function ($matches) {
        return '<a href="' . $matches[2] . '">' . $matches[1] . '</a>';
    }, htmlspecialchars($s));
}

如果你需要做一些比这更复杂的事情,我建议你使用一个现有的解析器,因为这样做太容易弄错了。