2010-05-10 50 views
0

將字符串中的純文本鏈接轉換爲錨標記的最佳選擇是什麼?用字符串中的錨標籤替換純文本鏈接最好的辦法是什麼? .NET

說例如我有「我今天去搜索了http://www.google.com/」。我想將其改爲「我今天去搜索http://www.google.com/」。

由於字符串是用戶生成的,因此該方法對於任何類型的XSS攻擊都必須是安全的。解析前它們將是安全的,所以我只需要確保沒有通過解析URL來引入漏洞。

回答

1

一個簡單的正則表達式可以讓你得到你想要的,因爲你說在解析之前字符串將是安全的。只需使用以下方法。

private static readonly Regex urlRegex = new Regex(@"(?<Protocol>\w+):\/\/(?<Domain>[\[email protected]][\w.:@]+)\/?[\w\.?=%&=\[email protected]/$,]*", RegexOptions.Compiled); 
private static readonly Regex emailRegex = new Regex(@"([a-zA-Z0-9_\-\.]+)@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.)|(([a-zA-Z0-9\-]+\.)+))([a-zA-Z]{2,4}|[0-9]{1,3})", RegexOptions.Compiled); 
private static readonly IEnumerable<string> disallowedProtocols = new[] { "javascript", "ftp" }; 
private static string ConvertUrls(string s) { 
    s = emailRegex.Replace(
      s, 
      match => string.Format(CultureInfo.InvariantCulture, "<a href=\"mailto:{0}\" rel=\"nofollow\">{0}</a>", match.Value) 
     ); 

    s = urlRegex.Replace(
      s, 
      match => { 
       var protocolGroup = match.Groups["Protocol"]; 
       if (protocolGroup.Success && !disallowedProtocols.Contains(protocolGroup.Value, StringComparer.OrdinalIgnoreCase)) { 
        return string.Format(CultureInfo.InvariantCulture, "<a href=\"{0}\" rel=\"nofollow\">{0}</a>", match.Value); 
       } else { 
        return match.Value; 
       } 
      } 
     ); 

    return s; 
} 
+0

'的JavaScript:警報( 'XSS')' – SLaks 2010-05-10 16:22:47

+1

我改變了我的代碼有點禁止某些協議,如 「ftp」,但如果用戶剛剛進入 「的javascript:警報( 'XSS')」,我正則表達式不會撿起來,所以你可以放心。 – 2010-05-10 16:35:42

+0

應該可以寫出通過你的正則表達式的惡意Javascript(我懶得做一個例子),所以你確實需要禁止'javascript:'。 – SLaks 2010-05-10 17:16:26