Filtering incoming spam

How to install SpamAssassin

To enable SpamAssassin on your server, you first need to install it.

  1. Use CustomBuild to install SpamAssassin:
cd /usr/local/directadmin/custombuild
./build set spamd spamassassin
./build spamassassin
  1. Now that SpamAssassin is set up and running, Users just need to enable it at their User Level -> SpamAssassin section to create their user_prefs file, and email scanning should begin.

How to install rspamd

Rspamd is another filtering system for preventing incoming spam by evaluating messages by a number of rules including regex, statistical analysis and custom services such as RBLs etc.

Because rspamd is a drop-in replacement for SpamAssassin, rspamd uses the same config files in the user's directory as SpamAssassin does.

System requirements include:

  • Exim 4.91+
  • SpamBlocker 4.5.9+ (exim.conf)
  • EasySpamFighter 1.19+
  • CentOS 7+, or Debian 9+

To install:

cd /usr/local/directadmin/custombuild
./build set spamd rspamd
./build rspamd
./build exim_conf

How to configure rspamd

When you save the SpamAssassin settings through DirectAdmin, the per-User config is saved at /etc/rspamd/users.d/username.conf, which is loaded from the included file (if it exists) /etc/rspamd/rspamd.conf.local, which then loads in /etc/rspamd/directadmin-users.conf, which holds the list of all User configs, where the list points to the users.d/username.conf.

Rspamd comes with a nice controller socket, allowing a WebUI: in new window. This feature will have DirectAdmin act as a proxy to this socket. This is an Admin-Only call, and the socket is proxied from the command:

Note, as all included files with this call are relative to it, it needs to be treated as a directory. Accessing "CMD_RSPAMD_SOCK" without the trailing / character will issue a redirect to CMD_RSPAMD_SOCK/. All files below this path, e.g., /CMD_RSPAMD_SOCK/img/rspamd_logo_navbar.png are sent to the socket as http://localhost/img/rspamd_logo_navbar.pngopen in new window, thus allowing a the rspamd WebUI to work through DirectAdmin's connection on 2222.


If you need to add other custom settings, place them inside the file /etc/rspamd/rspamd.conf.local. Just be sure NOT to remove the directadmin-users.conf include.


If you need to rewrite one or all Users' *.conf files in:


via the task.queue.

Command for one User:

echo "action=rewrite&value=rspamd&user=USERNAME" >> /usr/local/directadmin/data/task.queue

where USERNAME is set in lower case, to the User you'd like. Only does anything is user_prefs is present. Running the dataskq in debug mode will help if anything isn't writing, for whatever reason.

Command for ALL Users:

echo "action=rewrite&value=rspamd" >> /usr/local/directadmin/data/task.queue

How to Blacklist/Whitelist Email Using Wildcards for SpamAssassin and/or Rspamd

Via the User Level -> SpamAssassin Setup page, both the blacklist and whitelist entries now support more detailed wildcards.

For example, you can now use:

  • *.com
  • fred@*.com
  • fred@test.*
  • etc.

Previously supported values still supported include:

  • *

This applies via both Exim's per-domain filter for use with SpamAssassin and via Rspamd's per-user filter:


File: /etc/virtual/

The whitelisted values, if a wildcard is present will rely on Exim's "matches" command, instead of the previous "contains" command, and will (for example) look like:

$sender_address matches ".*@.*\\\\.com\\$$"

Where the actual regex is:


but a \ needs to be escaped multiple times for the multiple-levels of embedding, so a literal \ ends up being \\\\.

And the $ also needs to be escaped so it's not processed (it's a special character in Exim strings).


File: /etc/rspamd/users.d/fred.conf

The whitelist/blacklist entries would look like:

from = ‥/.*@.*\.com/”

Note that the whitelist priority has been changed in the rspamd_settings.conf from "high" to "4" so that it has a higher priority than the blacklist.

How to uninstall rspamd

If you want to get rid of rspamd and rollback to SpamAssassin, use the following steps:

./build set spamd spamassassin
./build remove_rspamd
./build remove_rspamd_conf
./build spamassassin
./build exim_conf

Adult filter to use template

DirectAdmin v1.593

A template file /usr/local/directadmin/data/templates/adult.list contains all internal adult words, allowing one to add/remove words as needed if you copy it to the custom file here:


How to enable SpamAssassin for new users

By default (if enabled), DA gives the User the option to enable SpamAssassin, but it is not turned on by default.

To have it on by default, you can use the script to create it for you.

Create the /usr/local/directadmin/scripts/custom/ with the following content:

if [ "$spam" = "ON" ]; then
  mkdir -p $DIR
  if [ ! -s ${UP} ]; then
     echo 'required_score 5.0' > ${UP}
     echo 'report_safe 1' >> ${UP}
     chown $username:$username  ${UP}
     chmod 644 ${UP}
  chown  ${username}:mail $DIR
  chmod 771 $DIR

  if grep -m1 -q "^spamd=rspamd$" /usr/local/directadmin/custombuild/options.conf; then
      echo "action=rewrite&value=rspamd&user=${username}" >> /usr/local/directadmin/data/task.queue

  if [ "${domain}" != "" ]; then
     if [ ! -s ${FCONF} ]; then
        echo 'high_score=15' > ${FCONF}
        echo 'high_score_block=no' >> ${FCONF}
        echo 'where=inbox' >> ${FCONF}
        chown mail:mail ${FCONF}

        echo "action=rewrite&value=filter&user=$username" >> /usr/local/directadmin/data/task.queue
exit 0;

And make it executable:

chmod 755 /usr/local/directadmin/scripts/custom/

How to enable SpamAssassin for existing customers

The above script can be used to also enable SpamAssassin for all existing accounts. You can create another simple script to do it called (for example) with the following code:

for i in `ls /usr/local/directadmin/data/users`; do
         for d in `cat /usr/local/directadmin/data/users/$i/domains.list`; do
                     username=$i domain=$d spam=ON /usr/local/directadmin/scripts/custom/
exit 0;

Make it executable and run just once:

chmod 755

I wish to change the default spam settings for new domains

Similar to the guide to enable SpamAssassin by default, this guide will explain the basics as to how to change the per-domain spam options for a newly created domain.

Using the domain_create_post.shopen in new window, you'll want to have your script edit the /etc/virtual/$domain/filter.conf file. This is where the per-domain settings are. To find out the setting you need to change, edit a test domain through the normal SpamAssassin/Spam Filters interface through DA, and take note of which option changed. This will tell you what change you need to make with your script.

For example, if you wish to set the filter.conf to use

Send the spam to the user's spam folder.

by default for new domains, you'd have a with this content:

if [ -e $F ]; then
   echo "where=userspamfolder" >> $F
   echo "action=rewrite&value=filter&user=$username" >> /usr/local/directadmin/data/task.queue

And make it executable:

chmod 755 /usr/local/directadmin/scripts/custom/

How to assign different score to a SpamAssassin variable

If you get a spam score in your headers such as this:


and you think 3 is too much, you can override any variable to a lower value by adding this to your ~/.spamassassin/user_prefs file, e.g.,

score SPF_FAIL 2

Note, the SPF_FAIL variable is just an example, 3 might not be its actual default.

Another option that should receive a high score would be any sender IP that does not have a reverse IP lookup. All valid mail servers should have one, so we can penalize those that don't:

score RDNS_NONE 3.0

This score still allows a small amount of room for error (in case you accidentally set up the remote sending server incorrectly, without rDNS, you might want to accept the email). Or, if you absolutely don't ever want to receive email from an incorrectly set up server, you'd use a higher value, like 5.0, to help push the total score over the threshold/limit.

How to lower the EasySpamFilter threshold for rDNS, DKIM and SPF

By default in EasySpamFighter, a rDNS, DKIM or SPF that fully fails is dropped right away. They all use a default score of 100, while the drop score is 100.

If you wish to instead add a score to the total, you can change them to use a lower score, e.g.,

echo "EASY_NO_REVERSE_IP==60" >> /etc/exim.easy_spam_fighter/variables.conf.custom
echo "EASY_SPF_FAIL==60" >> /etc/exim.easy_spam_fighter/variables.conf.custom
echo "EASY_DKIM_FAIL==60" >> /etc/exim.easy_spam_fighter/variables.conf.custom

then restart Exim:

service exim restart

How to create an email account that deletes all incoming mail

The easy way is to create a forwarder and send it to:


It will accept the email, but not save it.



Which will send a fail message to the sender.

It has the same functionality as the catch-all account options.

How to tell Exim not to skip mail filter from <>

Emails that are bounced from other mail severs will have a from value of <>.

The filters are set to not block those emails. If you still want those emails to be filtered, then run the following:

cd /usr/local/directadmin/data/templates/custom
cp ../filter_base .
perl -pi -e 's/^if error/#if error/' filter_base
echo "action=rewrite&value=filter" >> /usr/local/directadmin/data/task.queue

The filtering process includes the "SPAM Filters" and any email redirects for SpamAssassin. SpamAssassin will still scan the emails, it would only be the redirection that is affected with the <> address.

If you wish to simply delete all emails with <> as the sender (note, this includes bounces and valid errors from the mail system), add this to the top of your /etc/system_filter.exim file:

if $h_From: contains "<>"
         if $reply_address: contains "<>"
                  seen finish

SpamAssassin rules to block null envelope sender which has a List-Unsubscribe header

If you're getting spam from a <> sender (null envelope), and it also has a List-Unsubscribe header, SpamAssassin can be used to create a rule to block it. Edit your ~/.spamassassin/user_prefs file, and add the following to the bottom:

header  RETURNPATH_EMPTY        ALL =~ /.*?^Return-Path:s*<>.*/ism
score   RETURNPATH_EMPTY        0.0
header  LIST_UNSUBSCRIBE        List-Unsubscribe =~ /b.{3}b/i
score   LIST_UNSUBSCRIBE        0.0
score   RETURNPATHSPAM          10.0

What does URIBL_BLOCKED mean?

If you get a SpamAssassin tag that looks like this

URIBL_BLOCKED          ADMINISTRATOR NOTICE: The query to URIBL was blocked.
                       for more information.

It's referring to the DNS server you're using not being allowed to do an RBL request to the the RBL servers.

Most RBL servers use a "free for some" method, where as long as a given DNS server isn't doing too many requests, it's allowed. But for a DNS server that is too busy, (e.g., is very busy), it will be blocked from doing RBL queries, since it no longer qualifies as the "Free for some" method, and would then fall under the category where payment is required to do that volume of RBL queries.


Don't use a busy DNS server in your /etc/resolv.conf file.

The simplest solution is to just use your own server's DNS server for lookups. To do this, edit /etc/resolv.conf and remove the other nameserver IP lines, and replace them with just one:


which tells all DNS queries that your server makes, to call your local copy of "named", instead of querying the remote DNS server for lookups.

As RBLs are all DNS based, this means your RBL queries to the RBL servers would now be coming from your server, and not from a big DNS server, like, so it's most likely to go through.

How to enable realtime blocklists (RBLs) with Exim

Because SpamAssassin already factors in RBLs in its spam scoring and blocking, you can leave this option disabled and still benefit from RBLs. Only use this option if you are certain that you want very aggressive RBL blocking.

To enable RBL blocking for all current and future domains via the DirectAdmin GUI, use the following:
Admin Level -> Admin Settings -> Use RBL Blocking

Note: This option will show enabled if /etc/virtual/use_rbl_domains is a a link, and disabled if it's a file.
So, if you are using the use_rbl_domains as a file and are manually updating it, leave the option disabled.
If you enable it, the file will be deleted and it will be replaced by a link to "domains".

To enable RBL blocking for all current and future domains via the command line as root, run the following:

cd /etc/virtual
rm -f use_rbl_domains
ln -s domains use_rbl_domains

This will set up the list of domains to be filtered to match the active domains list, so new domains added to the server are also included for the spammer IP blocking.

The RBLs will connect out to remote servers for each email, check to see if the sending IP is a spammer, and prevent that email from arriving. These lists are regularly updated, so they are highly effective.

Note that some lists also block entire ISP IP ranges, so if your clients are not able to send email, then can switch to sending email through port 587 instead of port 25.

To disable RBLs, you can do the following:

cd /etc/virtual
rm -f use_rbl_domains
touch use_rbl_domains

How to omit a domain from Exim's RBL blocking

There are a few different methods:

  1. Exclusion List: Create the file /etc/virtual/skip_rbl_domains and add the domains that you want skipped when RBL block checks are occurring.
  2. Inclusion List: Manually add and maintain the domains that you do want checked in the file /etc/virtual/use_rbl_domains.

More information in new window

These methods require manually adding domains to the appropriate files as described above.

SpamBlocker 4.x: Custom RBL lists

As of SpamBlocker 4.3.3, the RBL list has been changed to a variable near the top of the /etc/exim.conf:

RBL_DNS_LIST=\ : \ : \ : \

As such, the variable can be overwritten by setting the variable again.

To do this, we have the /etc/exim.strings.conf.custom, which can be modified with the bottom of this guide </other-hosting-services/preventing-spam/general/#spamblocker-install-and-extra-modules>

So, for example, if you wanted to remove, you'd create /etc/exim.strings.conf.custom and add the list, without that one value: : : :

Note that we've unified all values for that variable onto one line.

And restart Exim:

service exim restart

SpamAssassin is not working

We often get this question, and the number of causes can be many, so there are several things to check.

  1. The first thing to check is to see if the messages are being scanned at all. The way to do that is to check your message headers. In the headers will be spam scoring which will let you know if it's being scanned or not. This is a sample set of spamassassin headers in a sample spam email. Note that even non-spam will have the same header names, they'll just have different values.
X-Spam-Flag: YES
X-Spam-Checker-Version: SpamAssassin 3.2.5 (2019-06-10) on
X-Spam-Level: *******
X-Spam-Status: Yes, score=7.4 required=5.0 tests=BAYES_80,FH_HELO_EQ_D_D_D_D,
            HELO_DYNAMIC_IPADDR2,RCVD_IN_PBL,RDNS_NONE autolearn=no version=3.2.5
            *  4.4 HELO_DYNAMIC_IPADDR2 Relay HELO'd using suspicious hostname (IP addr
            *         2)
            *  0.0 FH_HELO_EQ_D_D_D_D Helo is d-d-d-d
            *  2.0 BAYES_80 BODY: Bayesian spam probability is 80 to 95%
            *        [score: 0.8251]
            *  0.9 RCVD_IN_PBL RBL: Received via a relay in Spamhaus PBL
            *        [ listed in]
            *  0.1 RDNS_NONE Delivered to trusted network by a host with no rDNS
  1. If you are seeing those headers then SpamAssassin is in fact working, but perhaps just not catching everything you'd like. There are ways to make it catch more. One is to lower your scoring threshold. In the above example, a limit of 5.0 is used, but you can lower it if you're finding spam is being scored lower. Another way is to run the command:
sa-update --nogpg

every week or so, to update the SA rules. Another method is to customize the rules in your user_prefs files in order to give some common aspects a higher scoring (see the SpamAssassin docs for this). Lastly, you can create an teaching folder to help SA learn what is and is not spam.

  1. If your emails are not being scanned at all, here are the first things to check:
  • Ensure you have /home/username/.spamassassin/user_prefs present or your emails will not be scanned.

  • Check your /etc/exim.conf. Ensure your spamcheck_director section is uncommented as per step 3 of this guide.

  • Note that emails larger than 100k (by default) will not be scanned, pending on what your spamcheck_director settings are. You can increase this size if needed.

  • Ensure that spamd is running:

ps ax | grep spamd
  • Check your /var/log/exim/mainlog, /var/log/exim/paniclog and /var/log/maillog for any spamd related errors.

Email to my server is bouncing: BSMTP input, 421 Lost incoming connection

If email to your server gets the following error in a bounce:

An error was detected while processing a file of BSMTP input.
The error message was:

 421 Lost incoming connection

The SMTP transaction started in line 0.
The error was detected in line 3.
0 previous messages were successfully processed.
The rest of the batch was abandoned.
421 Lost incoming connection
Transaction started in line 0
Error detected in line 3

It likely means that spamd is not running, or not running correctly. Check the /var/log/maillog for clues regarding spamd. Also try restarting Exim and spamd:

service exim restart

How to enable pigeonhole

Pigeonhole is the name of the project that adds support for the Sieve language (RFC 5228) and the ManageSieve protocol (RFC 5804) to the Dovecot Secure IMAP Server. In a literal sense, a pigeonhole is a a hole or recess inside a dovecot for pigeons to nest in. It is, however, also the name for one of a series of small, open compartments in a cabinet used for filing or sorting mail. As a verb, it describes the act of putting an item into one of those pigeonholes.

The name Pigeonhole therefore adequately describes an important part of the functionality that this project adds to Dovecot: sorting and filing e-mail messages.

To install pigeonhole:

cd /usr/local/directadmin/custombuild
./build set pigeonhole yes
./build set dovecot yes
./build set dovecot_conf yes
./build dovecot
./build roundcube

How to teach SpamAssassin

This guide describes the steps required to teach SpamAssassin to distinguish between spam and non-spam (ham). The guide is tailored to the Maildir format.

This will assume that you've already installed SpamAssassin and Pigeonhole.

  1. Modify the /etc/systemd/system/spamassassin.service file to add the -l flag to allow spamc to learn and tell what is spam and what is not:
Description=Spamassassin daemon

ExecStart=/usr/bin/spamd --pidfile /var/run/ -d -c -m 15 --ipv4 -l


For this edit to persist after updates, copy it to /usr/local/directadmin/custombuild/custom/systemd/ .

Restart SpamAssassin:

systemctl daemon-reload
systemctl restart spamassassin
  1. Modify the /etc/dovecot/conf/imap_mail_plugins.conf to add imap_sieve to the mail_plugins:
mail_plugins = $mail_plugins quota imap_quota zlib imap_sieve

For this edit to persist after updates, copy it to /usr/local/directadmin/custombuild/custom/dovecot/conf/ .

  1. Create the /etc/dovecot/conf.d/99-imap-sieve.conf file with the following content:
plugin {
  sieve_plugins = sieve_imapsieve sieve_extprograms

  # From elsewhere to Spam folder
  imapsieve_mailbox1_name = Spam
  imapsieve_mailbox1_causes = COPY
  imapsieve_mailbox1_before = file:/usr/local/bin/dovecot-sieve/report-spam.sieve

  # From Spam folder to elsewhere
  imapsieve_mailbox2_name = *
  imapsieve_mailbox2_from = Spam
  imapsieve_mailbox2_causes = COPY
  imapsieve_mailbox2_before = file:/usr/local/bin/dovecot-sieve/report-ham.sieve

  sieve_pipe_bin_dir = /usr/local/bin/dovecot-sieve

  sieve_global_extensions = +vnd.dovecot.pipe +vnd.dovecot.environment
  1. Create the directory to store scripts:
mkdir -p /usr/local/bin/dovecot-sieve
  1. Create the /usr/local/bin/dovecot-sieve/report-spam.sieve:
require ["vnd.dovecot.pipe", "copy", "imapsieve", "environment", "variables"];

if environment :matches "imap.user" "*" {
  set "username" "${1}";

pipe :copy "" [ "${username}" ];
  1. Restart dovecot:
service dovecot restart
  1. Compile and fix permissions for it:
cd /usr/local/bin/dovecot-sieve
sievec report-spam.sieve
chown mail. report-spam.sieve
  1. Create the /usr/local/bin/dovecot-sieve/report-ham.sieve:
require ["vnd.dovecot.pipe", "copy", "imapsieve", "environment", "variables"];

if environment :matches "imap.mailbox" "*" {
  set "mailbox" "${1}";

if string "${mailbox}" "Trash" {

if environment :matches "imap.user" "*" {
  set "username" "${1}";

pipe :copy "" [ "${username}" ];
  1. Compile and fix permissions for it:
cd /usr/local/bin/dovecot-sieve
sievec report-ham.sieve
chown mail. report-ham.sieve
  1. Create the /usr/local/bin/dovecot-sieve/
# you can also use tcp/ip here, consult spamc(1)
ddomain=`/usr/bin/echo "${1}"| /usr/bin/cut -d'@' -f2`
dusername=`/usr/bin/egrep "^${ddomain}:" /etc/virtual/domainowners| /usr/bin/cut -d' ' -f2`
exec /usr/bin/spamc -u ${dusername} -L spam <<< "${inputmail}"
  1. Restart dovecot:
service dovecot restart

Now create the /Spam mailbox folder and populate it with some spam messages. Check that sa-learn works under any user with:

su -l username -s /bin/sh
sa-learn --dump magic

To train SpamAssassin, drag any spam messages not flagged as such into your Spam folder.

If you get an email that was tagged as spam that shouldn't have been, move it out of the Spam folder.

You can delete any email you've place there after a day or so, to ensure it has been caught by the sa-learn program. The more messages used to train sa-learn, the more effective it will be.

Exim SpamBlocker blacklist and whitelist files

Exim supports several backlist and whitelist files. Information on using each one, below:


  • /etc/virtual/blacklist_domains

The blacklist_domains is a nwildlsearch file, meaning you can use wildcards. It will contain any sending address domain you wish to block. Valid entries might be:

which blocks an explicit domain, or all domains ending with the spam domain extension, (e.g., would catch email@bad.spam).

  • /etc/virtual/blacklist_senders

Similar to the blacklist_domains, but instead, /etc/virtual/blacklist_senders would be a list of email addresses where wildcards are accepted. Samples in this file might be


NOTE: These 2 files will only be activated on domains which are enabled in the /etc/virtual/use_rbl_domains file. Usually, you'd just go to Admin Level -> Admin Settings -> Use RBL Blocking [x] to enable it, which replaces the use_rbl_domains file, with a symlink to the domains file (all domains on the server). Make sure "Use RBL Blocking" is enabled, else the blacklist files will not have any effect.

Outbound DirectAdmin Username/SMTP login blocks


These 3 files are meant to block OUTBOUND email from leaving your server. For more details see this guide.


  • /etc/virtual/whitelist_domains

This is also an nwildsearch, so the same format at the blacklist_domains applies. However this is for the destination domains, meaning NO SCANNING WILL BE DONE on these recipient domains. Rarely will you ever want to use this. It should be 0 bytes 99.999% of the time. Basically means any spam can arrive to this local domain list, which is not usually what would be desired.

  • /etc/virtual/whitelist_senders

An wilcard address list of sending/From emails that should be accepted without any scanning. Useful if you must receive emails from a specific sender. However, this value can be spoofed, and thus would typically not be the best way to whitelist a sender.

  • /etc/virtual/whitelist_hosts

This is a wildcard host list, containing a remote sending server's hostname. We usually expect a host to have both forward and reverse DNS to point to each other, so resolves to, and rDNS resolves to Sample format:
  • /etc/virtual/whitelist_hosts_ip

This is very similar to the whitelist_hosts file, except we use IPs, which can contain ranges. It does not support wildcards. Samples:

The WhiteList entries are not linked to the use_rbl_domains file.

Using the whitelists is somewhat aggressive in that it may bypass all scanning, allowing more in that you were expecting.

Adding Custom Code to SpamAssassin user_prefs Template

DirectAdmin uses the /usr/local/directadmin/data/templates/user_prefs template file for all writes of User ~/.spamassassin/user_prefs files.

If any changes were manually added to these files, any click of the "Save" button would overwrite your changes.

This featureopen in new window adds a safe area in between 2 tags:

#SAFE AREA start

where you can place your custom code.

Just before any save, DA will re-read the client's user_prefs file, hunting for these tags, and will save any code in between them.

That code will be added to a token SAFE_CODE, which has been added to the user_prefs template.

Disable the ESF high-score drop

If you wish to disable exim from blocking with this error:

Your message to <$recipients> was classified as SPAM.  Please add more content, cut down on HTML links, use fewer naughty words etc.  Also, ask your IT dept to make sure your mailserver has REVERSEDNS, SPF, DKIM, and is not on any black lists. Your score: 123

you'd increase the EASY_HIGH_SCORE_DROP variable to something that will never be hit, 1000 should be plenty.

To set this, type:

echo "EASY_HIGH_SCORE_DROP==1000" >> /etc/exim.easy_spam_fighter/variables.conf.custom

and restart exim:

service exim restart
Last Updated: