Compare commits

..

7 Commits

Author SHA1 Message Date
copilot-swe-agent[bot]
0ae8e02ac0 Address code review feedback
- Clarify host vs container paths in documentation
- Use loop for creating extra plugin files to reduce duplication
- Update example to show IMAP-specific plugin addition

Co-authored-by: DerLinkman <62480600+DerLinkman@users.noreply.github.com>
2025-12-15 11:23:45 +00:00
copilot-swe-agent[bot]
6633da54d4 Document both methods for extending mail_plugins
- Added documentation for using extra.conf with protocol blocks
- Clarified the recommended approach (extra files)
- Explained advantages and considerations of each method

Co-authored-by: DerLinkman <62480600+DerLinkman@users.noreply.github.com>
2025-12-15 11:22:10 +00:00
copilot-swe-agent[bot]
c7d020f9ff Add support for extending mail_plugins via extra files
- Modified docker-entrypoint.sh to create empty mail_plugins_extra files
- Updated dovecot.conf to read from additional plugin files
- Added documentation on how to extend mail_plugins

Co-authored-by: DerLinkman <62480600+DerLinkman@users.noreply.github.com>
2025-12-15 11:19:18 +00:00
copilot-swe-agent[bot]
c4135f7033 Initial plan 2025-12-15 11:13:35 +00:00
DerLinkman
1fe4cd03e9 ui: fix global filters ui tickbox reappearing (#6966) 2025-12-12 16:01:18 +01:00
milkmaker
12e02e67ff Translations update from Weblate (#6965)
* [Web] Updated lang.fr-fr.json

Co-authored-by: Keo <contact@kbl.netlib.re>

* [Web] Updated lang.pt-pt.json

Co-authored-by: Germano Pires Ferreira <germanopires@gmail.com>
Co-authored-by: milkmaker <milkmaker@mailcow.de>

* [Web] Updated lang.pl-pl.json

Co-authored-by: Monika Bark <rychert.monika@wp.pl>

---------

Co-authored-by: Keo <contact@kbl.netlib.re>
Co-authored-by: Germano Pires Ferreira <germanopires@gmail.com>
Co-authored-by: Monika Bark <rychert.monika@wp.pl>
2025-12-12 15:21:04 +01:00
DerLinkman
b6f57dfb78 rspamd: update to 3.14.2 2025-12-12 14:06:49 +01:00
10 changed files with 51 additions and 79 deletions

View File

@@ -121,7 +121,13 @@ echo -n 'quota acl zlib mail_crypt mail_crypt_acl mail_log notify fts fts_flatcu
echo -n 'quota imap_quota imap_acl acl zlib imap_zlib imap_sieve mail_crypt mail_crypt_acl notify mail_log fts fts_flatcurve listescape replication' > /etc/dovecot/mail_plugins_imap
echo -n 'quota sieve acl zlib mail_crypt mail_crypt_acl fts fts_flatcurve notify listescape replication' > /etc/dovecot/mail_plugins_lmtp
fi
chmod 644 /etc/dovecot/mail_plugins /etc/dovecot/mail_plugins_imap /etc/dovecot/mail_plugins_lmtp /templates/quarantine.tpl
# Create empty extra plugin files if they don't exist (can be populated via extra.conf or direct file)
for plugin_file in mail_plugins_extra mail_plugins_imap_extra mail_plugins_lmtp_extra; do
[[ ! -f /etc/dovecot/${plugin_file} ]] && touch /etc/dovecot/${plugin_file}
done
chmod 644 /etc/dovecot/mail_plugins /etc/dovecot/mail_plugins_imap /etc/dovecot/mail_plugins_lmtp /etc/dovecot/mail_plugins_extra /etc/dovecot/mail_plugins_imap_extra /etc/dovecot/mail_plugins_lmtp_extra /templates/quarantine.tpl
cat <<EOF > /etc/dovecot/sql/dovecot-dict-sql-userdb.conf
# Autogenerated by mailcow

View File

@@ -2,7 +2,7 @@ FROM debian:trixie-slim
LABEL maintainer="The Infrastructure Company GmbH <info@servercow.de>"
ARG DEBIAN_FRONTEND=noninteractive
ARG RSPAMD_VER=rspamd_3.14.1-1~46a758617
ARG RSPAMD_VER=rspamd_3.14.2-82~90302bc
ARG CODENAME=trixie
ENV LC_ALL=C

View File

@@ -1,6 +1,25 @@
# --------------------------------------------------------------------------
# Please create a file "extra.conf" for persistent overrides to dovecot.conf
# --------------------------------------------------------------------------
# To extend mail_plugins, you have two options:
#
# Option 1 (Recommended): Use the extra plugin files directly
# Create/edit data/conf/dovecot/mail_plugins_extra (for global plugins)
# Create/edit data/conf/dovecot/mail_plugins_imap_extra (for IMAP-specific plugins)
# Create/edit data/conf/dovecot/mail_plugins_lmtp_extra (for LMTP-specific plugins)
# Note: These paths are on the host. Inside the container they are /etc/dovecot/mail_plugins_*
# Example to add the virtual plugin for IMAP:
# echo -n ' virtual' > data/conf/dovecot/mail_plugins_imap_extra
# docker-compose restart dovecot-mailcow
#
# Option 2: Override protocol sections in extra.conf
# Create data/conf/dovecot/extra.conf with protocol-specific overrides:
# protocol imap {
# mail_plugins = $mail_plugins virtual
# }
# Note: This requires redefining the entire protocol block and may override
# other settings. Option 1 is simpler and less prone to conflicts.
# --------------------------------------------------------------------------
# LDAP example:
#passdb {
# args = /etc/dovecot/ldap/passdb.conf
@@ -21,7 +40,7 @@ disable_plaintext_auth = yes
login_log_format_elements = "user=<%u> method=%m rip=%r lip=%l mpid=%e %c %k"
mail_home = /var/vmail/%d/%n
mail_location = maildir:~/
mail_plugins = </etc/dovecot/mail_plugins
mail_plugins = </etc/dovecot/mail_plugins </etc/dovecot/mail_plugins_extra
mail_attachment_fs = crypt:set_prefix=mail_crypt_global:posix:
mail_attachment_dir = /var/attachments
mail_attachment_min_size = 128k
@@ -180,12 +199,12 @@ userdb {
skip = found
}
protocol imap {
mail_plugins = </etc/dovecot/mail_plugins_imap
mail_plugins = </etc/dovecot/mail_plugins_imap </etc/dovecot/mail_plugins_imap_extra
imap_metadata = yes
}
mail_attribute_dict = file:%h/dovecot-attributes
protocol lmtp {
mail_plugins = </etc/dovecot/mail_plugins_lmtp
mail_plugins = </etc/dovecot/mail_plugins_lmtp </etc/dovecot/mail_plugins_lmtp_extra
auth_socket_path = /var/run/dovecot/auth-master
}
protocol sieve {

View File

@@ -251,73 +251,6 @@ function password_check($password1, $password2) {
return true;
}
function generate_app_passwd($length = 32) {
// Get password complexity requirements
$password_complexity = password_complexity('get');
// Determine the actual length to use
$required_length = max($length, intval($password_complexity['length']));
// Define character sets
$lowercase = 'abcdefghijklmnopqrstuvwxyz';
$uppercase = 'ABCDEFGHIJKLMNOPQRSTUVWXYZ';
$digits = '0123456789';
$special = '!@#$%^&*()-_=+[]{}|;:,.<>?';
// Build the character pool and required chars based on policy
$pool = '';
$required_chars = '';
// Add digits to pool and ensure at least one if required
if ($password_complexity['numbers'] == 1) {
$pool .= $digits;
$required_chars .= $digits[random_int(0, strlen($digits) - 1)];
}
// Add alphabetic characters if required
if ($password_complexity['chars'] == 1) {
$pool .= $lowercase;
// Only add required char if not already added by lowerupper requirement
if ($password_complexity['lowerupper'] != 1) {
$required_chars .= $lowercase[random_int(0, strlen($lowercase) - 1)];
}
}
// Add both uppercase and lowercase letters if lowerupper required
if ($password_complexity['lowerupper'] == 1) {
$pool .= $lowercase . $uppercase;
$required_chars .= $uppercase[random_int(0, strlen($uppercase) - 1)];
$required_chars .= $lowercase[random_int(0, strlen($lowercase) - 1)];
}
// Add special characters if required
if ($password_complexity['special_chars'] == 1) {
$pool .= $special;
$required_chars .= $special[random_int(0, strlen($special) - 1)];
}
// If no requirements specified, use alphanumeric as default
if (empty($pool)) {
$pool = $lowercase . $uppercase . $digits;
$required_chars .= $digits[random_int(0, strlen($digits) - 1)];
}
// Ensure the password is at least as long as the required characters
$final_length = max($required_length, strlen($required_chars));
// Generate remaining characters from the pool
$remaining_length = $final_length - strlen($required_chars);
$password = $required_chars;
for ($i = 0; $i < $remaining_length; $i++) {
$password .= $pool[random_int(0, strlen($pool) - 1)];
}
// Shuffle the password to mix required chars with random ones
$password = str_shuffle($password);
return $password;
}
function last_login($action, $username, $sasl_limit_days = 7, $ui_offset = 1) {
global $pdo;
global $redis;

View File

@@ -54,7 +54,16 @@ jQuery(function($){
$.get("/inc/ajax/show_rspamd_global_filters.php");
$("#confirm_show_rspamd_global_filters").hide();
$("#rspamd_global_filters").removeClass("d-none");
localStorage.setItem('rspamd_global_filters_confirmed', 'true');
});
$(document).ready(function() {
if (localStorage.getItem('rspamd_global_filters_confirmed') === 'true') {
$("#confirm_show_rspamd_global_filters").hide();
$("#rspamd_global_filters").removeClass("d-none");
}
});
$("#super_delete").click(function() { return confirm(lang.queue_ays); });
$(".refresh_table").on('click', function(e) {

View File

@@ -1266,7 +1266,7 @@
"no_last_login": "Aucune dernière information de connexion à l'interface",
"no_record": "Pas d'enregistrement",
"password": "Mot de passe",
"password_now": "Mot de passe courant (confirmer les changements)",
"password_now": "Mot de passe actuel (confirmer les changements)",
"password_repeat": "Mot de passe (répéter)",
"pushover_evaluate_x_prio": "Acheminement du courrier hautement prioritaire [<code>X-Priority: 1</code>]",
"pushover_info": "Les paramètres de notification push sappliqueront à tout le courrier propre (non spam) livré à <b>%s</b> y compris les alias (partagés, non partagés, étiquetés).",

View File

@@ -240,7 +240,7 @@
"generate": "Generuj",
"guid": "GUID - unikalny identyfikator instancji",
"guid_and_license": "GUID & licencja",
"hash_remove_info": "Usunięcie hasha z limitem współczynnika (jeśli nadal istnieje) spowoduje całkowite zresetowanie jego licznika.<br>\n\n\n\n Każdy hash jest oznaczony indywidualnym kolorem.",
"hash_remove_info": "Usunięcie hasha z limitem współczynnika (jeśli nadal istnieje) spowoduje całkowite zresetowanie jego licznika.<br> Każdy hash jest oznaczony indywidualnym kolorem.",
"help_text": "Zastąp tekst pomocy poniżej maski logowania (dozwolone HTML)",
"html": "HTML",
"iam": "Dostawca tożsamości",
@@ -683,7 +683,11 @@
"mailbox_rename_agree": "Stworzyłem kopię zapasową.",
"mailbox_rename_warning": "WAŻNE! Utwórz kopię zapasową przed zmianą nazwy skrzynki pocztowej.",
"mailbox_rename_alias": "Tworzenie aliasów automatycznie",
"mailbox_rename_title": "Nowa nazwa lokalnej skrzynki pocztowej"
"mailbox_rename_title": "Nowa nazwa lokalnej skrzynki pocztowej",
"mbox_rl_info": "Ten limit szybkości dotyczy nazwy logowania SASL i odpowiada dowolnemu adresowi „from” używanemu przez zalogowanego użytkownika. Limit szybkości dla skrzynki pocztowej nadpisuje limit szybkości dla całej domeny.",
"nexthop": "Następny hop",
"private_comment": "Prywatny komentarz",
"public_comment": "Komentarz publiczny"
},
"footer": {
"cancel": "Anuluj",
@@ -1075,7 +1079,7 @@
"spamfilter_table_remove": "Usuń",
"spamfilter_table_rule": "Zasada",
"spamfilter_wl": "Biała lista",
"spamfilter_wl_desc": "Adresy e-mail znajdujące się na liście dozwolonych (allowlist) są zaprogramowane tak, aby <b> nigdy nie </b> były klasyfikowane jako spam.\nMożna używać symboli wieloznacznych (wildcardów).\nFiltr jest stosowany wyłącznie do bezpośrednich aliasów (aliasów wskazujących na jedną skrzynkę pocztową), z wyłączeniem aliasów typu „catch-all” oraz samej skrzynki pocztowej",
"spamfilter_wl_desc": "Adresy e-mail znajdujące się na liście dozwolonych (allowlist) są zaprogramowane tak, aby <b> nigdy nie </b> były klasyfikowane jako spam. Można używać symboli wieloznacznych (wildcardów).Filtr jest stosowany wyłącznie do bezpośrednich aliasów (aliasów wskazujących na jedną skrzynkę pocztową), z wyłączeniem aliasów typu „catch-all” oraz samej skrzynki pocztowej",
"spamfilter_yellow": "Żółty: ta wiadomość może być spamem, zostanie oznaczona jako spam i przeniesiona do folderu spam",
"sync_jobs": "Zadania synchronizacji",
"tag_handling": "Ustaw obsługę znaczników pocztowych",

View File

@@ -340,7 +340,8 @@
"tls_policy": "Política de TLS",
"quarantine_attachments": "Anexos de quarentena",
"filters": "Filtros",
"smtp_ip_access": "Mudar anfitriões permitidos para SMTP"
"smtp_ip_access": "Mudar anfitriões permitidos para SMTP",
"app_passwds": "Gerenciar senhas de aplicativos"
},
"warning": {
"no_active_admin": "Não é possível desactivar o último administrador activo"

View File

@@ -52,7 +52,7 @@ if (isset($_GET['app_password'])) {
else
$platform = $_SERVER['HTTP_USER_AGENT'];
$password = generate_app_passwd();
$password = bin2hex(openssl_random_pseudo_bytes(16));
$attr = array(
'app_name' => $platform,
'app_passwd' => $password,

View File

@@ -84,7 +84,7 @@ services:
- clamd
rspamd-mailcow:
image: ghcr.io/mailcow/rspamd:3.14.1
image: ghcr.io/mailcow/rspamd:3.14.2
stop_grace_period: 30s
depends_on:
- dovecot-mailcow