Only prepend {CRYPT} scheme if there is no scheme present

This commit is contained in:
Charlotte Van Petegem
2026-04-23 10:09:09 +02:00
parent 0b1ca54241
commit 6e9a4420b3
2 changed files with 42 additions and 1 deletions
+8 -1
View File
@@ -65,6 +65,13 @@ let
# Prevent world-readable password files, even temporarily. # Prevent world-readable password files, even temporarily.
umask 077 umask 077
prepend_scheme() {
case "$1" in
{*}*) printf '%s' "$1" ;;
*) printf '{CRYPT}%s' "$1" ;;
esac
}
for f in ${ for f in ${
builtins.toString (lib.mapAttrsToList (name: _: passwordFiles."${name}") cfg.accounts) builtins.toString (lib.mapAttrsToList (name: _: passwordFiles."${name}") cfg.accounts)
}; do }; do
@@ -81,7 +88,7 @@ let
if lib.elem name accountsWithPlaintextPasswordFiles then if lib.elem name accountsWithPlaintextPasswordFiles then
"${name}:${"$(sed -n '1{p;p;q}' ${passwordFiles."${name}"} | ${lib.getExe' config.services.dovecot2.package "doveadm"} pw)"}::::::" "${name}:${"$(sed -n '1{p;p;q}' ${passwordFiles."${name}"} | ${lib.getExe' config.services.dovecot2.package "doveadm"} pw)"}::::::"
else else
"${name}:{CRYPT}${"$(head -n 1 ${passwordFiles."${name}"})"}::::::" "${name}:${"$(prepend_scheme \"$(head -n 1 ${passwordFiles."${name}"})\")"}::::::"
) cfg.accounts ) cfg.accounts
)} )}
EOF EOF
+34
View File
@@ -41,7 +41,19 @@ let
mkpasswd -s <<<"$password" > $out mkpasswd -s <<<"$password" > $out
''; '';
hashPasswordWithScheme =
password:
pkgs.runCommand "password-${password}-hashed-with-scheme"
{
buildInputs = [ pkgs.dovecot ];
inherit password;
}
''
printf "$password\n$password\n" | doveadm -O pw -s SSHA256 > $out
'';
hashedPasswordFile = hashPassword "my-password"; hashedPasswordFile = hashPassword "my-password";
hashedPasswordFileWithScheme = hashPasswordWithScheme "my-password";
passwordFile = pkgs.writeText "password" "my-password"; passwordFile = pkgs.writeText "password" "my-password";
in in
{ {
@@ -100,6 +112,9 @@ in
"user3@example.com" = { "user3@example.com" = {
passwordFile = "/run/passwords/user3"; passwordFile = "/run/passwords/user3";
}; };
"user4@example.com" = {
hashedPasswordFile = hashedPasswordFileWithScheme;
};
"send-only@example.com" = { "send-only@example.com" = {
hashedPasswordFile = hashPassword "send-only"; hashedPasswordFile = hashPassword "send-only";
sendOnly = true; sendOnly = true;
@@ -258,6 +273,25 @@ in
) )
) )
with subtest("user with scheme-prefixed hashedPasswordFile can send and receive"):
machine.succeed(
" ".join(
[
"mail-check send-and-read",
"--smtp-port 587",
"--smtp-starttls",
"--smtp-host localhost",
"--imap-host localhost",
"--imap-username user4@example.com",
"--from-addr user4@example.com",
"--to-addr user4@example.com",
"--src-password-file ${passwordFile}",
"--dst-password-file ${passwordFile}",
"--ignore-dkim-spf",
]
)
)
with subtest("imap port 143 is closed and imaps is serving SSL"): with subtest("imap port 143 is closed and imaps is serving SSL"):
machine.wait_for_closed_port(143) machine.wait_for_closed_port(143)
machine.wait_for_open_port(993) machine.wait_for_open_port(993)