Email - setting a Sender Policy Framework (SPF) record

Spam. No one likes it. No one wants it. No one needs it. However, it is there and is likely to be there for the foreseeable future.

All we can do as responsible mail server administrators is to ensure we are not part of the problem by not running an open relay and locking down our services as much as possible.

One tool that can help our legitimate email not being classed as spam is to set a Sender Policy Framework (SPF) record in our domain's DNS zone.


Sender Policy Framework

A SPF record is a DNS TXT record and is added to our DNS zone in the same manner that A records and MX records are added.

I started the article with a commentary regarding spam email. A common method spammers use is to forge the sender address in the email. Thus, they send email from their mail servers but with your domain as the sending email.

Not good.

The SPF record (remember the record is associated with the domain) specifies which mail server(s) the domain uses to send mail.

It does require the server receiving your mail to check the SPF record to ensure it complies with the domain records but the majority of public mail servers (such as your ISPs mail servers, google mail and so on) will do so.

Having said, that I do not guarantee every ISP complies with the SPF policy or, even if they do, that they do so correctly.

If the receiving server complies with the SPF policy correctly, and the sent email does not conform to your domain records (i.e. comes from an unknown server), it will be marked as fake and either deleted or marked as spam.

One thing to note is that the SPF record allows mail to be quickly assessed by compliant recipients as the checks are completed from information in the header of the email. That is, before the body of the message is loaded. This saves a great deal of time and resources if the mail is a forgery.

Setting SPF

To correctly set the SPF for your domain you need to think about a few things such as:

From what server(s) will mail from the domain originate. The answer may not be as simple as 'from my Slice of course!'. If you are sending mail from your workstation via your ISP's mail servers, you may want to consider their servers.

Perhaps you use Google Apps for their mail services.

All possible (legitimate) sending servers need to be taken into account.

How do want non-legitimate mail to be handled? Do you want them to be rejected out of hand with no questions asked, or do you perhaps want the message to be classed as a 'soft fail', meaning the email will be subjected to further scrutiny.

Example

Let's say we have listed the following as details for our mail on demoslice.com.

The Slice itself (i.e. the incoming MX details also send mail).

Google mail.

We also want to ensure that no other mail servers are authorised.

The TXT record would look like this:

v=spf1 mx include:aspmx.googlemail.com -all

Let's go through each one:

v=spf1

This sets the SPF version being used

mx

Allows the domain's MXers to send mail

include:aspmx.googlemail.com

Included in our list of authorised sending servers are the google mail servers

-all

Any servers not listed previously as NOT authorised. This will produce a fail and action will be taken according to the receiving mail server's own policy (i.e. delete it or mark it as spam, etc).

The 'all' setting

The final setting shown above - the 'all' setting - is an important aspect of the record and has 3 basic markers:

-all

As already explained, this means that any server not previously listed is not authorised - no questions asked.

~all

If mail is received from a server not previously listed, mark it as a 'soft fail' - this allows the mail to be scrutinised further.

+all

Allow any server, anywhere to send mail from my domain. Naturally, this is a very silly setting and should never even be considered.

demoslice.com

So, back to my domain.

I have given it some thought and I know that all I need is to send mail from this Slice. I won't be sending mail via Google or via my ISP.

I also want to ensure that no other mail servers are authorised.

As such, my SPF record is going to be quite simple:

v=spf1 mx -all

It is a sparse record but suits the needs of this Slice perfectly.

Naturally, you will want to consider all options for your Slice needs. Perhaps an '~all' may be better for your domain.

Do give it some thought and plan carefully what your mail needs are for the domain.

Adding the record

So now we have the record we want to use, we can go ahead and add it to the DNS zone.

Log into the Slicemanager (https://manage.slicehost.com).

Select the DNS tab and then the 'records' link for your domain.

Click new record.

Select TXT from the drop down and enter the details as shown in the example here:

Adding an SPF record

So that gives us the record for the demoslice.com domain.

More information

There is a huge amount of data on the Sender Policy Framework and I highly recommend reading more on the subject to get the most from this policy and to reduce the chances of your domain being used by spammers.

A good site is http://www.openspf.org/.

Summary

Setting an SPF record for your domain can help in reducing the chances of a spammer using your domain name in unsolicited emails.

Research carefully what mail servers your domain is likely to use and plan how you want any non-authorised email to be handled.

PickledOnion

Article Comments:

Andrew commented Fri Aug 22 05:45:02 UTC 2008:

I want to send mail from both my slice and using Google Apps, however my MX records contain only the *.ASPMX.L.GOOGLE.COM and *.GOOGLEMAIL.COM records.

Would the v=spf1 mx -all record use the Google domains in this case? What does this article assume about the slice's MX records?

PickledOnion commented Wed Aug 27 09:26:38 UTC 2008:

Hi Andrew,

The example shown above shows exactly what you are asking by using the 'include' option.

Please read the other articles for details of the MX records.

Thanks

PickledOnion

Jon commented Wed Aug 27 23:20:41 UTC 2008:

Awesome! I feel like the proto-human in 2001 A Space Odyssey comprehending the tool. Now I'll go bash spammers over the head with with it! Arrgh Arrgh Arrgh!!!

Mohammed commented Thu Sep 25 12:56:22 UTC 2008:

Google recommends the following string:

v=spf1 include:aspmx.googlemail.com ~all

http://www.google.com/support/a/bin/answer.py?hl=en&answer=33786

jc commented Sat Nov 22 23:53:09 UTC 2008:

Also good to try out this wizard: http://www.openspf.org/

Brian commented Thu Dec 25 00:59:06 UTC 2008:

Mohammed thanks for the tip!

I just got this setup on my site (www.universitytutor.com) hopefully it cleans things up a bit.

A note for anyone else: another good thing to check is that your reverse DNS points to the correct domain! Mine was still pointing to my old domain. That was causing some messages to get flagged as spam as well.

Good article. Brian

jack commented Sun Jan 11 12:11:45 UTC 2009:

Strange, after setting up the SPF record Hotmail marks the emails sent from the server as junk.

Micah commented Sun Feb 22 15:05:46 UTC 2009:

Any way to test if it's set up correctly? I'm trying to use dig but not getting very far. I don't know if my syntax is wrong or I have to wait for it to propagate or what.

Feeling a little lost...

jason commented Sun Apr 05 23:20:37 UTC 2009:

Micah: You should see your record in the results of the following command: dig -t TXT example.com

Dave commented Mon May 04 20:01:54 UTC 2009:

What if you are hosting multiple domains on the same slice?

Bart commented Mon May 25 20:00:04 UTC 2009:

One thing to note, if your slice is capable of sending email but isn't the same as your MX for whatever reason, you'll need to add it as well. Two basic examples from reading the comments, and I hope I'm doing the markdown right:

First example, if your MX records aim at google to recieve mail there: v=spf1 a include:aspmx.googlemail.com -all Note I replaced MX with A. That says "any machine with an A record defined in my DNS can send e-mail" - if you've kept your DNS records short and sweet, that'll be plenty restrictive.

Second example, two slices and only one of them accepts email, but both can send (take a webforum, or results of a chron task)... two versions here. The first is the more complicated one: v=spf1 a mx -all Secondly, the simpler one: v=spf1 a -all Yeah, that probably got a "wait, what?" out of some of you. Well... your recieving MTA has an A record somewhere in your DNS, doesn't it? Thus for that machine, the MX lookup's redundant as it will already have passed on the A lookup. This last one can also handle if you've only got the one slice/machine, to boot.

Andrew commented Mon Aug 03 23:29:07 UTC 2009:

I was hoping someone out there could help me. I setup a mail server will all of pickled onion's tutorials, but am stumped on one last problem I'm having.

When sending an email to one of my clients I get the following bounce back message: someemail@destination.com: host mail.destination.com[55.555.55.555] said: 550 domain of myname@mydomain.com does not designate 444.44.444.44 as permitted sender (in reply to MAIL FROM command)

... of course the email and ip addresses were diferent, but I had a feeling it had something to do with my SPF records or something else with slice setup. Thanks in advance for any help.

Eric commented Tue Aug 04 22:20:06 UTC 2009:

This site seems pretty handy: http://old.openspf.org/wizard.html

Andrew commented Tue Aug 04 23:56:53 UTC 2009:

I previously posted information about a 550 error... I hope the following can assist anyone...

So of course it took my forever to do the simple... I emailed my gmail account from my domain account and looked at the email headers (who would have thought uh?) This is what I saw:

Received-SPF: fail (google.com: domain of abessa@qqq.com does not designate xxx.xx.xxx.xx as permitted sender) client-ip=xxx.xx.xxx.xx; Authentication-Results: mx.google.com; spf=hardfail (google.com: domain of abessa@qqq.com does not designate xxx.xx.xxx.xx as permitted sender) smtp.mail=abessa@qqq.com

This would explain why email didn't deliver to my client, as well as yahoo marking my email as spam...

So I used the website just posted (http://old.openspf.org/wizard.html)

My server is not currently setup with any MX servers, so I had to change my SPF record to: v=spf1 a -all

Notice the "a" instead of "mx"

I'll be the first to admit that I don't know what an MX server is, that will be the next thing to learn... don't laugh though, there was a point where you didn't know what an MX server was either...

Good luck everyone

Michael Bamford commented Sat Sep 12 18:45:22 UTC 2009:

These articles are an amazing resource and time savers. It's because of them that I've given Slicehost my business. Keep up the good work!

Craig commented Mon Oct 05 17:00:01 UTC 2009:

For some reason my SPF Record reflects without spaces: v=spf1mx~all when in fact my Zonefile has spaces in it. Anyone?

racy_rick commented Mon Nov 23 19:45:53 UTC 2009:

Nice writeup, my dns was hosted at godaddy and they have a way on their web admin area to add TXT records.

Thanks for the info!

Nicolas Block commented Mon Jan 18 20:42:18 UTC 2010:

Some sites will show you an example -all changed to a ~all, a tilde instead of a dash. ~all (tilde) means to treat unspecified senders as "soft-fail" and they are usually not blocked. Use the dash, not the tilde in your production environment.

Phil commented Fri May 14 12:27:52 UTC 2010:

Spammers are really such a pain! Thank you for coming up with an alternative...

Online Accounting Tutoring commented Fri Jun 10 09:03:19 UTC 2011:

Hi Can someone help set this up for us? We are accountants and dont have the know how to do something like this. Is there a wordpress plugin?

Gaurav Shah commented Wed Sep 07 12:04:07 UTC 2011:

The new spf record for google mail is something like this :

v=spf1 include:_spf.google.com ~all

source google : http://www.google.com/support/a/bin/answer.py?answer=178723

Z commented Mon Dec 19 20:29:12 UTC 2011:

In order to get the spf record set up correctly you must contain the record within quotes. So for example, instead of v=spf1 mx -all it should be "v=spf1 mx -all". At least this is what I had to do to get it working.

Yang commented Fri Jan 13 00:06:44 UTC 2012:

For people who want to verify if their SPF record is correctly working, just send an email from your intended IP to any of your other emails, and when the message arrives, check the email headers or original message for a header field of "Received-SPF". If the value of it is "pass" followed by permitted sender IP which is the same as that of "Received from" IP, then you can be sure the SPF record of your domain is working properly.

Amit commented Tue Oct 16 08:13:43 UTC 2012:

For setting spf records of multiple domains using same pool of ips you can set the spf for one domain and then include this in other domain's spf records using "include:" directive. This way you can manage all from one domain and doesn't have to change the spf settings everytime you add/remove an ip for all domains.

Jones sabo find it irresistible committed consumed commented Mon Apr 22 20:05:16 UTC 2013:

Magnificent goods from you, man. I have understand your stuff previous to and you are just extremely excellent.

Want to comment?


(not made public)

(optional)

(use plain text or Markdown syntax)