aboutsummaryrefslogtreecommitdiff
path: root/roles
diff options
context:
space:
mode:
authorSam Chudnick <sam@chudnick.com>2023-07-02 19:04:30 -0400
committerSam Chudnick <sam@chudnick.com>2023-07-02 19:04:30 -0400
commit724d877995dfcc10c462a18dcb4ea6c8b60c2d03 (patch)
tree270537b8fca585717c1ffa7708e492593f7b2ed5 /roles
initial commit
Diffstat (limited to 'roles')
-rw-r--r--roles/dovecot/defaults/main.yml0
-rw-r--r--roles/dovecot/files/conf.d/10-auth.conf10
-rw-r--r--roles/dovecot/files/conf.d/10-director.conf60
-rw-r--r--roles/dovecot/files/conf.d/10-logging.conf109
-rw-r--r--roles/dovecot/files/conf.d/10-mail.conf10
-rw-r--r--roles/dovecot/files/conf.d/10-master.conf22
-rw-r--r--roles/dovecot/files/conf.d/10-tcpwrapper.conf14
-rw-r--r--roles/dovecot/files/conf.d/15-lda.conf4
-rw-r--r--roles/dovecot/files/conf.d/15-mailboxes.conf25
-rw-r--r--roles/dovecot/files/conf.d/20-imap.conf2
-rw-r--r--roles/dovecot/files/conf.d/90-acl.conf19
-rw-r--r--roles/dovecot/files/conf.d/90-plugin.conf11
-rw-r--r--roles/dovecot/files/conf.d/90-quota.conf83
-rw-r--r--roles/dovecot/files/conf.d/90-sieve-extprograms.conf44
-rw-r--r--roles/dovecot/files/conf.d/90-sieve.conf6
-rw-r--r--roles/dovecot/files/conf.d/auth-checkpassword.conf.ext21
-rw-r--r--roles/dovecot/files/conf.d/auth-deny.conf.ext15
-rw-r--r--roles/dovecot/files/conf.d/auth-dict.conf.ext16
-rw-r--r--roles/dovecot/files/conf.d/auth-master.conf.ext16
-rw-r--r--roles/dovecot/files/conf.d/auth-passwdfile.conf.ext20
-rw-r--r--roles/dovecot/files/conf.d/auth-sql.conf.ext30
-rw-r--r--roles/dovecot/files/conf.d/auth-static.conf.ext24
-rw-r--r--roles/dovecot/files/conf.d/auth-system.conf.ext74
-rw-r--r--roles/dovecot/files/default.sieve22
-rw-r--r--roles/dovecot/files/dovecot.conf16
-rw-r--r--roles/dovecot/files/dovecot_pam8
-rw-r--r--roles/dovecot/handlers/main.yml0
-rw-r--r--roles/dovecot/tasks/main.yml67
-rw-r--r--roles/dovecot/templates/10-ssl.conf.j220
-rw-r--r--roles/opendkim/defaults/main.yml0
-rw-r--r--roles/opendkim/handlers/main.yml0
-rw-r--r--roles/opendkim/tasks/main.yml57
-rw-r--r--roles/opendkim/templates/opendkim.conf.j221
-rw-r--r--roles/opendmarc/defaults/main.yml0
-rw-r--r--roles/opendmarc/files/opendmarc.conf11
-rw-r--r--roles/opendmarc/handlers/main.yml0
-rw-r--r--roles/opendmarc/tasks/main.yml39
-rw-r--r--roles/policyd_spf/defaults/main.yml0
-rw-r--r--roles/policyd_spf/files/policyd-spf.conf8
-rw-r--r--roles/policyd_spf/handlers/main.yml0
-rw-r--r--roles/policyd_spf/tasks/main.yml13
-rw-r--r--roles/postfix/defaults/main.yml0
-rw-r--r--roles/postfix/files/body_checks2
-rw-r--r--roles/postfix/files/header_checks11
-rw-r--r--roles/postfix/handlers/main.yml0
-rw-r--r--roles/postfix/tasks/main.yml84
-rw-r--r--roles/postfix/templates/aliases3
-rw-r--r--roles/postfix/templates/local_maps1
-rw-r--r--roles/postfix/templates/login_maps1
-rw-r--r--roles/postfix/templates/main.cf.j269
-rw-r--r--roles/postfix/templates/master.cf.j284
-rw-r--r--roles/postgrey/defaults/main.yml0
-rw-r--r--roles/postgrey/files/postgrey2
-rw-r--r--roles/postgrey/handlers/main.yml0
-rw-r--r--roles/postgrey/tasks/main.yml24
-rw-r--r--roles/spamassassin/defaults/main.yml0
-rw-r--r--roles/spamassassin/files/defaults9
-rw-r--r--roles/spamassassin/handlers/main.yml0
-rw-r--r--roles/spamassassin/tasks/main.yml40
-rw-r--r--roles/spamassassin/templates/local.cf.j218
60 files changed, 1265 insertions, 0 deletions
diff --git a/roles/dovecot/defaults/main.yml b/roles/dovecot/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/dovecot/defaults/main.yml
diff --git a/roles/dovecot/files/conf.d/10-auth.conf b/roles/dovecot/files/conf.d/10-auth.conf
new file mode 100644
index 0000000..7ac1eee
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-auth.conf
@@ -0,0 +1,10 @@
1# Authentication
2disable_plaintext_auth = yes
3auth_username_format = %n
4auth_mechanisms = plain
5userdb {
6 driver = passwd
7}
8passdb {
9 driver = pam
10}
diff --git a/roles/dovecot/files/conf.d/10-director.conf b/roles/dovecot/files/conf.d/10-director.conf
new file mode 100644
index 0000000..073d8a8
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-director.conf
@@ -0,0 +1,60 @@
1##
2## Director-specific settings.
3##
4
5# Director can be used by Dovecot proxy to keep a temporary user -> mail server
6# mapping. As long as user has simultaneous connections, the user is always
7# redirected to the same server. Each proxy server is running its own director
8# process, and the directors are communicating the state to each others.
9# Directors are mainly useful with NFS-like setups.
10
11# List of IPs or hostnames to all director servers, including ourself.
12# Ports can be specified as ip:port. The default port is the same as
13# what director service's inet_listener is using.
14#director_servers =
15
16# List of IPs or hostnames to all backend mail servers. Ranges are allowed
17# too, like 10.0.0.10-10.0.0.30.
18#director_mail_servers =
19
20# How long to redirect users to a specific server after it no longer has
21# any connections.
22#director_user_expire = 15 min
23
24# How the username is translated before being hashed. Useful values include
25# %Ln if user can log in with or without @domain, %Ld if mailboxes are shared
26# within domain.
27#director_username_hash = %Lu
28
29# To enable director service, uncomment the modes and assign a port.
30service director {
31 unix_listener login/director {
32 #mode = 0666
33 }
34 fifo_listener login/proxy-notify {
35 #mode = 0666
36 }
37 unix_listener director-userdb {
38 #mode = 0600
39 }
40 inet_listener {
41 #port =
42 }
43}
44
45# Enable director for the wanted login services by telling them to
46# connect to director socket instead of the default login socket:
47service imap-login {
48 #executable = imap-login director
49}
50service pop3-login {
51 #executable = pop3-login director
52}
53service submission-login {
54 #executable = submission-login director
55}
56
57# Enable director for LMTP proxying:
58protocol lmtp {
59 #auth_socket_path = director-userdb
60}
diff --git a/roles/dovecot/files/conf.d/10-logging.conf b/roles/dovecot/files/conf.d/10-logging.conf
new file mode 100644
index 0000000..bcd6dea
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-logging.conf
@@ -0,0 +1,109 @@
1##
2## Log destination.
3##
4
5# Log file to use for error messages. "syslog" logs to syslog,
6# /dev/stderr logs to stderr.
7#log_path = syslog
8
9# Log file to use for informational messages. Defaults to log_path.
10#info_log_path =
11# Log file to use for debug messages. Defaults to info_log_path.
12#debug_log_path =
13
14# Syslog facility to use if you're logging to syslog. Usually if you don't
15# want to use "mail", you'll use local0..local7. Also other standard
16# facilities are supported.
17#syslog_facility = mail
18
19##
20## Logging verbosity and debugging.
21##
22
23# Log filter is a space-separated list conditions. If any of the conditions
24# match, the log filter matches (i.e. they're ORed together). Parenthesis
25# are supported if multiple conditions need to be matched together.
26# Supported conditions are:
27# event:<name wildcard> - Match event name. '*' and '?' wildcards supported.
28# source:<filename>[:<line number>] - Match source code filename [and line]
29# field:<key>=<value wildcard> - Match field key to a value. Can be specified
30# multiple times to match multiple keys.
31# cat[egory]:<value> - Match a category. Can be specified multiple times to
32# match multiple categories.
33# For example: event:http_request_* (cat:error cat:storage)
34
35# Filter to specify what debug logging to enable. This will eventually replace
36# mail_debug and auth_debug settings.
37#log_debug =
38
39# Crash after logging a matching event. For example category:error will crash
40# any time an error is logged, which can be useful for debugging.
41#log_core_filter =
42
43# Log unsuccessful authentication attempts and the reasons why they failed.
44#auth_verbose = no
45
46# In case of password mismatches, log the attempted password. Valid values are
47# no, plain and sha1. sha1 can be useful for detecting brute force password
48# attempts vs. user simply trying the same password over and over again.
49# You can also truncate the value to n chars by appending ":n" (e.g. sha1:6).
50#auth_verbose_passwords = no
51
52# Even more verbose logging for debugging purposes. Shows for example SQL
53# queries.
54#auth_debug = no
55
56# In case of password mismatches, log the passwords and used scheme so the
57# problem can be debugged. Enabling this also enables auth_debug.
58#auth_debug_passwords = no
59
60# Enable mail process debugging. This can help you figure out why Dovecot
61# isn't finding your mails.
62#mail_debug = no
63
64# Show protocol level SSL errors.
65#verbose_ssl = no
66
67# mail_log plugin provides more event logging for mail processes.
68plugin {
69 # Events to log. Also available: flag_change append
70 #mail_log_events = delete undelete expunge copy mailbox_delete mailbox_rename
71 # Available fields: uid, box, msgid, from, subject, size, vsize, flags
72 # size and vsize are available only for expunge and copy events.
73 #mail_log_fields = uid box msgid size
74}
75
76##
77## Log formatting.
78##
79
80# Prefix for each line written to log file. % codes are in strftime(3)
81# format.
82#log_timestamp = "%b %d %H:%M:%S "
83
84# Space-separated list of elements we want to log. The elements which have
85# a non-empty variable value are joined together to form a comma-separated
86# string.
87#login_log_format_elements = user=<%u> method=%m rip=%r lip=%l mpid=%e %c
88
89# Login log format. %s contains login_log_format_elements string, %$ contains
90# the data we want to log.
91#login_log_format = %$: %s
92
93# Log prefix for mail processes. See doc/wiki/Variables.txt for list of
94# possible variables you can use.
95#mail_log_prefix = "%s(%u)<%{pid}><%{session}>: "
96
97# Format to use for logging mail deliveries:
98# %$ - Delivery status message (e.g. "saved to INBOX")
99# %m / %{msgid} - Message-ID
100# %s / %{subject} - Subject
101# %f / %{from} - From address
102# %p / %{size} - Physical size
103# %w / %{vsize} - Virtual size
104# %e / %{from_envelope} - MAIL FROM envelope
105# %{to_envelope} - RCPT TO envelope
106# %{delivery_time} - How many milliseconds it took to deliver the mail
107# %{session_time} - How long LMTP session took, not including delivery_time
108# %{storage_id} - Backend-specific ID for mail, e.g. Maildir filename
109#deliver_log_format = msgid=%m: %$
diff --git a/roles/dovecot/files/conf.d/10-mail.conf b/roles/dovecot/files/conf.d/10-mail.conf
new file mode 100644
index 0000000..683c5e9
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-mail.conf
@@ -0,0 +1,10 @@
1# Mail location
2mail_location = maildir:~/Mail:INBOX=~/Mail/Inbox:LAYOUT=fs
3namespace inbox {
4 type = private
5 prefix =
6 separator = /
7 inbox = yes
8 subscriptions = yes
9 list = yes
10}
diff --git a/roles/dovecot/files/conf.d/10-master.conf b/roles/dovecot/files/conf.d/10-master.conf
new file mode 100644
index 0000000..c2c9493
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-master.conf
@@ -0,0 +1,22 @@
1# Master Configuration
2service imap-login {
3 # Run login processes in high-security mode (see: LoginProcess.txt in dovecot docs)
4 service_count = 1
5 # Disable unencrypted IMAP by setting port for plain IMAP to 0
6 inet_listener imap {
7 port = 0
8 }
9 inet_listener imaps {
10 port = 993
11 ssl = yes
12 }
13}
14
15# Allow postfix to user dovecot SASL
16service auth {
17 unix_listener /var/spool/postfix/private/auth {
18 mode = 0660
19 user = postfix
20 group = postfix
21 }
22}
diff --git a/roles/dovecot/files/conf.d/10-tcpwrapper.conf b/roles/dovecot/files/conf.d/10-tcpwrapper.conf
new file mode 100644
index 0000000..b237d96
--- /dev/null
+++ b/roles/dovecot/files/conf.d/10-tcpwrapper.conf
@@ -0,0 +1,14 @@
1# 10-tcpwrapper.conf
2#
3# service name for hosts.{allow|deny} are those defined as
4# inet_listener in master.conf
5#
6#login_access_sockets = tcpwrap
7#
8#service tcpwrap {
9# unix_listener login/tcpwrap {
10# group = $default_login_user
11# mode = 0600
12# user = $default_login_user
13# }
14#}
diff --git a/roles/dovecot/files/conf.d/15-lda.conf b/roles/dovecot/files/conf.d/15-lda.conf
new file mode 100644
index 0000000..8538f79
--- /dev/null
+++ b/roles/dovecot/files/conf.d/15-lda.conf
@@ -0,0 +1,4 @@
1# Local Delivery Agent
2protocol lda {
3 mail_plugins = $mail_plugins sieve
4}
diff --git a/roles/dovecot/files/conf.d/15-mailboxes.conf b/roles/dovecot/files/conf.d/15-mailboxes.conf
new file mode 100644
index 0000000..4de88b0
--- /dev/null
+++ b/roles/dovecot/files/conf.d/15-mailboxes.conf
@@ -0,0 +1,25 @@
1# Mailboxes
2namespace inbox {
3 mailbox Sent {
4 special_use = \Sent
5 auto = subscribe
6 }
7 mailbox Trash {
8 special_use = \Trash
9 auto = create
10 autoexpunge = 30d
11 }
12 mailbox Drafts {
13 special_use = \Drafts
14 auto = subscribe
15 }
16 mailbox Spam {
17 special_use = \Junk
18 auto = create
19 autoexpunge = 30d
20 }
21 mailbox Archive {
22 special_use = \Archive
23 auto = create
24 }
25}
diff --git a/roles/dovecot/files/conf.d/20-imap.conf b/roles/dovecot/files/conf.d/20-imap.conf
new file mode 100644
index 0000000..0e7d4ae
--- /dev/null
+++ b/roles/dovecot/files/conf.d/20-imap.conf
@@ -0,0 +1,2 @@
1# IMAP
2imap_capability = +SPECIAL-USE
diff --git a/roles/dovecot/files/conf.d/90-acl.conf b/roles/dovecot/files/conf.d/90-acl.conf
new file mode 100644
index 0000000..f0c0e7a
--- /dev/null
+++ b/roles/dovecot/files/conf.d/90-acl.conf
@@ -0,0 +1,19 @@
1##
2## Mailbox access control lists.
3##
4
5# vfile backend reads ACLs from "dovecot-acl" file from mail directory.
6# You can also optionally give a global ACL directory path where ACLs are
7# applied to all users' mailboxes. The global ACL directory contains
8# one file for each mailbox, eg. INBOX or sub.mailbox. cache_secs parameter
9# specifies how many seconds to wait between stat()ing dovecot-acl file
10# to see if it changed.
11plugin {
12 #acl = vfile:/etc/dovecot/global-acls:cache_secs=300
13}
14
15# To let users LIST mailboxes shared by other users, Dovecot needs a
16# shared mailbox dictionary. For example:
17plugin {
18 #acl_shared_dict = file:/var/lib/dovecot/shared-mailboxes
19}
diff --git a/roles/dovecot/files/conf.d/90-plugin.conf b/roles/dovecot/files/conf.d/90-plugin.conf
new file mode 100644
index 0000000..8c8fccf
--- /dev/null
+++ b/roles/dovecot/files/conf.d/90-plugin.conf
@@ -0,0 +1,11 @@
1##
2## Plugin settings
3##
4
5# All wanted plugins must be listed in mail_plugins setting before any of the
6# settings take effect. See <doc/wiki/Plugins.txt> for list of plugins and
7# their configuration. Note that %variable expansion is done for all values.
8
9plugin {
10 #setting_name = value
11}
diff --git a/roles/dovecot/files/conf.d/90-quota.conf b/roles/dovecot/files/conf.d/90-quota.conf
new file mode 100644
index 0000000..3308c05
--- /dev/null
+++ b/roles/dovecot/files/conf.d/90-quota.conf
@@ -0,0 +1,83 @@
1##
2## Quota configuration.
3##
4
5# Note that you also have to enable quota plugin in mail_plugins setting.
6# <doc/wiki/Quota.txt>
7
8##
9## Quota limits
10##
11
12# Quota limits are set using "quota_rule" parameters. To get per-user quota
13# limits, you can set/override them by returning "quota_rule" extra field
14# from userdb. It's also possible to give mailbox-specific limits, for example
15# to give additional 100 MB when saving to Trash:
16
17plugin {
18 #quota_rule = *:storage=1G
19 #quota_rule2 = Trash:storage=+100M
20
21 # LDA/LMTP allows saving the last mail to bring user from under quota to
22 # over quota, if the quota doesn't grow too high. Default is to allow as
23 # long as quota will stay under 10% above the limit. Also allowed e.g. 10M.
24 #quota_grace = 10%%
25
26 # Quota plugin can also limit the maximum accepted mail size.
27 #quota_max_mail_size = 100M
28}
29
30##
31## Quota warnings
32##
33
34# You can execute a given command when user exceeds a specified quota limit.
35# Each quota root has separate limits. Only the command for the first
36# exceeded limit is executed, so put the highest limit first.
37# The commands are executed via script service by connecting to the named
38# UNIX socket (quota-warning below).
39# Note that % needs to be escaped as %%, otherwise "% " expands to empty.
40
41plugin {
42 #quota_warning = storage=95%% quota-warning 95 %u
43 #quota_warning2 = storage=80%% quota-warning 80 %u
44}
45
46# Example quota-warning service. The unix listener's permissions should be
47# set in a way that mail processes can connect to it. Below example assumes
48# that mail processes run as vmail user. If you use mode=0666, all system users
49# can generate quota warnings to anyone.
50#service quota-warning {
51# executable = script /usr/local/bin/quota-warning.sh
52# user = dovecot
53# unix_listener quota-warning {
54# user = vmail
55# }
56#}
57
58##
59## Quota backends
60##
61
62# Multiple backends are supported:
63# dirsize: Find and sum all the files found from mail directory.
64# Extremely SLOW with Maildir. It'll eat your CPU and disk I/O.
65# dict: Keep quota stored in dictionary (eg. SQL)
66# maildir: Maildir++ quota
67# fs: Read-only support for filesystem quota
68
69plugin {
70 #quota = dirsize:User quota
71 #quota = maildir:User quota
72 #quota = dict:User quota::proxy::quota
73 #quota = fs:User quota
74}
75
76# Multiple quota roots are also possible, for example this gives each user
77# their own 100MB quota and one shared 1GB quota within the domain:
78plugin {
79 #quota = dict:user::proxy::quota
80 #quota2 = dict:domain:%d:proxy::quota_domain
81 #quota_rule = *:storage=102400
82 #quota2_rule = *:storage=1048576
83}
diff --git a/roles/dovecot/files/conf.d/90-sieve-extprograms.conf b/roles/dovecot/files/conf.d/90-sieve-extprograms.conf
new file mode 100644
index 0000000..17dcb77
--- /dev/null
+++ b/roles/dovecot/files/conf.d/90-sieve-extprograms.conf
@@ -0,0 +1,44 @@
1# Sieve Extprograms plugin configuration
2
3# Don't forget to add the sieve_extprograms plugin to the sieve_plugins setting.
4# Also enable the extensions you need (one or more of vnd.dovecot.pipe,
5# vnd.dovecot.filter and vnd.dovecot.execute) by adding these to the
6# sieve_extensions or sieve_global_extensions settings. Restricting these
7# extensions to a global context using sieve_global_extensions is recommended.
8
9plugin {
10
11 # The directory where the program sockets are located for the
12 # vnd.dovecot.pipe, vnd.dovecot.filter and vnd.dovecot.execute extension
13 # respectively. The name of each unix socket contained in that directory
14 # directly maps to a program-name referenced from the Sieve script.
15 #sieve_pipe_socket_dir = sieve-pipe
16 #sieve_filter_socket_dir = sieve-filter
17 #sieve_execute_socket_dir = sieve-execute
18
19 # The directory where the scripts are located for direct execution by the
20 # vnd.dovecot.pipe, vnd.dovecot.filter and vnd.dovecot.execute extension
21 # respectively. The name of each script contained in that directory
22 # directly maps to a program-name referenced from the Sieve script.
23 #sieve_pipe_bin_dir = /usr/lib/dovecot/sieve-pipe
24 #sieve_filter_bin_dir = /usr/lib/dovecot/sieve-filter
25 #sieve_execute_bin_dir = /usr/lib/dovecot/sieve-execute
26}
27
28# An example program service called 'do-something' to pipe messages to
29#service do-something {
30 # Define the executed script as parameter to the sieve service
31 #executable = script /usr/lib/dovecot/sieve-pipe/do-something.sh
32
33 # Use some unprivileged user for executing the program
34 #user = dovenull
35
36 # The unix socket located in the sieve_pipe_socket_dir (as defined in the
37 # plugin {} section above)
38 #unix_listener sieve-pipe/do-something {
39 # LDA/LMTP must have access
40 # user = vmail
41 # mode = 0600
42 #}
43#}
44
diff --git a/roles/dovecot/files/conf.d/90-sieve.conf b/roles/dovecot/files/conf.d/90-sieve.conf
new file mode 100644
index 0000000..c7ef6c4
--- /dev/null
+++ b/roles/dovecot/files/conf.d/90-sieve.conf
@@ -0,0 +1,6 @@
1# Sieve Configuration
2plugin {
3 sieve = ~/.dovecot.sieve
4 sieve_default = /var/lib/dovecot/sieve/default.sieve
5 sieve_global = /var/lib/dovecot/sieve/
6}
diff --git a/roles/dovecot/files/conf.d/auth-checkpassword.conf.ext b/roles/dovecot/files/conf.d/auth-checkpassword.conf.ext
new file mode 100644
index 0000000..b2fb13a
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-checkpassword.conf.ext
@@ -0,0 +1,21 @@
1# Authentication for checkpassword users. Included from 10-auth.conf.
2#
3# <doc/wiki/AuthDatabase.CheckPassword.txt>
4
5passdb {
6 driver = checkpassword
7 args = /usr/bin/checkpassword
8}
9
10# passdb lookup should return also userdb info
11userdb {
12 driver = prefetch
13}
14
15# Standard checkpassword doesn't support direct userdb lookups.
16# If you need checkpassword userdb, the checkpassword must support
17# Dovecot-specific extensions.
18#userdb {
19# driver = checkpassword
20# args = /usr/bin/checkpassword
21#}
diff --git a/roles/dovecot/files/conf.d/auth-deny.conf.ext b/roles/dovecot/files/conf.d/auth-deny.conf.ext
new file mode 100644
index 0000000..ce3f1cf
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-deny.conf.ext
@@ -0,0 +1,15 @@
1# Deny access for users. Included from 10-auth.conf.
2
3# Users can be (temporarily) disabled by adding a passdb with deny=yes.
4# If the user is found from that database, authentication will fail.
5# The deny passdb should always be specified before others, so it gets
6# checked first.
7
8# Example deny passdb using passwd-file. You can use any passdb though.
9passdb {
10 driver = passwd-file
11 deny = yes
12
13 # File contains a list of usernames, one per line
14 args = /etc/dovecot/deny-users
15}
diff --git a/roles/dovecot/files/conf.d/auth-dict.conf.ext b/roles/dovecot/files/conf.d/auth-dict.conf.ext
new file mode 100644
index 0000000..0be4847
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-dict.conf.ext
@@ -0,0 +1,16 @@
1# Authentication via dict backend. Included from 10-auth.conf.
2#
3# <doc/wiki/AuthDatabase.Dict.txt>
4
5passdb {
6 driver = dict
7
8 # Path for dict configuration file, see
9 # example-config/dovecot-dict-auth.conf.ext
10 args = /etc/dovecot/dovecot-dict-auth.conf.ext
11}
12
13userdb {
14 driver = dict
15 args = /etc/dovecot/dovecot-dict-auth.conf.ext
16}
diff --git a/roles/dovecot/files/conf.d/auth-master.conf.ext b/roles/dovecot/files/conf.d/auth-master.conf.ext
new file mode 100644
index 0000000..2cf128f
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-master.conf.ext
@@ -0,0 +1,16 @@
1# Authentication for master users. Included from 10-auth.conf.
2
3# By adding master=yes setting inside a passdb you make the passdb a list
4# of "master users", who can log in as anyone else.
5# <doc/wiki/Authentication.MasterUsers.txt>
6
7# Example master user passdb using passwd-file. You can use any passdb though.
8passdb {
9 driver = passwd-file
10 master = yes
11 args = /etc/dovecot/master-users
12
13 # Unless you're using PAM, you probably still want the destination user to
14 # be looked up from passdb that it really exists. pass=yes does that.
15 pass = yes
16}
diff --git a/roles/dovecot/files/conf.d/auth-passwdfile.conf.ext b/roles/dovecot/files/conf.d/auth-passwdfile.conf.ext
new file mode 100644
index 0000000..c89d28c
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-passwdfile.conf.ext
@@ -0,0 +1,20 @@
1# Authentication for passwd-file users. Included from 10-auth.conf.
2#
3# passwd-like file with specified location.
4# <doc/wiki/AuthDatabase.PasswdFile.txt>
5
6passdb {
7 driver = passwd-file
8 args = scheme=CRYPT username_format=%u /etc/dovecot/users
9}
10
11userdb {
12 driver = passwd-file
13 args = username_format=%u /etc/dovecot/users
14
15 # Default fields that can be overridden by passwd-file
16 #default_fields = quota_rule=*:storage=1G
17
18 # Override fields from passwd-file
19 #override_fields = home=/home/virtual/%u
20}
diff --git a/roles/dovecot/files/conf.d/auth-sql.conf.ext b/roles/dovecot/files/conf.d/auth-sql.conf.ext
new file mode 100644
index 0000000..ccbea86
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-sql.conf.ext
@@ -0,0 +1,30 @@
1# Authentication for SQL users. Included from 10-auth.conf.
2#
3# <doc/wiki/AuthDatabase.SQL.txt>
4
5passdb {
6 driver = sql
7
8 # Path for SQL configuration file, see example-config/dovecot-sql.conf.ext
9 args = /etc/dovecot/dovecot-sql.conf.ext
10}
11
12# "prefetch" user database means that the passdb already provided the
13# needed information and there's no need to do a separate userdb lookup.
14# <doc/wiki/UserDatabase.Prefetch.txt>
15#userdb {
16# driver = prefetch
17#}
18
19userdb {
20 driver = sql
21 args = /etc/dovecot/dovecot-sql.conf.ext
22}
23
24# If you don't have any user-specific settings, you can avoid the user_query
25# by using userdb static instead of userdb sql, for example:
26# <doc/wiki/UserDatabase.Static.txt>
27#userdb {
28 #driver = static
29 #args = uid=vmail gid=vmail home=/var/vmail/%u
30#}
diff --git a/roles/dovecot/files/conf.d/auth-static.conf.ext b/roles/dovecot/files/conf.d/auth-static.conf.ext
new file mode 100644
index 0000000..90890c5
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-static.conf.ext
@@ -0,0 +1,24 @@
1# Static passdb. Included from 10-auth.conf.
2
3# This can be used for situations where Dovecot doesn't need to verify the
4# username or the password, or if there is a single password for all users:
5#
6# - proxy frontend, where the backend verifies the password
7# - proxy backend, where the frontend already verified the password
8# - authentication with SSL certificates
9# - simple testing
10
11#passdb {
12# driver = static
13# args = proxy=y host=%1Mu.example.com nopassword=y
14#}
15
16#passdb {
17# driver = static
18# args = password=test
19#}
20
21#userdb {
22# driver = static
23# args = uid=vmail gid=vmail home=/home/%u
24#}
diff --git a/roles/dovecot/files/conf.d/auth-system.conf.ext b/roles/dovecot/files/conf.d/auth-system.conf.ext
new file mode 100644
index 0000000..dadb9f7
--- /dev/null
+++ b/roles/dovecot/files/conf.d/auth-system.conf.ext
@@ -0,0 +1,74 @@
1# Authentication for system users. Included from 10-auth.conf.
2#
3# <doc/wiki/PasswordDatabase.txt>
4# <doc/wiki/UserDatabase.txt>
5
6# PAM authentication. Preferred nowadays by most systems.
7# PAM is typically used with either userdb passwd or userdb static.
8# REMEMBER: You'll need /etc/pam.d/dovecot file created for PAM
9# authentication to actually work. <doc/wiki/PasswordDatabase.PAM.txt>
10passdb {
11 driver = pam
12 # [session=yes] [setcred=yes] [failure_show_msg=yes] [max_requests=<n>]
13 # [cache_key=<key>] [<service name>]
14 #args = dovecot
15}
16
17# System users (NSS, /etc/passwd, or similar).
18# In many systems nowadays this uses Name Service Switch, which is
19# configured in /etc/nsswitch.conf. <doc/wiki/AuthDatabase.Passwd.txt>
20#passdb {
21 #driver = passwd
22 # [blocking=no]
23 #args =
24#}
25
26# Shadow passwords for system users (NSS, /etc/shadow or similar).
27# Deprecated by PAM nowadays.
28# <doc/wiki/PasswordDatabase.Shadow.txt>
29#passdb {
30 #driver = shadow
31 # [blocking=no]
32 #args =
33#}
34
35# PAM-like authentication for OpenBSD.
36# <doc/wiki/PasswordDatabase.BSDAuth.txt>
37#passdb {
38 #driver = bsdauth
39 # [blocking=no] [cache_key=<key>]
40 #args =
41#}
42
43##
44## User databases
45##
46
47# System users (NSS, /etc/passwd, or similar). In many systems nowadays this
48# uses Name Service Switch, which is configured in /etc/nsswitch.conf.
49userdb {
50 # <doc/wiki/AuthDatabase.Passwd.txt>
51 driver = passwd
52 # [blocking=no]
53 #args =
54
55 # Override fields from passwd
56 #override_fields = home=/home/virtual/%u
57}
58
59# Static settings generated from template <doc/wiki/UserDatabase.Static.txt>
60#userdb {
61 #driver = static
62 # Can return anything a userdb could normally return. For example:
63 #
64 # args = uid=500 gid=500 home=/var/mail/%u
65 #
66 # LDA and LMTP needs to look up users only from the userdb. This of course
67 # doesn't work with static userdb because there is no list of users.
68 # Normally static userdb handles this by doing a passdb lookup. This works
69 # with most passdbs, with PAM being the most notable exception. If you do
70 # the user verification another way, you can add allow_all_users=yes to
71 # the args in which case the passdb lookup is skipped.
72 #
73 #args =
74#}
diff --git a/roles/dovecot/files/default.sieve b/roles/dovecot/files/default.sieve
new file mode 100644
index 0000000..6709988
--- /dev/null
+++ b/roles/dovecot/files/default.sieve
@@ -0,0 +1,22 @@
1require ["fileinto", "mailbox"];
2/*
3* Discard mail that has a spam score greater than or equal to 5
4*/
5if header :contains "X-Spam-Level" "*****" {
6 discard;
7 stop;
8}
9/*
10* Discard messages marked as infected by virus scanner
11*/
12if header :contains "X-Virus-Scan" "infected" {
13 discard;
14 stop;
15}
16/*
17* If message is marked as spam (and falls below discard threshold) put into spam mailbox
18*/
19if header :contains "X-Spam-Flag" "YES" {
20 fileinto "Spam";
21}
22
diff --git a/roles/dovecot/files/dovecot.conf b/roles/dovecot/files/dovecot.conf
new file mode 100644
index 0000000..14a4cf0
--- /dev/null
+++ b/roles/dovecot/files/dovecot.conf
@@ -0,0 +1,16 @@
1# Enable installed protocols
2!include_try /usr/share/dovecot/protocols.d/*.protocol
3
4dict {
5 #quota = mysql:/etc/dovecot/dovecot-dict-sql.conf.ext
6 #expire = sqlite:/etc/dovecot/dovecot-dict-sql.conf.ext
7}
8
9# Most of the actual configuration gets included below. The filenames are
10# first sorted by their ASCII value and parsed in that order. The 00-prefixes
11# in filenames are intended to make it easier to understand the ordering.
12!include conf.d/*.conf
13
14# A config file can also tried to be included without giving an error if
15# it's not found:
16!include_try local.conf
diff --git a/roles/dovecot/files/dovecot_pam b/roles/dovecot/files/dovecot_pam
new file mode 100644
index 0000000..af0e0dd
--- /dev/null
+++ b/roles/dovecot/files/dovecot_pam
@@ -0,0 +1,8 @@
1#%PAM-1.0
2
3@include common-auth
4@include common-account
5@include common-session
6
7auth required pam_unix.so
8account required pam_unix.so
diff --git a/roles/dovecot/handlers/main.yml b/roles/dovecot/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/dovecot/handlers/main.yml
diff --git a/roles/dovecot/tasks/main.yml b/roles/dovecot/tasks/main.yml
new file mode 100644
index 0000000..ce5eb2c
--- /dev/null
+++ b/roles/dovecot/tasks/main.yml
@@ -0,0 +1,67 @@
1- name: install packages
2 package:
3 name:
4 - dovecot-imapd
5 - dovecot-sieve
6 state: latest
7
8- name: deploy dovecot.conf
9 copy:
10 src: dovecot.conf
11 dest: /etc/dovecot/dovecot.conf
12 owner: root
13 group: root
14 mode: '0644'
15
16- name: deploy dovecot configuration files
17 copy:
18 src: "{{ item }}"
19 dest: /etc/dovecot/conf.d/
20 owner: root
21 group: root
22 mode: '0644'
23 with_fileglob: "files/conf.d/*"
24
25- name: deploy dovecot tls configuration file
26 template:
27 src: templates/10-ssl.conf.j2
28 dest: /etc/dovecot/conf.d/10-ssl.conf
29 owner: root
30 group: root
31 mode: '0644'
32
33- name: create sieve dir
34 file:
35 path: /var/lib/dovecot/sieve
36 state: directory
37
38- name: deploy default sieve script
39 copy:
40 src: default.sieve
41 dest: /var/lib/dovecot/sieve/default.sieve
42 owner: root
43 group: root
44 mode: '0644'
45
46- name: compile default sieve script
47 command:
48 cmd: sievec /var/lib/dovecot/sieve/default.sieve
49
50- name: deploy dovecot PAM configuration
51 copy:
52 src: dovecot_pam
53 dest: /etc/pam.d/dovecot
54 owner: root
55 group: root
56 mode: '0644'
57
58- name: enable dovecot
59 systemd:
60 enabled: yes
61 masked: no
62 name: dovecot
63
64- name: restart dovecot
65 service:
66 name: dovecot
67 state: restarted
diff --git a/roles/dovecot/templates/10-ssl.conf.j2 b/roles/dovecot/templates/10-ssl.conf.j2
new file mode 100644
index 0000000..8efa1d2
--- /dev/null
+++ b/roles/dovecot/templates/10-ssl.conf.j2
@@ -0,0 +1,20 @@
1# SSL/TLS Configuration
2ssl = required
3ssl_key = "</etc/letsencrypt/live/{{ mail_domain }}/privkey.pem"
4ssl_cert = "</etc/letsencrypt/live/{{ mail_domain }}/fullchain.pem"
5ssl_client_ca_dir = /etc/ssl/certs
6ssl_dh = </usr/share/dovecot/dh.pem
7
8# Mozilla modern compatibility (https://wiki.mozilla.org/Security/Server_Side_TLS)
9# This is here for future use - Dovecot does not support using only TLSv1.3 right now.
10#ssl_min_protocol = TLSv1.3
11# Ciphers listed here are just for reference, DO NOT uncomment, this is not a valid
12# openssl cipherlist
13#ssl_cipher_list = TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256:TLS_AES_128_GCM_SHA256
14
15# Mozilla intermediate compatibility (https://wiki.mozilla.org/Security/Server_Side_TLS)
16ssl_min_protocol = TLSv1.2
17ssl_cipher_list = ECDHE+ECDSA+AESGCM:ECDHE+aRSA+AESGCM:ECDHE+ECDSA+CHACHA20:ECDHE+aRSA+CHACHA20:DHE+aRSA+AESGCM:!aNULL:!eNULL
18
19ssl_prefer_server_ciphers = yes
20ssl_client_require_valid_cert = yes
diff --git a/roles/opendkim/defaults/main.yml b/roles/opendkim/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/opendkim/defaults/main.yml
diff --git a/roles/opendkim/handlers/main.yml b/roles/opendkim/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/opendkim/handlers/main.yml
diff --git a/roles/opendkim/tasks/main.yml b/roles/opendkim/tasks/main.yml
new file mode 100644
index 0000000..b56081a
--- /dev/null
+++ b/roles/opendkim/tasks/main.yml
@@ -0,0 +1,57 @@
1- name: install packages
2 package:
3 name:
4 - opendkim
5 - opendkim-tools
6 state: latest
7
8- name: create dkimkeys directory
9 file:
10 path: /etc/dkimkeys
11 owner: opendkim
12 group: opendkim
13 mode: '700'
14 state: directory
15
16- name: generate opendkim key
17 command:
18 cmd: "opendkim-genkey -D /etc/dkimkeys -d {{ domain }} -s {{ dkim_selector }}"
19
20- name: rename dkim key file
21 command: "mv /etc/dkimkeys/{{ dkim_selector }}.private /etc/dkimkeys/{{ dkim_selector }}.pem"
22 args:
23 removes: "/etc/dkimkeys/{{ dkim_selector }}.private"
24 creates: "/etc/dkimkeys/{{ dkim_selector }}.pem"
25
26- name: make directory for socket inside postfix chroot
27 file:
28 path: /var/spool/postfix/opendkim
29 owner: opendkim
30 group: opendkim
31 mode: '770'
32 state: directory
33
34- name: add postfix user to opendkim group
35 user:
36 name: postfix
37 groups: opendkim
38 append: yes
39
40- name: deploy configuration
41 template:
42 src: opendkim.conf.j2
43 dest: /etc/opendkim.conf
44 owner: root
45 group: root
46 mode: '0644'
47
48- name: enable opendkim
49 systemd:
50 enabled: yes
51 masked: no
52 name: opendkim
53
54- name: restart opendkim
55 service:
56 name: opendkim
57 state: restarted
diff --git a/roles/opendkim/templates/opendkim.conf.j2 b/roles/opendkim/templates/opendkim.conf.j2
new file mode 100644
index 0000000..d3335a2
--- /dev/null
+++ b/roles/opendkim/templates/opendkim.conf.j2
@@ -0,0 +1,21 @@
1# OpenDKIM Configuration
2On-BadSignature reject
3On-Security reject
4Syslog yes
5SyslogSuccess yes
6LogResults yes
7Canonicalization simple
8Mode sv
9OversignHeaders From
10Domain {{ domain }}
11Selector {{ dkim_selector }}
12KeyFile /etc/dkimkeys/{{ dkim_selector }}.pem
13UserID opendkim
14UMask 007
15Socket local:/var/spool/postfix/opendkim/opendkim.sock
16PidFile /run/opendkim/opendkim.pid
17TemporaryDirectory /run/opendkim
18InternalHosts 127.0.0.1
19TrustAnchorFile /usr/share/dns/root.key
20RequireSafeKeys True
21AlwaysAddARHeader True
diff --git a/roles/opendmarc/defaults/main.yml b/roles/opendmarc/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/opendmarc/defaults/main.yml
diff --git a/roles/opendmarc/files/opendmarc.conf b/roles/opendmarc/files/opendmarc.conf
new file mode 100644
index 0000000..85a05c2
--- /dev/null
+++ b/roles/opendmarc/files/opendmarc.conf
@@ -0,0 +1,11 @@
1# OpenDMARC Configuration
2PidFile /run/opendmarc/opendmarc.pid
3PublicSuffixList /usr/share/publicsuffix/public_suffix_list.dat
4RejectFailures True
5Socket local:/var/spool/postfix/opendmarc/opendmarc.sock
6Syslog True
7SyslogFacility mail
8UMask 002
9UserID opendmarc
10SPFIgnoreResults True
11SPFSelfValidate True
diff --git a/roles/opendmarc/handlers/main.yml b/roles/opendmarc/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/opendmarc/handlers/main.yml
diff --git a/roles/opendmarc/tasks/main.yml b/roles/opendmarc/tasks/main.yml
new file mode 100644
index 0000000..6c2fb8b
--- /dev/null
+++ b/roles/opendmarc/tasks/main.yml
@@ -0,0 +1,39 @@
1- name: install packages
2 package:
3 name:
4 - opendmarc
5 - dbconfig-no-thanks
6 state: latest
7
8- name: make directory for socket inside postfix chroot
9 file:
10 path: /var/spool/postfix/opendmarc
11 owner: opendmarc
12 group: opendmarc
13 mode: '770'
14 state: directory
15
16- name: add postfix user to opendmarc group
17 user:
18 name: postfix
19 groups: opendmarc
20 append: yes
21
22- name: deploy configuration
23 copy:
24 src: opendmarc.conf
25 dest: /etc/opendmarc.conf
26 owner: root
27 group: root
28 mode: '0644'
29
30- name: enable opendmarc
31 systemd:
32 enabled: yes
33 masked: no
34 name: opendmarc
35
36- name: restart opendmarc
37 service:
38 name: opendmarc
39 state: restarted
diff --git a/roles/policyd_spf/defaults/main.yml b/roles/policyd_spf/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/policyd_spf/defaults/main.yml
diff --git a/roles/policyd_spf/files/policyd-spf.conf b/roles/policyd_spf/files/policyd-spf.conf
new file mode 100644
index 0000000..7fba9ba
--- /dev/null
+++ b/roles/policyd_spf/files/policyd-spf.conf
@@ -0,0 +1,8 @@
1# postfix-policyd-spf configuration
2debugLevel = 1
3TestOnly = 1
4HELO_reject = Fail
5Mail_From_reject = Fail
6PermError_reject = True
7TempError_Defer = True
8Header_Type = AR
diff --git a/roles/policyd_spf/handlers/main.yml b/roles/policyd_spf/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/policyd_spf/handlers/main.yml
diff --git a/roles/policyd_spf/tasks/main.yml b/roles/policyd_spf/tasks/main.yml
new file mode 100644
index 0000000..48aa12d
--- /dev/null
+++ b/roles/policyd_spf/tasks/main.yml
@@ -0,0 +1,13 @@
1- name: install packages
2 package:
3 name:
4 - postfix-policyd-spf-python
5 state: latest
6
7- name: deploy configuration
8 copy:
9 src: policyd-spf.conf
10 dest: /etc/postfix-policyd-spf-python/policyd-spf.conf
11 owner: root
12 group: root
13 mode: '0644'
diff --git a/roles/postfix/defaults/main.yml b/roles/postfix/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/postfix/defaults/main.yml
diff --git a/roles/postfix/files/body_checks b/roles/postfix/files/body_checks
new file mode 100644
index 0000000..795c922
--- /dev/null
+++ b/roles/postfix/files/body_checks
@@ -0,0 +1,2 @@
1#Block iframe vulnerability
2/<iframe/ REJECT
diff --git a/roles/postfix/files/header_checks b/roles/postfix/files/header_checks
new file mode 100644
index 0000000..f655904
--- /dev/null
+++ b/roles/postfix/files/header_checks
@@ -0,0 +1,11 @@
1#Block attachments with executable extensions
2/name=[^>]*\.(exe|pif|com|dll|vbs|bat|sh|bash|so|zip|tar|gz|cpio)/ REJECT
3# Block message/partial vulnerability
4/message\/partial/ REJECT
5# CVE-2022-1328 mitigation - block messages with uuencode
6/^Content-Transfer-Encoding:.*uuencode.*/ REJECT
7# Remove Received string that is created when spamassassin reinjects message into postfix
8# This is to prevent leaking the userid of the spamassassin user
9/^Received:.*userid.*/ IGNORE
10# Remove User-Agent strings from headers
11/^User-Agent: .*/ IGNORE
diff --git a/roles/postfix/handlers/main.yml b/roles/postfix/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/postfix/handlers/main.yml
diff --git a/roles/postfix/tasks/main.yml b/roles/postfix/tasks/main.yml
new file mode 100644
index 0000000..0b482ea
--- /dev/null
+++ b/roles/postfix/tasks/main.yml
@@ -0,0 +1,84 @@
1- name: install packages
2 package:
3 name:
4 - postfix
5 state: latest
6
7- name: deploy postfix main.cf
8 template:
9 src: main.cf.j2
10 dest: /etc/postfix/main.cf
11 owner: root
12 group: root
13 mode: '0644'
14
15- name: deploy postfix master.cf
16 template:
17 src: master.cf.j2
18 dest: /etc/postfix/master.cf
19 owner: root
20 group: root
21 mode: '0644'
22
23- name: create mailadmin user
24 user:
25 name: mailadmin
26 shell: /usr/sbin/nologin
27 password_lock: yes
28
29- name: deploy aliases file
30 template:
31 src: aliases
32 dest: /etc/aliases
33 owner: root
34 group: root
35 mode: '0644'
36
37- name: deploy login_maps
38 template:
39 src: login_maps
40 dest: /etc/postfix/login_maps
41 owner: root
42 group: root
43 mode: '0644'
44
45- name: deploy local_maps
46 template:
47 src: local_maps
48 dest: /etc/postfix/local_maps
49 owner: root
50 group: root
51 mode: '0644'
52
53- name: update address databases
54 shell: |
55 newaliases
56 postmap /etc/postfix/login_maps
57 postmap /etc/postfix/local_maps
58
59- name: deploy header checks file
60 copy:
61 src: header_checks
62 dest: /etc/postfix/header_checks
63 owner: root
64 group: root
65 mode: '0644'
66
67- name: deploy body checks file
68 copy:
69 src: body_checks
70 dest: /etc/postfix/body_checks
71 owner: root
72 group: root
73 mode: '0644'
74
75- name: enable postfix
76 systemd:
77 enabled: yes
78 masked: no
79 name: postfix
80
81- name: restart postfix
82 service:
83 name: postfix
84 state: restarted
diff --git a/roles/postfix/templates/aliases b/roles/postfix/templates/aliases
new file mode 100644
index 0000000..6cb2ca6
--- /dev/null
+++ b/roles/postfix/templates/aliases
@@ -0,0 +1,3 @@
1postmaster: mailadmin
2root: mailadmin
3dmarc: mailadmin
diff --git a/roles/postfix/templates/local_maps b/roles/postfix/templates/local_maps
new file mode 100644
index 0000000..57592f9
--- /dev/null
+++ b/roles/postfix/templates/local_maps
@@ -0,0 +1 @@
mailadmin mailadmin
diff --git a/roles/postfix/templates/login_maps b/roles/postfix/templates/login_maps
new file mode 100644
index 0000000..d3ace34
--- /dev/null
+++ b/roles/postfix/templates/login_maps
@@ -0,0 +1 @@
mailadmin@{{ domain }} mailadmin
diff --git a/roles/postfix/templates/main.cf.j2 b/roles/postfix/templates/main.cf.j2
new file mode 100644
index 0000000..8a2d767
--- /dev/null
+++ b/roles/postfix/templates/main.cf.j2
@@ -0,0 +1,69 @@
1smtpd_banner = $myhostname ESMTP $mail_name
2biff = no
3
4# appending .domain is the MUA's job.
5append_dot_mydomain = no
6
7# Uncomment the next line to generate "delayed mail" warnings
8#delay_warning_time = 4h
9
10readme_directory = no
11
12# See http://www.postfix.org/COMPATIBILITY_README.html -- default to 2 on
13# fresh installs.
14compatibility_level = 2
15
16# TLS parameters
17smtpd_tls_cert_file = /etc/letsencrypt/live/mail.{{ domain }}/fullchain.pem
18smtpd_tls_key_file = /etc/letsencrypt/live/mail.{{ domain }}/privkey.pem
19smtpd_tls_security_level = encrypt
20smtp_tls_CApath=/etc/ssl/certs
21smtp_tls_CAfile=/etc/ssl/certs/ca-certificates.crt
22smtp_tls_security_level = encrypt
23smtp_tls_session_cache_database = btree:${data_directory}/smtp_scache
24
25smtpd_relay_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_unauth_destination
26myhostname = {{ mail_domain }}
27alias_maps = hash:/etc/aliases
28alias_database = hash:/etc/aliases
29myorigin = $mydomain
30mydestination = $myhostname, $mydomain, localhost
31relayhost =
32mynetworks = 127.0.0.0/8 [::1]/128
33mailbox_size_limit = 0
34recipient_delimiter = +
35inet_interfaces = all
36inet_protocols = ipv4
37smtpd_tls_auth_only = yes
38smtpd_tls_mandatory_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
39smtpd_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
40smtp_tls_mandatory_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
41smtp_tls_protocols = !SSLv2, !SSLv3, !TLSv1, !TLSv1.1
42tls_preempt_cipherlist = yes
43smtpd_tls_ciphers = high
44smtpd_tls_mandatory_ciphers = high
45smtp_tls_ciphers = high
46smtp_tls_mandatory_ciphers = high
47smtpd_tls_exclude_ciphers = aNULL, eNULL, EXP, LOW, MEDIUM, PSK, SRP, SHA1, kRSA, CAMELLIA, ARIA, DSS, RSA+AES, ADH, AECDH
48smtp_tls_exclude_ciphers = aNULL, eNULL, EXP, LOW, MEDIUM, PSK, SRP, SHA1, kRSA, CAMELLIA, ARIA, DSS, RSA+AES, ADH, AECDH
49smtpd_sasl_type = dovecot
50smtpd_sasl_path = private/auth
51smtpd_sasl_auth_enable = yes
52smtpd_sasl_security_options = noanonymous, noplaintext
53smtpd_sasl_tls_security_options = noanonymous
54smtpd_helo_required = yes
55smtpd_sender_login_maps = proxy:hash:/etc/postfix/login_maps
56smtpd_helo_restrictions = reject_unknown_helo_hostname, reject_non_fqdn_helo_hostname
57smtpd_sender_restrictions = reject_sender_login_mismatch, reject_non_fqdn_sender, reject_unknown_sender_domain
58smtpd_recipient_restrictions = reject_non_fqdn_recipient, reject_unknown_recipient_domain, permit_sasl_authenticated, reject_unauth_destination, check_policy_service unix:private/postgrey, check_policy_service unix:private/policyd-spf, reject_rbl_client zen.spamhaus.org
59smtpd_data_restrictions = reject_unauth_pipelining
60disable_vrfy_command = yes
61local_recipient_maps = proxy:hash:/etc/postfix/local_maps $alias_maps
62home_mailbox = Mail/Inbox/
63mailbox_command = /usr/lib/dovecot/deliver
64header_checks = regexp:/etc/postfix/header_checks
65body_checks = regexp:/etc/postfix/body_checks
66postscreen_dnsbl_sites = zen.spamhaus.org
67postscreen_dnsbl_action = enforce
68postscreen_greet_action = enforce
69policyd-spf_time_limit = 3600
diff --git a/roles/postfix/templates/master.cf.j2 b/roles/postfix/templates/master.cf.j2
new file mode 100644
index 0000000..ea64537
--- /dev/null
+++ b/roles/postfix/templates/master.cf.j2
@@ -0,0 +1,84 @@
1# ==========================================================================
2# service type private unpriv chroot wakeup maxproc command + args
3# (yes) (yes) (no) (never) (100)
4# ==========================================================================
5smtp inet n - y - 1 postscreen
6pickup unix n - y 60 1 pickup
7cleanup unix n - y - 0 cleanup
8qmgr unix n - n 300 1 qmgr
9tlsmgr unix - - y 1000? 1 tlsmgr
10rewrite unix - - y - - trivial-rewrite
11bounce unix - - y - 0 bounce
12defer unix - - y - 0 bounce
13trace unix - - y - 0 bounce
14verify unix - - y - 1 verify
15flush unix n - y 1000? 0 flush
16proxymap unix - - n - - proxymap
17proxywrite unix - - n - 1 proxymap
18smtp unix - - y - - smtp
19relay unix - - y - - smtp
20 -o syslog_name=postfix/$service_name
21showq unix n - y - - showq
22error unix - - y - - error
23retry unix - - y - - error
24discard unix - - y - - discard
25local unix - n n - - local
26virtual unix - n n - - virtual
27lmtp unix - - y - - lmtp
28anvil unix - - y - 1 anvil
29scache unix - - y - 1 scache
30postlog unix-dgram n - n - 1 postlogd
31
32# ====================================================================
33# Interfaces to non-Postfix software. Be sure to examine the manual
34# pages of the non-Postfix software to find out what options it wants.
35#
36# Many of the following services use the Postfix pipe(8) delivery
37# agent. See the pipe(8) man page for information about ${recipient}
38# and other message envelope options.
39# ====================================================================
40maildrop unix - n n - - pipe
41 flags=DRXhu user=vmail argv=/usr/bin/maildrop -d ${recipient}
42
43uucp unix - n n - - pipe
44 flags=Fqhu user=uucp argv=uux -r -n -z -a$sender - $nexthop!rmail ($recipient)
45
46ifmail unix - n n - - pipe
47 flags=F user=ftn argv=/usr/lib/ifmail/ifmail -r $nexthop ($recipient)
48
49bsmtp unix - n n - - pipe
50 flags=Fq. user=bsmtp argv=/usr/lib/bsmtp/bsmtp -t$nexthop -f$sender $recipient
51
52scalemail-backend unix - n n - 2 pipe
53 flags=R user=scalemail argv=/usr/lib/scalemail/bin/scalemail-store ${nexthop} ${user} ${extension}
54
55mailman unix - n n - - pipe
56 flags=FRX user=list argv=/usr/lib/mailman/bin/postfix-to-mailman.py ${nexthop} ${user}
57
58smtpd pass - - y - - smtpd
59 -o content_filter=spamassassin
60 -o smtpd_milters=unix:opendkim/opendkim.sock,unix:opendmarc/opendmarc.sock
61tlsproxy unix - - y - 0 tlsproxy
62
63dnsblog unix - - y - 0 dnsblog
64
65submissions inet n - y - - smtpd
66 -o smtpd_tls_wrappermode=yes
67 -o smtpd_tls_security_level=encrypt
68 -o smtpd_tls_auth_only=yes
69 -o smtpd_sasl_auth_enable=yes
70 -o smtpd_client_restrictions=permit_sasl_authenticated,permit_mynetworks,reject
71 -o smtpd_helo_restrictions=
72 -o smtpd_sender_restrictions=permit_mynetworks,reject_sender_login_mismatch
73 -o smtpd_recipient_restrictions=reject_non_fqdn_recipient,reject_unknown_recipient_domain,permit_sasl_authenticated,permit_mynetworks,reject
74 -o syslog_name=postfix/submissions
75 -o smtpd_tls_protocols=!SSLv2,!SSLv3,!TLSv1,!TLSv1.1,!TLSv1.2
76 -o smtpd_tls_mandatory_protocols=!SSLv2,!SSLv3,!TLSv1,!TLSv1.1,!TLSv1.2
77 -o smtpd_milters=unix:opendkim/opendkim.sock
78
79spamassassin unix - n n - - pipe user=debian-spamd
80 argv=/usr/bin/spamc --socket=/var/spool/postfix/spamd/spamd.sock -e /usr/sbin/sendmail -oi
81 -f ${sender} ${recipient}
82
83policyd-spf unix - n n - 0 spawn user=policyd-spf
84 argv=/usr/bin/policyd-spf
diff --git a/roles/postgrey/defaults/main.yml b/roles/postgrey/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/postgrey/defaults/main.yml
diff --git a/roles/postgrey/files/postgrey b/roles/postgrey/files/postgrey
new file mode 100644
index 0000000..d9a79d5
--- /dev/null
+++ b/roles/postgrey/files/postgrey
@@ -0,0 +1,2 @@
1POSTGREY_OPTS="--unix=/var/spool/postfix/private/postgrey --privacy"
2POSTGREY_TEXT="Greylisted - see https://www.greylisting.org"
diff --git a/roles/postgrey/handlers/main.yml b/roles/postgrey/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/postgrey/handlers/main.yml
diff --git a/roles/postgrey/tasks/main.yml b/roles/postgrey/tasks/main.yml
new file mode 100644
index 0000000..7c0caa7
--- /dev/null
+++ b/roles/postgrey/tasks/main.yml
@@ -0,0 +1,24 @@
1- name: install packages
2 package:
3 name:
4 - postgrey
5 state: latest
6
7- name: deploy configuration
8 copy:
9 src: postgrey
10 dest: /etc/default/postgrey
11 owner: root
12 group: root
13 mode: '0644'
14
15- name: enable postgrey
16 systemd:
17 enabled: yes
18 masked: no
19 name: postgrey
20
21- name: restart postgrey
22 service:
23 name: postgrey
24 state: restarted
diff --git a/roles/spamassassin/defaults/main.yml b/roles/spamassassin/defaults/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/spamassassin/defaults/main.yml
diff --git a/roles/spamassassin/files/defaults b/roles/spamassassin/files/defaults
new file mode 100644
index 0000000..a38795c
--- /dev/null
+++ b/roles/spamassassin/files/defaults
@@ -0,0 +1,9 @@
1OPTIONS="--listen /var/run/spamd.sock --max-children 5 --socketpath=/var/spool/postfix/spamd/spamd.sock --socketowner root --socketgroup root --socketmode 0666"
2
3PIDFILE=/var/run/spamd.pid
4
5# Cronjob
6# Set to anything but 0 to enable the cron job to automatically update
7# spamassassin's rules on a nightly basis
8CRON=1
9
diff --git a/roles/spamassassin/handlers/main.yml b/roles/spamassassin/handlers/main.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/roles/spamassassin/handlers/main.yml
diff --git a/roles/spamassassin/tasks/main.yml b/roles/spamassassin/tasks/main.yml
new file mode 100644
index 0000000..4c69be5
--- /dev/null
+++ b/roles/spamassassin/tasks/main.yml
@@ -0,0 +1,40 @@
1- name: install packages
2 package:
3 name:
4 - spamassassin
5 state: latest
6
7- name: make directory in postfix chroot
8 file:
9 path: /var/spool/postfix/spamd
10 owner: root
11 group: root
12 mode: '0755'
13 state: directory
14
15- name: deploy configuration
16 template:
17 src: local.cf.j2
18 dest: /etc/spamassassin/local.cf
19 owner: root
20 group: root
21 mode: '0644'
22
23- name: deploy defaults file
24 copy:
25 src: defaults
26 dest: /etc/default/spamd
27 owner: root
28 group: root
29 mode: '0644'
30
31- name: enable spamassassin
32 systemd:
33 enabled: yes
34 masked: no
35 name: spamd
36
37- name: restart spamassassin
38 service:
39 name: spamd
40 state: restarted
diff --git a/roles/spamassassin/templates/local.cf.j2 b/roles/spamassassin/templates/local.cf.j2
new file mode 100644
index 0000000..1fdc978
--- /dev/null
+++ b/roles/spamassassin/templates/local.cf.j2
@@ -0,0 +1,18 @@
1# SpamAssassin Configuration
2# Clearly indicate message is spam to user
3rewrite_header Subject *****SPAM*****
4rewrite_header From *****SPAM*****
5
6# Halves default spam score thus implementing a very strict spam policy
7# Comment or edit as needed for your deployment
8required_score {{ spam_score }}
9
10# Attach original messages as text/plain instead of message/rfc822 to spam reports
11# This is basically a safety net to prevent mail clients from automatically loading
12# attached spam messages. Note though that this makes the original message harder to recover
13# If this is not something you are worried about, comment the next line to use the default.
14report_safe 2
15
16# This specifies languages considered OK for incoming mail
17# If you expect to receive mail in non-western character sets, comment or edit as needed
18ok_locales {{ sa_locales }}