【问题标题】:Javascript Regex to replace URLs with links, but not in embed (or img) tagsJavascript 正则表达式用链接替换 ​​URL,但不在嵌入(或 img)标签中
【发布时间】:2010-02-01 14:02:53
【问题描述】:

我目前正在使用以下代码在页面上的 div 中搜索 URL 并将它们替换为标签。

但是,当我们在 div 中嵌入标签时,它会弄乱这些标签中的链接。

function replaceURLWithHTMLLinks(text) { 
    return text.replace(/(ftp|http|https|file):\/\/[\S]+(\b|$)/gim,'<a href="$&" class="my_link" target="_blank">$&</a>').replace(/([^\/])(www[^ <]+(\b|$))/gim,'$1<a href="http://$2" class="my_link" target="_blank">$2</a>');
}

$(document).ready(function(){
    var htmlStr = $("div.content-a").html();
    var htmlStrAfter = replaceURLWithHTMLLinks(htmlStr);
    $("div.content-a").html(htmlStrAfter);
});

谁能告诉我们如何排除任何前面有 " 或 ' 的 http://...?

还是类似的?

【问题讨论】:

  • 如果你有 JavaScript,为什么不使用 DOM 而不是 HTML 文本呢?正则表达式 HTML 解析已经够难了,而且 JS 没有lookbehind,这让你的要求有点讨厌。

标签: javascript regex


【解决方案1】:

您可能应该按照建议使用 DOM。但为了使您的正则表达式按需要工作,您应该在它前面加上(?:^|[^"'])。这意味着匹配行首或匹配除'" 之外的任何字符。因此,您的第一个正则表达式将如下所示:

/(?:^|[^"'])(ftp|http|https|file):\/\/[\S]+(\b|$)/gim  

而且你的replace 方法的链接很丑陋。如果您将方法调用拆分到不同的行,代码将更具可读性。

更新:为了跳过第一个多余的字符,您可以使用 $1 而不是 $&amp; 并且您的正则表达式必须更改为:

/(?:^|[^"'])((ftp|http|https|file):\/\/[\S]+(\b|$))/gim  

【讨论】:

    【解决方案2】:

    +1 约翰内斯所说的话...

        $(document).ready(function(){
           $('div.content').contents().filter(function() {
             return this.nodeType == 3;
           }).each(function(){
                 this.nodeValue.replace(/(ftp|http|https|file):\/\/[\S]+(\b|$)/gim,'<a href="$&" class="my_link" target="_blank">$&</a>').replace(/([^\/])(www[^ <]+(\b|$))/gim,'$1<a href="http://$2" class="my_link" target="_blank">$2</a>');
           });
        });
    

    请注意,上面的代码未经测试,但它应该看起来像我相信的那样。

    【讨论】:

    • 即使我将 'div.content' 更改为 'div.content-a',我似乎也无法让它工作。这个 div 通常包含文本和几个 div。但是,它还包含一个带有嵌入标签的表格。还有一个在 alt 中带有 URL 的 img 标签(我们系统的怪癖)。
    • 好吧,假设它根本不能工作,因为除非你的选择器不匹配任何东西,否则应该没有区别......你会发生什么错误?
    • 顺便说一句 - 我只是使用了你的正则表达式 - 我认为除了在标签中捕获 url 之外,我的代码只尝试错过标签 - 如果正则表达式本身不起作用,那么也许重新制定它 Rorick 有一些很好的建议据我所知,但我没有正则表达式忍者 :-)
    • 正则表达式有效,但您的代码似乎过滤了所有标签。 div 中的内容不包含在任何

      标记中,只是带有可选内联嵌入标记的纯文本。

    • 那不应该对标签做任何事情...contents() 将获取选择器的所有子节点,包括文本节点(文本节点是你想要的)然后 if 语句应该测试节点是一个文本节点(nodeType = 3 = text)......或者至少它应该......我将其更改为使用jquery的过滤器方法,而不是看看这是否有所作为。
    猜你喜欢
    • 1970-01-01
    • 2011-11-20
    • 2015-03-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-09
    相关资源
    最近更新 更多