Subbi Reddy K
Subbi Reddy K

Reputation: 412

How to find the HTTP links in HTML mail using regular expressions in JavaScript

I am working on mail client application. I want to show all HTTP links as clickable hyper links.

I have noticed that some clients are sending HTTP links without enclosing them inside the anchor tags. In this case I am failing to show those links as clickable links.

My requirement is to find all HTTP links in a HTML mail and need to replace those links by enclosing them within anchor tags and also I need to exclude the links which are already in anchor tags or in source attribute of any tag.

Ex: Suppose my HTML mail is having the following text

Input:  "http://www.google.com/"     < a href = "http:\\gmail.com"></a>

After replacing I want the following out put

Output: <a href = "http://www.google.com"> </a> < a href = "http:\\gmail.com"></a>

I think I can not directly look for pattern which starts with http... because it can also come as src of any tag.

So Can some one help me to solve these issue

Thanks in advance

Subbi

Upvotes: 0

Views: 514

Answers (3)

FK82
FK82

Reputation: 5075

I just tested this expression:

/\s+("http:[^\s]+")\s+/g 

This will replace every quoted URL enclosed by whitespace. You use it like this:

var string = "\"http://www.google.com/\"     < a href = \"http:\\gmail.com\"></a>" ; //!! the email string you provided
var replaced = string.replace(/\s+("http:[^\s]+")\s+/g," <a href=$1></a> ") ;

Other than that, javascript does not support (negative) lookbehind in regex which one would need to perfectly identify whether the matched URL was within a html tag or not.

HTH ,

FK

Upvotes: 0

ManojMarathayil
ManojMarathayil

Reputation: 742

Check this:

(function($){
  $.fn.hyperlinkRegex = function(regex, target, ismailto) {
    ismailto = ismailto || false;
    if(regex == undefined || regex.source == '') {
      $(this).find('a').each(function(){
        $(this).replaceWith($(this).text());
        $(this).parent().each(function(){
          node = $(this).get(0);
          if(node.normalize) node.normalize();
        });
      });
    } else {
      $(this).each(function(){
        elt = $(this).get(0)
        elt.normalize();
        $.each($.makeArray(elt.childNodes), function(i, node){
          if(node.nodeType == 3) {
            var searchnode = node
            while((pos = searchnode.data.search(regex)) >= 0) {
              match = searchnode.data.slice(pos).match(regex)[0];
              if(match.length == 0) break;
              var anode = document.createElement('a');
              var middlebit = searchnode.splitText(pos);
              var searchnode = middlebit.splitText(match.length);
              var middleclone = middlebit.cloneNode(true);
              anode.appendChild(middleclone);
              if (ismailto == true) {
                anode.href = "mailto:" + middleclone.nodeValue;
              } else {
                anode.href = middleclone.nodeValue;
              }
              anode.target = target;
              searchnode.parentNode.replaceChild(anode, middlebit);
            }
          } else {
            $(node).hyperlinkRegex(regex, target, ismailto);
          }
        })
      })
    }
    return $(this);
  }
})(jQuery);

Usage:

// basic links
var exp = /(\b(https?|ftp|file):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig;
node.hyperlinkRegex(exp, "_blank", false);
// email
exp = /(\b[A-Z0-9._%-]+@[A-Z0-9.-]+\.[A-Z]{2,4}\b)/ig;
node.hyperlinkRegex(exp, "_blank", true);

Let me know this solves your problem

Upvotes: 0

Amadan
Amadan

Reputation: 198418

I believe you can't do it properly in one regexp; and also, obligatory link. Why are you keen on doing it with regexp if you're working in JavaScript? Your interpreter is boxed together with the archetypal HTML parsing engine: a web browser. Just delve into DOM and replace on text nodes.

If you're not doing it in JS and the tag is just misleading, and you can't find a decent HTML parsing library, then your best bet is to split the string by tags, replace on non-tag elements, then join back up, I think.

Upvotes: 2

Related Questions