From 5367d2650e350f1fb48c8531f391bd9f75298f9c Mon Sep 17 00:00:00 2001 From: Alex Palaistras Date: Sat, 13 Nov 2021 13:12:24 +0000 Subject: [PATCH] dovecot: Activate FTS, ManagedSieve plugins This commit enables FTS via Xapian, and exposes the port required for ManagedSieve integration with Dovecot; additionally, bugs in the integration of LMTP with RSpamd have been fixed. In support of these changes, configuration files that were previously split into container-based and service-based are now consolidated, and we now ensure that only our own container-based configuration is used when running Dovecot. --- config/service/dovecot/Containerfile | 5 +-- .../container/config/conf.d/80-fts.conf | 9 ++++++ .../container/config/conf.d/85-lmtp.conf | 10 ++++++ .../container/config/conf.d/90-sieve.conf | 31 +++++++++++++++++++ .../config/dovecot-sql.conf.local.template | 3 +- .../container/config/dovecot.conf.template | 24 ++++++-------- .../config/scripts/learn-rspamd.script} | 2 +- .../config/sieve}/learn-ham.sieve | 0 .../config/sieve}/learn-spam.sieve | 0 config/service/dovecot/container/run-dovecot | 17 +++------- .../dovecot/service/config/90-sieve.conf | 25 --------------- config/service/dovecot/spec.bu | 2 ++ .../systemd/dovecot-fts-optimize.service | 12 +++++++ .../systemd/dovecot-fts-optimize.timer | 9 ++++++ .../service/dovecot/systemd/dovecot.service | 5 ++- 15 files changed, 96 insertions(+), 58 deletions(-) create mode 100644 config/service/dovecot/container/config/conf.d/80-fts.conf create mode 100644 config/service/dovecot/container/config/conf.d/85-lmtp.conf create mode 100644 config/service/dovecot/container/config/conf.d/90-sieve.conf rename config/service/dovecot/{service/config/learn-spamd.script => container/config/scripts/learn-rspamd.script} (88%) rename config/service/dovecot/{service/config => container/config/sieve}/learn-ham.sieve (100%) rename config/service/dovecot/{service/config => container/config/sieve}/learn-spam.sieve (100%) delete mode 100644 config/service/dovecot/service/config/90-sieve.conf create mode 100644 config/service/dovecot/systemd/dovecot-fts-optimize.service create mode 100644 config/service/dovecot/systemd/dovecot-fts-optimize.timer diff --git a/config/service/dovecot/Containerfile b/config/service/dovecot/Containerfile index 3c7e109..3b992e1 100644 --- a/config/service/dovecot/Containerfile +++ b/config/service/dovecot/Containerfile @@ -3,14 +3,15 @@ ARG VERSION=2.3.13 RUN apt-get update -y && apt-get install -y --no-install-recommends \ dovecot-imapd=1:${VERSION}* dovecot-lmtpd=1:${VERSION}* dovecot-mysql=1:${VERSION}* \ - dovecot-sieve=1:${VERSION}* dovecot-managesieved=1:${VERSION}* \ + dovecot-sieve=1:${VERSION}* dovecot-managesieved=1:${VERSION}* dovecot-fts-xapian \ gettext ca-certificates curl +RUN rm -Rf /etc/dovecot COPY container/config /etc/dovecot COPY container/run-dovecot /run-dovecot RUN addgroup --system --gid 5000 virtual RUN adduser --system --uid 5000 --ingroup virtual --home /var/mail/virtual virtual -EXPOSE 24 143 993 3659 +EXPOSE 24 143 993 3659 4190 ENTRYPOINT ["/run-dovecot"] diff --git a/config/service/dovecot/container/config/conf.d/80-fts.conf b/config/service/dovecot/container/config/conf.d/80-fts.conf new file mode 100644 index 0000000..5091042 --- /dev/null +++ b/config/service/dovecot/container/config/conf.d/80-fts.conf @@ -0,0 +1,9 @@ +# Use Xapian as the default full-text-search backend. +mail_plugins = $mail_plugins fts fts_xapian + +plugin { + fts = xapian + fts_xapian = partial=3 full=20 verbose=0 + fts_autoindex = yes + fts_enforced = yes +} diff --git a/config/service/dovecot/container/config/conf.d/85-lmtp.conf b/config/service/dovecot/container/config/conf.d/85-lmtp.conf new file mode 100644 index 0000000..aaab5f5 --- /dev/null +++ b/config/service/dovecot/container/config/conf.d/85-lmtp.conf @@ -0,0 +1,10 @@ +protocols = $protocols lmtp + +service lmtp { + user = virtual + group = virtual + + inet_listener lmtp { + port = 24 + } +} diff --git a/config/service/dovecot/container/config/conf.d/90-sieve.conf b/config/service/dovecot/container/config/conf.d/90-sieve.conf new file mode 100644 index 0000000..f1606d3 --- /dev/null +++ b/config/service/dovecot/container/config/conf.d/90-sieve.conf @@ -0,0 +1,31 @@ +protocols = $protocols sieve + +protocol imap { + mail_plugins = $mail_plugins imap_sieve +} + +protocol lmtp { + mail_plugins = $mail_plugins sieve +} + +plugin { + # Setup default plugins and extensions. + sieve_plugins = sieve_imapsieve sieve_extprograms + sieve_global_extensions = +vnd.dovecot.pipe +vnd.dovecot.environment + sieve_pipe_bin_dir = /etc/dovecot/scripts + + # Read Sieve scripts from pre-defined directories. + sieve_before = /etc/dovecot/sieve.before.d + sieve_after = /etc/dovecot/sieve.after.d + + # From elsewhere to Junk folder. + imapsieve_mailbox1_name = INBOX.Junk + imapsieve_mailbox1_causes = COPY + imapsieve_mailbox1_before = file:/etc/dovecot/sieve/learn-spam.sieve + + # From Junk folder to elsewhere. + imapsieve_mailbox2_name = * + imapsieve_mailbox2_from = INBOX.Junk + imapsieve_mailbox2_causes = COPY + imapsieve_mailbox2_before = file:/etc/dovecot/sieve/learn-ham.sieve +} diff --git a/config/service/dovecot/container/config/dovecot-sql.conf.local.template b/config/service/dovecot/container/config/dovecot-sql.conf.local.template index df9a6f9..8dbae25 100644 --- a/config/service/dovecot/container/config/dovecot-sql.conf.local.template +++ b/config/service/dovecot/container/config/dovecot-sql.conf.local.template @@ -3,5 +3,6 @@ driver = mysql connect = "host=${DOVECOT_DATABASE_HOST} dbname=${DOVECOT_DATABASE_NAME} user=${DOVECOT_DATABASE_USERNAME} password=${DOVECOT_DATABASE_PASSWORD}" default_pass_scheme = SHA512-CRYPT -password_query = SELECT username AS user, password, CONCAT(home, '/', maildir) AS userdb_home, uid AS userdb_uid, gid AS userdb_gid FROM users WHERE username = '%u' +iterate_query = SELECT username FROM users user_query = SELECT CONCAT(home, '/', maildir) AS home, uid, gid, CONCAT('maildir:', home, '/', maildir) AS mail FROM users WHERE username = '%u' +password_query = SELECT username AS user, password, CONCAT(home, '/', maildir) AS userdb_home, uid AS userdb_uid, gid AS userdb_gid FROM users WHERE username = '%u' diff --git a/config/service/dovecot/container/config/dovecot.conf.template b/config/service/dovecot/container/config/dovecot.conf.template index 19945ff..b380706 100644 --- a/config/service/dovecot/container/config/dovecot.conf.template +++ b/config/service/dovecot/container/config/dovecot.conf.template @@ -8,6 +8,11 @@ log_path = /dev/stderr auth_verbose = yes +plugin { + mail_log_events = delete undelete expunge copy mailbox_delete mailbox_rename + mail_log_fields = uid box msgid size +} + # Mail directory. mail_location = maildir:/var/mail/virtual/%u mail_privileged_group = virtual @@ -58,26 +63,17 @@ namespace inbox { # ---------------------- # Enabled protocols. -protocols = imap lmtp sieve +protocols = imap # Enable SSL and STARTTLS. ssl = yes +ssl_min_protocol = TLSv1.2 +ssl_cipher_list = ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384 +ssl_prefer_server_ciphers = no + ssl_cert = "`echo $file | awk -F '.template$' '{print $1}'`" + envsubst "$ENV_NAMES" < "$file" > "$(echo "$file" | awk -F '.template$' '{print $1}')" done -# Prepare other configuration. -mkdir -p /var/lib/dovecot/script /var/lib/dovecot/sieve -install -m 0755 /etc/dovecot/conf.d/*.script /var/lib/dovecot/script -install -m 0644 /etc/dovecot/conf.d/*.sieve /var/lib/dovecot/sieve - # Compile Sieve scripts. -find /etc/dovecot/sieve.* -name '*.sieve' | xargs -I@ sievec @ -find /var/lib/dovecot/sieve -name '*.sieve' | xargs -I@ sievec @ +find /etc/dovecot -name '*.sieve' -execdir sievec {} \; -# Set up environment variables for Rspamd. -mkdir -p /etc/dovecot/rspamd -env | awk -F '_' '$1 == "RSPAMD" {print $0}' > /etc/dovecot/rspamd/rspamd.env +# Set up environment variables for Rspamd integration. +env | awk -F_ '$1 == "RSPAMD" {print $0}' > /etc/dovecot/rspamd.env # Run Dovecot daemon. /usr/sbin/dovecot -F diff --git a/config/service/dovecot/service/config/90-sieve.conf b/config/service/dovecot/service/config/90-sieve.conf deleted file mode 100644 index 2fc5342..0000000 --- a/config/service/dovecot/service/config/90-sieve.conf +++ /dev/null @@ -1,25 +0,0 @@ -protocol imap { - mail_plugins = $mail_plugins imap_sieve -} - -plugin { - # Setup default plugins and extensions. - sieve_plugins = sieve_imapsieve sieve_extprograms - sieve_global_extensions = +vnd.dovecot.pipe +vnd.dovecot.environment - sieve_pipe_bin_dir = /var/lib/dovecot/script - - # Read Sieve scripts from pre-defined directories. - sieve_before = /etc/dovecot/sieve.before.d - sieve_after = /etc/dovecot/sieve.after.d - - # From elsewhere to Junk folder. - imapsieve_mailbox1_name = INBOX.Junk - imapsieve_mailbox1_causes = COPY - imapsieve_mailbox1_before = file:/var/lib/dovecot/sieve/learn-spam.sieve - - # From Junk folder to elsewhere. - imapsieve_mailbox2_name = * - imapsieve_mailbox2_from = INBOX.Junk - imapsieve_mailbox2_causes = COPY - imapsieve_mailbox2_before = file:/var/lib/dovecot/sieve/learn-ham.sieve -} diff --git a/config/service/dovecot/spec.bu b/config/service/dovecot/spec.bu index 02e4a9a..457a3cb 100644 --- a/config/service/dovecot/spec.bu +++ b/config/service/dovecot/spec.bu @@ -8,5 +8,7 @@ systemd: units: - name: dovecot-firstboot.target enabled: true + - name: dovecot-fts-optimize.timer + enabled: true - name: dovecot.service enabled: true diff --git a/config/service/dovecot/systemd/dovecot-fts-optimize.service b/config/service/dovecot/systemd/dovecot-fts-optimize.service new file mode 100644 index 0000000..ce09d6e --- /dev/null +++ b/config/service/dovecot/systemd/dovecot-fts-optimize.service @@ -0,0 +1,12 @@ +[Unit] +Description=Optimize Dovecot FTS Index +Wants=dovecot.service +After=dovecot.service + +[Service] +Type=oneshot +SyslogIdentifier=%N +ExecStart=/bin/podman exec dovecot doveadm fts optimize -A + +[Install] +WantedBy=multi-user.target diff --git a/config/service/dovecot/systemd/dovecot-fts-optimize.timer b/config/service/dovecot/systemd/dovecot-fts-optimize.timer new file mode 100644 index 0000000..8624b91 --- /dev/null +++ b/config/service/dovecot/systemd/dovecot-fts-optimize.timer @@ -0,0 +1,9 @@ +[Unit] +Description=Optimize Dovecot FTS Index + +[Timer] +OnCalendar=daily +Persistent=true + +[Install] +WantedBy=timers.target diff --git a/config/service/dovecot/systemd/dovecot.service b/config/service/dovecot/systemd/dovecot.service index f533d0a..58e0b08 100644 --- a/config/service/dovecot/systemd/dovecot.service +++ b/config/service/dovecot/systemd/dovecot.service @@ -12,10 +12,9 @@ Environment=PODMAN_SYSTEMD_UNIT=%n ExecStart=/bin/podman run --replace --name %N --net internal --sdnotify=conmon \ --env-file %E/coreos-home-server/%N/%N.env \ --env-file %E/coreos-home-server/rspamd/rspamd.env \ - --publish 143:143 --publish 993:993 \ + --publish 143:143 --publish 993:993 --publish 4190:4190 \ --volume %N:/var/mail:z \ - --volume letsencrypt:/etc/ssl/private:z \ - --volume %E/coreos-home-server/%N/service/config:/etc/%N/conf.d:z,ro \ + --volume letsencrypt:/etc/ssl/private:z,ro \ localhost/%N:latest ExecStop=/bin/podman stop --ignore --time 10 %N ExecStopPost=/bin/podman rm --ignore --force %N