Changeset - f774e938a4ed
[Not reviewed]
0 5 4
Branko Majic (branko) - 7 years ago 2017-07-06 22:06:28
branko@majic.rs
MAR-27: Implemented tests for mail_forwarder role:

- Install hping3 (for testing connectivity) on mail-server test machine.
- Changed syntax used for deploying the SMTP relay truststore in order to ensure
that tabs are preserved.
- Implemented tests for the mail_fotwarder role.
- Updated tests for mail_server role to check for new setting
added (smtp_host_lookup).
9 files changed with 326 insertions and 8 deletions:
0 comments (0 inline, 0 general)
roles/mail_forwarder/playbook.yml
Show inline comments
 
@@ -88,6 +88,11 @@
 
      notify:
 
        - Restart Postfix
 

	
 
    - name: Install tool for testing TCP connectivity
 
      apt:
 
        name: hping3
 
        state: installed
 

	
 
  handlers:
 

	
 
    - name: Update CA certificate cache
roles/mail_forwarder/tasks/main.yml
Show inline comments
 
@@ -7,8 +7,12 @@
 
  apt: name="exim4*" state=absent purge=yes
 

	
 
- name: Deploy the SMTP relay TLS truststore
 
  copy: content="{{ smtp_relay_truststore }}" dest="/etc/ssl/certs/smtp_relay_truststore.pem"
 
        owner=root group=root mode=0644
 
  copy:
 
    content: "{{ smtp_relay_truststore }}"
 
    dest: "/etc/ssl/certs/smtp_relay_truststore.pem"
 
    owner: root
 
    group: root
 
    mode: 0644
 

	
 
- name: Configure visible mail name of the system
 
  copy: content="{{ inventory_hostname }}\n" dest="/etc/mailname"
roles/mail_forwarder/tests/test_connectivity_from_client.py
Show inline comments
 
new file 100644
 
import testinfra.utils.ansible_runner
 

	
 

	
 
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
 
    '.molecule/ansible_inventory').get_hosts('client1')
 

	
 

	
 
def test_connectivity_from_client(Command, Sudo):
 
    """
 
    Tests connectivity towards mail forwarder servers from client
 
    (non-relay). Connectivity should fail for both.
 
    """
 

	
 
    with Sudo():
 

	
 
        ping = Command('hping3 -S -p 25 -c 1 parameters-mandatory')
 
        assert ping.rc != 0
 

	
 
        ping = Command('hping3 -S -p 25 -c 1 parameters-optional')
 
        assert ping.rc != 0
roles/mail_forwarder/tests/test_connectivity_from_relay.py
Show inline comments
 
new file 100644
 
import testinfra.utils.ansible_runner
 

	
 

	
 
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
 
    '.molecule/ansible_inventory').get_hosts('mail-server')
 

	
 

	
 
def test_connectivity_from_relay(Command, Sudo):
 
    """
 
    Tests connectivity towards mail forwarder servers from relay. Connection
 
    towards parameters-mandatory should fail.
 
    """
 

	
 
    with Sudo():
 

	
 
        ping = Command('hping3 -S -p 25 -c 1 parameters-mandatory')
 
        assert ping.rc != 0
 

	
 
        ping = Command('hping3 -S -p 25 -c 1 parameters-optional')
 
        assert ping.rc == 0
 

	
 

	
 
def test_mail_reception_from_relay(Command, Sudo):
 
    """
 
    Tests if mails can be sent from relay to servers configured to use the
 
    relay.
 
    """
 

	
 
    send = Command('swaks --suppress-data --to root@parameters-optional --server parameters-optional')
 
    assert send.rc == 0
 

	
 

	
 
def test_open_relay(Command):
 
    """
 
    Tests if mail forwarder behaves as open relay.
 
    """
 

	
 
    no_recipients_accepted = 24
 

	
 
    send = Command('swaks --suppress-data --to root@client1 --server parameters-optional')
 
    assert send.rc == no_recipients_accepted
 
    assert "Relay access denied" in send.stdout
roles/mail_forwarder/tests/test_default.py
Show inline comments
 
import testinfra.utils.ansible_runner
 

	
 

	
 
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
 
    '.molecule/ansible_inventory').get_hosts('all')
 
    '.molecule/ansible_inventory').get_hosts(['parameters-mandatory', 'parameters-optional'])
 

	
 

	
 
def test_installed_packages(Package):
 
    """
 
    Tests if the necessary packages have been installed.
 
    """
 

	
 
    assert Package('postfix').is_installed
 
    assert Package('swaks').is_installed
 

	
 

	
 
def test_removed_packages(Package):
 
    """
 
    Tests if certain packages have been removed from the system.
 
    """
 

	
 
    assert not Package('exim4').is_installed
 

	
 

	
 
def test_smtp_relay_truststore_file(File):
 
    """
 
    Tests if SMTP relay truststore has correct permissions
 
    """
 

	
 
    truststore = File('/etc/ssl/certs/smtp_relay_truststore.pem')
 

	
 
    assert truststore.is_file
 
    assert truststore.user == 'root'
 
    assert truststore.group == 'root'
 
    assert truststore.mode == 0o644
 

	
 

	
 
def test_smtp_mailname(File):
 
    """
 
    Tests if SMTP mailname configuration file has correct permissions.
 
    """
 

	
 
    mailname = File('/etc/mailname')
 

	
 
    assert mailname.is_file
 
    assert mailname.user == 'root'
 
    assert mailname.group == 'root'
 
    assert mailname.mode == 0o644
 

	
 

	
 
def test_postfix_main_cf_file(File):
 
    """
 
    Tests Postfix main configuration file permissions.
 
    """
 

	
 
    config = File('/etc/postfix/main.cf')
 
    assert config.is_file
 
    assert config.user == 'root'
 
    assert config.group == 'root'
 
    assert config.mode == 0o644
 

	
 

	
 
def test_services(Service):
 
    """
 
    Tests if all the necessary services are enabled and running.
 
    """
 

	
 
    service = Service('postfix')
 
    assert service.is_running
 
    assert service.is_enabled
 

	
 

	
 
def test_hosts_file(File):
 
    f = File('/etc/hosts')
 
def test_firewall_configuration_file(File, Sudo):
 
    """
 
    Tests if firewall configuration file has correct permissions.
 
    """
 

	
 
    assert f.exists
 
    assert f.user == 'root'
 
    assert f.group == 'root'
 
    with Sudo():
 
        config = File('/etc/ferm/conf.d/20-mail.conf')
 
        assert config.is_file
 
        assert config.user == 'root'
 
        assert config.group == 'root'
 
        assert config.mode == 0o640
roles/mail_forwarder/tests/test_mandatory.py
Show inline comments
 
new file 100644
 
import re
 

	
 

	
 
import testinfra.utils.ansible_runner
 

	
 

	
 
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
 
    '.molecule/ansible_inventory').get_hosts('parameters-mandatory')
 

	
 

	
 
def test_smtp_relay_truststore_file(File):
 
    """
 
    Tests if SMTP relay truststore has correct content.
 
    """
 

	
 
    truststore = File('/etc/ssl/certs/smtp_relay_truststore.pem')
 

	
 
    assert truststore.content == open("tests/data/x509/truststore.pem", "r").read().rstrip()
 

	
 

	
 
def test_smtp_mailname(File):
 
    """
 
    Tests if SMTP mailname configuration file has correct content.
 
    """
 

	
 
    mailname = File('/etc/mailname')
 

	
 
    assert mailname.content == "parameters-mandatory"
 

	
 

	
 
def test_postfix_main_cf_file_content(File):
 
    """
 
    Tests if the Postfix main configuration file content is correct.
 
    """
 

	
 
    config = File('/etc/postfix/main.cf')
 
    config_lines = config.content.split("\n")
 

	
 
    assert "myhostname = parameters-mandatory" in config_lines
 
    assert "mydestination = parameters-mandatory, parameters-mandatory, localhost.localdomain, localhost" in config_lines
 
    assert "relayhost = " in config_lines
 
    assert "mynetworks = 127.0.0.0/8 [::ffff:127.0.0.0]/104 [::1]/128" in config_lines
 
    assert "smtp_tls_security_level" not in config.content
 
    assert "smtp_tls_CAfile" not in config.content
 
    assert "smtp_host_lookup = dns, native" in config_lines
 

	
 

	
 
def test_direct_mail_sending(Command, File, Sudo):
 
    """
 
    Tests if mails are sent correctly directly without relay if relay has not
 
    been configured.
 
    """
 

	
 
    send = Command('swaks --suppress-data --to root@domain1 --server localhost')
 
    assert send.rc == 0
 
    message_id = re.search('Ok: queued as (.*)', send.stdout).group(1)
 

	
 
    with Sudo():
 
        mail_log = File('/var/log/mail.log')
 
        pattern = "%s: to=<root@domain1>, relay=domain1.*status=sent" % message_id
 

	
 
        assert re.search(pattern, mail_log.content) is not None
roles/mail_forwarder/tests/test_optional.py
Show inline comments
 
new file 100644
 
import re
 

	
 

	
 
import testinfra.utils.ansible_runner
 

	
 

	
 
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
 
    '.molecule/ansible_inventory').get_hosts('parameters-optional')
 

	
 

	
 
def test_smtp_relay_truststore_file(File):
 
    """
 
    Tests if SMTP relay truststore has correct content.
 
    """
 

	
 
    truststore = File('/etc/ssl/certs/smtp_relay_truststore.pem')
 

	
 
    assert truststore.content == open("tests/data/x509/ca.cert.pem", "r").read().rstrip()
 

	
 

	
 
def test_smtp_mailname(File):
 
    """
 
    Tests if SMTP mailname has been configured correctly.
 
    """
 

	
 
    mailname = File('/etc/mailname')
 

	
 
    assert mailname.content == "parameters-optional"
 

	
 

	
 
def test_postfix_main_cf_file_content(File):
 
    """
 
    Tests if the Postfix main configuration file content is correct.
 
    """
 

	
 
    config = File('/etc/postfix/main.cf')
 
    config_lines = config.content.split("\n")
 

	
 
    assert "myhostname = parameters-optional" in config_lines
 
    assert "mydestination = parameters-optional, parameters-optional, localhost.localdomain, localhost" in config_lines
 
    assert "relayhost = mail-server" in config_lines
 
    assert "mynetworks = 127.0.0.0/8 [::ffff:127.0.0.0]/104 [::1]/128" in config_lines
 
    assert "smtp_tls_security_level=verify" in config_lines
 
    assert "smtp_tls_CAfile=/etc/ssl/certs/smtp_relay_truststore.pem" in config_lines
 
    assert "smtp_host_lookup = dns, native" in config_lines
 

	
 

	
 
def test_local_aliases(Command, File, Sudo):
 
    """
 
    Tests if local aliases are configured correctly.
 
    """
 

	
 
    send = Command('swaks --suppress-data --to root@localhost')
 
    assert send.rc == 0
 
    message_id = re.search('Ok: queued as (.*)', send.stdout).group(1)
 

	
 
    with Sudo():
 
        mail_log = File('/var/log/mail.log')
 
        pattern1 = "%s: to=<root@parameters-optional>, orig_to=<root@localhost>.*status=sent" % message_id
 
        pattern2 = "%s: to=<testuser@parameters-optional>, orig_to=<root@localhost>.*status=sent" % message_id
 

	
 
        assert re.search(pattern1, mail_log.content) is not None
 
        assert re.search(pattern2, mail_log.content) is not None
 

	
 

	
 
def test_relay_mail_sending(Command, File, Sudo):
 
    """
 
    Tests if mails are sent correctly via relay if relay has been configured.
 
    """
 

	
 
    send = Command('swaks --suppress-data --to root@domain1 --server localhost')
 
    assert send.rc == 0
 
    message_id = re.search('Ok: queued as (.*)', send.stdout).group(1)
 

	
 
    with Sudo():
 
        mail_log = File('/var/log/mail.log')
 
        pattern = "%s: to=<root@domain1>, relay=mail-server.*status=sent" % message_id
 

	
 
        assert re.search(pattern, mail_log.content) is not None
 

	
 

	
 
def test_tls_enforced_towards_relay_mail_server(Command, File, Sudo):
 
    """
 
    Tests if TLS verification is enfoced towards the relay mail server.
 
    """
 

	
 
    with Sudo():
 
        # Replace the relayhost with name that is not present in relay's
 
        # certificate.
 
        command = Command("sed -i -e s#relayhost\\ =\\ mail-server#relayhost\\ =\\ domain1# /etc/postfix/main.cf")
 
        assert command.rc == 0
 
        command = Command("service postfix restart")
 
        assert command.rc == 0
 

	
 
        # Try to send out an e-mail
 
        send = Command('swaks --suppress-data --to root@domain1 --server localhost')
 

	
 
        # Restore correct relay name in the configuration file.
 
        command = Command("sed -i -e s#relayhost\\ =\\ domain1#relayhost\\ =\\ mail-server# /etc/postfix/main.cf")
 
        assert command.rc == 0
 
        command = Command("service postfix restart")
 
        assert command.rc == 0
 

	
 
        # Finally check the results.
 
        assert send.rc == 0
 
        message_id = re.search('Ok: queued as (.*)', send.stdout).group(1)
 

	
 
        with Sudo():
 
            mail_log = File('/var/log/mail.log')
 
            pattern = "%s: to=<root@domain1>, relay=domain1.*status=deferred \(Server certificate not verified\)" % message_id
 

	
 
            assert re.search(pattern, mail_log.content) is not None
roles/mail_server/tests/test_mandatory.py
Show inline comments
 
@@ -85,6 +85,7 @@ def test_postfix_main_cf_file_content(File):
 
    assert "smtpd_tls_cert_file = /etc/ssl/certs/parameters-mandatory_smtp.pem" in config_lines
 
    assert "smtpd_tls_key_file = /etc/ssl/private/parameters-mandatory_smtp.key" in config_lines
 
    assert "reject_rbl" not in config_lines
 
    assert "smtp_host_lookup = dns, native" in config_lines
 

	
 

	
 
def test_dovecot_mailbox_directories(Command, File, Sudo):
roles/mail_server/tests/test_optional.py
Show inline comments
 
@@ -89,6 +89,7 @@ def test_postfix_main_cf_file_content(File):
 
    assert "smtpd_tls_key_file = /etc/ssl/private/parameters-optional_smtp.key" in config_lines
 
    assert "  reject_rbl bl.spamcop.net" in config_lines
 
    assert "  reject_rbl zen.spamhaus.org" in config_lines
 
    assert "smtp_host_lookup = dns, native" in config_lines
 

	
 

	
 
def test_local_aliases(Command, File, Sudo):
0 comments (0 inline, 0 general)