115 lines
3.8 KiB
Nix
115 lines
3.8 KiB
Nix
{ config, lib, pkgs, ... }:
|
|
|
|
with lib;
|
|
|
|
let
|
|
cfg = config.fudo.mail-server;
|
|
|
|
createDomainDkimCert = dom:
|
|
let
|
|
dkim_key = "${cfg.dkim.key-directory}/${dom}.${cfg.dkim.selector}.key";
|
|
dkim_txt = "${cfg.dkim.key-directory}/${dom}.${cfg.dkim.selector}.txt";
|
|
in
|
|
''
|
|
if [ ! -f "${dkim_key}" ] || [ ! -f "${dkim_txt}" ]
|
|
then
|
|
${cfg.dkim.package}/bin/opendkim-genkey -s "${cfg.dkim.selector}" \
|
|
-d "${dom}" \
|
|
--bits="${toString cfg.dkim.key-bits}" \
|
|
--directory="${cfg.dkim.key-directory}"
|
|
mv "${cfg.dkim.key-directory}/${cfg.dkim.selector}.private" "${dkim_key}"
|
|
mv "${cfg.dkim.key-directory}/${cfg.dkim.selector}.txt" "${dkim_txt}"
|
|
echo "Generated key for domain ${dom} selector ${cfg.dkim.selector}"
|
|
fi
|
|
'';
|
|
|
|
createAllCerts = lib.concatStringsSep "\n" (map createDomainDkimCert cfg.local-domains);
|
|
|
|
keyTable = pkgs.writeText "opendkim-KeyTable"
|
|
(lib.concatStringsSep "\n" (lib.flip map cfg.local-domains
|
|
(dom: "${dom} ${dom}:${cfg.dkim.selector}:${cfg.dkim.key-directory}/${dom}.${cfg.dkim.selector}.key")));
|
|
signingTable = pkgs.writeText "opendkim-SigningTable"
|
|
(lib.concatStringsSep "\n" (lib.flip map cfg.local-domains (dom: "${dom} ${dom}")));
|
|
|
|
dkim = config.services.opendkim;
|
|
args = [ "-f" "-l" ] ++ lib.optionals (dkim.configFile != null) [ "-x" dkim.configFile ];
|
|
in
|
|
{
|
|
|
|
options.fudo.mail-server.dkim = {
|
|
signing = mkOption {
|
|
type = types.bool;
|
|
default = true;
|
|
description = "Enable dkim signatures for mail.";
|
|
};
|
|
|
|
key-directory = mkOption {
|
|
type = types.str;
|
|
default = "/var/dkim";
|
|
description = "Path to use to store DKIM keys.";
|
|
};
|
|
|
|
selector = mkOption {
|
|
type = types.str;
|
|
default = "mail";
|
|
description = "Name to use for mail-signing keys.";
|
|
};
|
|
|
|
key-bits = mkOption {
|
|
type = types.int;
|
|
default = 2048;
|
|
description = ''
|
|
How many bits in generated DKIM keys. RFC6376 advises minimum 1024-bit keys.
|
|
|
|
If you have already deployed a key with a different number of bits than specified
|
|
here, then you should use a different selector (dkimSelector). In order to get
|
|
this package to generate a key with the new number of bits, you will either have to
|
|
change the selector or delete the old key file.
|
|
'';
|
|
};
|
|
|
|
package = mkOption {
|
|
type = types.package;
|
|
default = pkgs.opendkim;
|
|
description = "OpenDKIM package to use.";
|
|
};
|
|
};
|
|
|
|
config = mkIf (cfg.dkim.signing && cfg.enable) {
|
|
services.opendkim = {
|
|
enable = true;
|
|
selector = cfg.dkim.selector;
|
|
domains = "csl:${builtins.concatStringsSep "," cfg.local-domains}";
|
|
configFile = pkgs.writeText "opendkim.conf" (''
|
|
Canonicalization relaxed/simple
|
|
UMask 0002
|
|
Socket ${dkim.socket}
|
|
KeyTable file:${keyTable}
|
|
SigningTable file:${signingTable}
|
|
'' + (lib.optionalString cfg.debug ''
|
|
Syslog yes
|
|
SyslogSuccess yes
|
|
LogWhy yes
|
|
''));
|
|
};
|
|
|
|
users.users = {
|
|
"${config.services.postfix.user}" = {
|
|
extraGroups = [ "${config.services.opendkim.group}" ];
|
|
};
|
|
};
|
|
|
|
systemd.services.opendkim = {
|
|
preStart = lib.mkForce createAllCerts;
|
|
serviceConfig = {
|
|
ExecStart = lib.mkForce "${cfg.dkim.package}/bin/opendkim ${escapeShellArgs args}";
|
|
PermissionsStartOnly = lib.mkForce false;
|
|
};
|
|
};
|
|
|
|
systemd.tmpfiles.rules = [
|
|
"d '${cfg.dkim.key-directory}' - ${config.services.opendkim.user} ${config.services.opendkim.group} - -"
|
|
];
|
|
};
|
|
}
|