2013-03-08 59 views
3

我已经创建了一个Html帮助程序来编码电子邮件地址以防止垃圾邮件。这是自动生成电子邮件链接时MarkdownSharp库使用的相同技术。从编码属性文本中阻止TagBuilder.MergeAttribute

问题是,TagBuilder.MergeAttribute编码断开链接的属性文本。是否有可能重写此行为或至少以另一种方式指定属性。我知道我可以退回到只使用字符串连接或StringBuilder,但TabBuilder确实提供了许多好处,例如轻松地合并其他HTML属性。

/// <summary> 
    /// Creates an encoded email link in the hopes of foiling most SPAM bots 
    /// </summary> 
    public static IHtmlString EmailLink(this HtmlHelper html, string email, string text = null, object htmlAttributes = null) 
    { 
     Ensure.Argument.NotNullOrEmpty(email, "email"); 

     var encodedEmail = EncodeEmailAddress(email); 

     var tb = new TagBuilder("a"); 
     tb.MergeAttribute("href", "mailto:" + encodedEmail); 

     tb.InnerHtml = text ?? encodedEmail; 

     if (htmlAttributes != null) 
     { 
      tb.MergeAttributes(new RouteValueDictionary(htmlAttributes)); 
     } 

     return new HtmlString(tb.ToString()); 
    } 

    /// <summary> 
    /// encodes email address randomly 
    /// roughly 10% raw, 45% hex, 45% dec 
    /// note that @ is always encoded and : never is 
    /// </summary> 
    private static string EncodeEmailAddress(string addr) 
    { 
     var sb = new StringBuilder(addr.Length * 5); 
     var rand = new Random(); 
     int r; 
     foreach (char c in addr) 
     { 
      r = rand.Next(1, 100); 
      if ((r > 90 || c == ':') && c != '@') 
       sb.Append(c);       // m 
      else if (r < 45) 
       sb.AppendFormat("&#x{0:x};", (int)c); // &#x6D 
      else 
       sb.AppendFormat("&#{0};", (int)c); // &#109 
     } 
     return sb.ToString(); 
    } 

回答

3

我不相信你的帮手会做任何有意义的事情来帮助减少垃圾邮件。当抓取工具使用HTML解析器时,他们看到解码的字符串,而不是编码的字符串。它与浏览器本身的逻辑相同。所以他们需要做的就是去掉mailto:前缀,他们现在有了原始的电子邮件地址。

如果你仍然希望追求这个,你必须使用字符串连接。 TagBuilder不适用于已经编码的输入。确保你编码&,'和'字符,如果你走这条路线

+0

当我在我的浏览器中查看链接的源时,我得到了编码的字符串*不*解码的,所以我假设这如果抓取工具没有使用解析器,它会是一样的吗? – 2013-03-10 12:26:39