Checklist to achieve proper email verification

This is what a proper email verification consists of:

  • Syntax validation
  • Check for disposable emails
  • Check for obvious typos
  • Look up DNS
  • Ping email box

Syntax validation

Let’s take a regular email address: example@mailtrap.io. It consists of local (example) and domain (mailtrap.io) parts.

The local part can contain:

  • alphanumeric characters – A to Z (both upper and lower case) and 0 to 9
  • printable characters – !#$%&'*+-/=?^_`{|}~
  • a dot . (the local part cannot start and end with a dot, and you can’t use the dot consecutively like example..first@mailtrap.io).

The domain part can contain alphanumeric characters (both upper and lower case). It can also contain a hyphen if it is not the first or last character. The hyphen cannot be used consecutively.

These validation rules can be implemented in a regular expression or RegEx to verify the email address syntax. However, do not limit the verification to a RegEx rule only. You should also consider IETF standards, ISP-specific syntax checking, quoted words, domain literals, non-ASCII domains, and so on. If you’re building your app using Angular, React, or React Native, check our respective blog posts dedicated to email validation:

Check for disposable email address

A disposable email address is a temporary address that is valid for some time. You should clean your mail of any disposable emails generated by Nada, Mailinator, and similar services. You can make use of a third-party API, such as InboxHit. Those can reliably detect disposable email addresses. Also, you may search for a list of domains used for temporary email addresses and use them in your RegEx.

DNS lookup

A DNS lookup is the process of requesting a DNS record from a DNS server. In our case, we’re interested in the MX record. It is a DNS entry that specifies an email server for accepting emails for the domain name. Here is an example of a DNS lookup for mailtrap.io:

  • Open your console app and run the following command:
nslookup –type=mx mailtrap.io
  • You’ll see a number of MX records for domain “mailtrap.io” and their priority values:
mailtrap.io     MX preference = 5, mail exchanger = alt2.aspmx.l.google.com
mailtrap.io MX preference = 1, mail exchanger = aspmx.l.google.com
mailtrap.io MX preference = 10, mail exchanger = aspmx2.googlemail.com
mailtrap.io MX preference = 10, mail exchanger = aspmx3.googlemail.com
mailtrap.io MX preference = 5, mail exchanger = alt1.aspmx.l.google.com
  • Pick the email server with the highest priority. The smaller is the preference value, the higher is the priority. In our case, this is “aspmx.l.google.com” You’ll need this input for the next step of the checklist.

Email box pinging

After the DNS lookup, you can verify the email address via SMTP connection. You need to connect to the chosen SMTP server and check if an email address exists. If the server replies with (250 OK), the email address is valid. If the client gets a negative response (550-5.1.1 User Unknown), the address does not exist. For the following manipulations, you’ll need a console app and Telnet.

  • Connect to the email server on standard SMTP port 25:
telnet aspmx.l.google.com 25

Here is the response that establishes the SMTP handshake:

220 mx.google.com ESMTP z23si732378lfb.34 - gsmtp
  • Commence the SMTP conversation
EHLO mailtrap.io

Here is the response:

250-mx.google.com at your service, [31.42.66.68]
250-SIZE 157286400
250-8BITMIME
250-STARTTLS
250-ENHANCEDSTATUSCODES
250-PIPELINING
250-CHUNKING
250 SMTPUTF8
  • Now, you need to specify the sender email address using the MAIL FROM: command:
mail from:<sender@example.io>

Response:

250 2.1.0 OK z23si732378lfb.34 - gsmtp
  • Eventually, you can do the email address verification. Enter the recipient email address using the RCPT TO: command:
rcpt to:<new-recipient@mailtrap.io>

We’ve got 550-5.1.1 code response since the recipient was fake:

550-5.1.1 The email account that you tried to reach does not exist. Please try
550-5.1.1 double-checking the recipient's email address for typos or
550-5.1.1 unnecessary spaces. Learn more at
550 5.1.1 https://support.google.com/mail/?p=NoSuchUser z23si732378lfb.34 - gsmtp

On the other hand, if you get 250 OK, this will show that the email address is valid.

  • After that, you can close the conversation with the QUIT command.

Here is how the entire SMTP session to verify the invalid recipient looks:

C: ehlo mailtrap.io
S: 250-mx.google.com at your service, [31.42.66.68]
250-SIZE 157286400
250-8BITMIME
250-STARTTLS
250-ENHANCEDSTATUSCODES
250-PIPELINING
250-CHUNKING
250 SMTPUTF8
C: mail from:<sender@example.com>
S: 250 2.1.0 OK q25si5330153lfb.56 - gsmtp
C: rcpt to:<new-recipient@mailtrap.io>
S: 550-5.1.1 The email account that you tried to reach does not exist. Please try
550-5.1.1 double-checking the recipient's email address for typos or
550.1.1 unnecessary spaces. Learn more at
550 5.1.1 https://support.google.com/mail/?p=NoSuchUser q25si5330153lfb.56 - gsmtp
C: quit
S: 221 2.0.0 closing connection q25si5330153lfb.56 - gsmtp

And here is the session for a valid email address:

C: ehlo mailtrap.io
S: 250-mx.google.com at your service, [31.42.66.68]
250-SIZE 157286400
250-8BITMIME
250-STARTTLS
250-ENHANCEDSTATUSCODES
250-PIPELINING
250-CHUNKING
250 SMTPUTF8 C: mail from:<sender@example.io>
S: 250 2.1.0 OK q14si6283798lji.50 - gsmtp
C: rcpt to:<support@mailtrap.io>
S: 250 2.1.5 OK q14si6283798lji.50 - gsmtp
C: quit
S: 221 2.0.0 closing connection q14si6283798lji.50 - gsmtp

Why the VRFY and EXPN commands are not considered?

The VRFY command is used to verify whether a mailbox in the argument exists on the local host. For example:

C: VRFY recipient
S: 250 The Recipient recipient@example.io

The EXPN command is used to verify whether a mailing list in the argument exists on the local host. For example:

C: EXPN mail-list
S: 250-recipient1@example.io
250-recipient2@example.io
250-recipient3@example.io

Both commands implement SMTP authentication. However, they are considered a security risk – spammers can use them to steal valid email addresses from the server. Therefore, most of the servers disable these commands for security purposes.

To learn more about verifying an email address without sending an email click here.