97 lines
		
	
	
	
		
			2.6 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			97 lines
		
	
	
	
		
			2.6 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
from ipaddress import ip_interface
 | 
						|
 | 
						|
database_password = repo.vault.password_for(f'{node.name} db mailserver')
 | 
						|
 | 
						|
defaults = {
 | 
						|
    'mailserver': {
 | 
						|
        'debug': False,
 | 
						|
        'maildir': '/var/vmail',
 | 
						|
        'database': {
 | 
						|
            'host': '127.0.0.1', # dont use localhost
 | 
						|
            'name': 'mailserver',
 | 
						|
            'user': 'mailserver',
 | 
						|
            'password': database_password,
 | 
						|
        },
 | 
						|
        'test_password': repo.vault.password_for(f'{node.name} test_pw mailserver'),
 | 
						|
        'domains': [],
 | 
						|
    },
 | 
						|
    'postgresql': {
 | 
						|
        'roles': {
 | 
						|
            'mailserver': {
 | 
						|
                'password': database_password,
 | 
						|
            },
 | 
						|
        },
 | 
						|
        'databases': {
 | 
						|
            'mailserver': {
 | 
						|
                'owner': 'mailserver',
 | 
						|
            },
 | 
						|
        },
 | 
						|
    },
 | 
						|
    'zfs': {
 | 
						|
        'datasets': {
 | 
						|
            'tank/vmail': {
 | 
						|
                'mountpoint': '/var/vmail',
 | 
						|
                'compression': 'on',
 | 
						|
                'atime': 'off',
 | 
						|
                'recordsize': '16384',
 | 
						|
            },
 | 
						|
            'tank/vmail/index': {
 | 
						|
                'mountpoint': '/var/vmail/index',
 | 
						|
                'compression': 'on',
 | 
						|
                'atime': 'off',
 | 
						|
                'recordsize': '4096',
 | 
						|
                'com.sun:auto-snapshot': 'false',
 | 
						|
                'backup': False,
 | 
						|
            },
 | 
						|
        },
 | 
						|
    },
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
@metadata_reactor.provides(
 | 
						|
    'dns',
 | 
						|
)
 | 
						|
def dns(metadata):
 | 
						|
    dns = {}
 | 
						|
 | 
						|
    for domain in metadata.get('mailserver/domains'):
 | 
						|
        dns[domain] = {
 | 
						|
            'MX': [f"5 {metadata.get('mailserver/hostname')}."],
 | 
						|
            'TXT': ['v=spf1 a mx -all'],
 | 
						|
        }
 | 
						|
        report_email = metadata.get('mailserver/dmarc_report_email')
 | 
						|
        dns[f'_dmarc.{domain}'] = {
 | 
						|
            'TXT': ['; '.join(f'{k}={v}' for k, v in {
 | 
						|
                # dmarc version
 | 
						|
                'v': 'DMARC1',
 | 
						|
                # reject on failure
 | 
						|
                'p': 'reject',
 | 
						|
                # standard reports
 | 
						|
                'rua': f'mailto:{report_email}',
 | 
						|
                # forensic reports
 | 
						|
                'fo': 1,
 | 
						|
                'ruf': f'mailto:{report_email}',
 | 
						|
                # require alignment between the DKIM domain and the parent Header From domain
 | 
						|
                'adkim': 's',
 | 
						|
                # require alignment between the SPF domain (the sender) and the Header From domain
 | 
						|
                'aspf': 's',
 | 
						|
            }.items())]
 | 
						|
        }
 | 
						|
 | 
						|
    return {
 | 
						|
        'dns': dns,
 | 
						|
    }
 | 
						|
 | 
						|
@metadata_reactor.provides(
 | 
						|
    'letsencrypt/domains',
 | 
						|
)
 | 
						|
def letsencrypt(metadata):
 | 
						|
    return {
 | 
						|
        'letsencrypt': {
 | 
						|
            'domains': {
 | 
						|
                metadata.get('mailserver/hostname'): {
 | 
						|
                    'reload': {'dovecot', 'postfix'},
 | 
						|
                },
 | 
						|
            },
 | 
						|
        },
 | 
						|
    }
 |