Получить все адреса электронной почты в строке с JavaScript - PullRequest
1 голос
/ 06 мая 2010

Итак, у меня есть эта функция JavaScript:

ME.Utils = {
    RxEmail: new RegExp(/^(("[\w-\s]+")|([\w-]+(?:\.[\w-]+)*)|("[\w-\s]+")([\w-]+(?:\.[\w-]+)*))(@((?:[\w-]+\.)*\w[\w-]{0,66})\.([a-z]{2,6}(?:\.[a-z]{2})?)$)|(@\[?((25[0-5]\.|2[0-4][0-9]\.|1[0-9]{2}\.|[0-9]{1,2}\.))((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[0-9]{1,2})\.){2}(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[0-9]{1,2})\]?$)/i),

    ValidateEmail: function(email) {
        return ME.Utils.RxEmail.test(email);
    },

    GetEmailAddresses: function(text) {
        return text.match(ME.Utils.RxEmail);
    },

    HasEmail: function(text) {
        return ME.Utils.GetEmailAddresses != null;
    }
};

ValidateEmail работает очень хорошо.Однако HasEmail и GetEmailAddresses не работают должным образом.

GetEmailAdresses всегда возвращает null, за исключением случаев, когда строка содержит только адрес электронной почты.В этом случае GetEmailAdresses возвращает массив, содержащий не только адрес электронной почты, но и адрес электронной почты (test@test.com), только идентификатор (test), а также некоторые неопознанные и т. Д. И т. Д. *

Можете ли вы помочь мне понять, что не так в моем выражении?

Ответы [ 4 ]

4 голосов
/ 06 мая 2010

Есть несколько проблем.

  1. Ваше регулярное выражение привязано в начале и конце строки. Из него следует удалить символы ^ и $.

  2. Если вы хотите вернуть только адреса электронной почты, используйте группы без захвата.

  3. В HasEmail() вы не звоните GetEmailAddresses(). Вы фактически проверяете, определено ли значение этого свойства.

В целом исправленная версия может выглядеть так:

ME.Utils = {
    RxEmail: /(?:(?:"[\w-\s]+")|(?:[\w-]+(?:\.[\w-]+)*)|(?:"[\w-\s]+")(?:[\w-]+(?:\.[\w-]+)*))(?:@(?:(?:[\w-]+\.)*\w[\w-]{0,66})\.(?:[a-z]{2,6}(?:?:\.[a-z]{2})?))|(?:@\[?(?:(?:25[0-5]\.|2[0-4][0-9]\.|1[0-9]{2}\.|[0-9]{1,2}\.))(?:(?:25[0-5]|2[0-4][0-9]|1[0-9]{2}|[0-9]{1,2})\.){2}(?:25[0-5]|2[0-4][0-9]|1[0-9]{2}|[0-9]{1,2})\]?)/gi,

    ValidateEmail: function(email) {
        // We can't do a simple test() since we're using an unanchored regex now.
        var match = ME.Utils.RxEmail.match(email);
        return match.length == 1 && match[0] == email;
    },

    GetEmailAddresses: function(text) {
        return text.match(ME.Utils.RxEmail);
    },

    HasEmail: function(text) {
        return ME.Utils.GetEmailAddresses(text) != null;
    }
};
2 голосов
/ 06 мая 2010

Ваше регулярное выражение специально соответствует всей строке

RxEmail: new RegExp(/^ ... $)/i),

^ и $ соответствуют началу и концу ввода соответственно. попробуйте удалить этих персонажей и посмотреть, как вы попали?

1 голос
/ 06 мая 2010

Причина, по которой вы получаете несколько записей в массиве при представлении его с адресом электронной почты, заключается в том, что в вашем выражении есть группы захвата. В Javascript результатом совпадения является массив, где индекс 0 - это общая совпадающая строка, а затем есть (необязательно) дополнительные индексы для каждой группы захвата. Вы можете запретить захват своих групп, изменив их с (...) на (?:...).

Что касается того, почему вы не получаете ожидаемых результатов при использовании GetEmailAddresses со строкой , содержащей адрес электронной почты, попробуйте вместо этого:

GetEmailAddresses: function(text) {
    var rv = [];
    var match;

    while (match = ME.Utils.RxEmail.exec(text)) {
        rv.push(match[0]);
    }
    return rv.length == 0 ? null : rv;
},

См. Этот вопрос и ответ , я не могу сказать, что знаю , почему String#match не совсем то же самое, что и цикл RegExp#exec выше, но это не так т.

Редактировать И вам нужно будет исправить проблему, на которую oedo указал также ; RegExp должен быть разрешен для соответствия подстрок.

1 голос
/ 06 мая 2010
if (emailMatch = ME.Utils.GetEmailAddresses(myEmail))
  // do stuff with emailMatch[1]
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...