278 lines
8.4 KiB
Nix
278 lines
8.4 KiB
Nix
{
|
|
lib,
|
|
pkgs,
|
|
shb,
|
|
...
|
|
}:
|
|
let
|
|
domain = "example.com";
|
|
subdomain = "imap";
|
|
fqdn = "${subdomain}.${domain}";
|
|
|
|
trySendMail = pkgs.writeShellApplication {
|
|
name = "trySendMail";
|
|
runtimeInputs = [
|
|
pkgs.swaks
|
|
];
|
|
text = ''
|
|
USER="''${1:-}"
|
|
PASSWORD="''${2:-}"
|
|
|
|
if [ -z "$USER" ]; then
|
|
echo "No user given"
|
|
exit 1
|
|
fi
|
|
|
|
if [ -z "$PASSWORD" ]; then
|
|
swaks \
|
|
--server ${fqdn} \
|
|
--port 465 \
|
|
--tls-on-connect \
|
|
--from "$USER" \
|
|
--to "$USER"
|
|
else
|
|
swaks \
|
|
--server ${fqdn} \
|
|
--port 465 \
|
|
--tls-on-connect \
|
|
--auth LOGIN \
|
|
--auth-user "$USER" \
|
|
--auth-password "$PASSWORD" \
|
|
--from "$USER" \
|
|
--to "$USER"
|
|
fi
|
|
'';
|
|
};
|
|
|
|
tryRcvMail = pkgs.writeShellApplication {
|
|
name = "tryRcvMail";
|
|
runtimeInputs = [
|
|
pkgs.curl
|
|
];
|
|
text = ''
|
|
USER="''${1:-}"
|
|
PASSWORD="''${2:-}"
|
|
|
|
if [ -z "$USER" ]; then
|
|
echo "No user given"
|
|
exit 1
|
|
fi
|
|
if [ -z "$PASSWORD" ]; then
|
|
echo "No password given"
|
|
exit 1
|
|
fi
|
|
|
|
curl -s --url "imaps://imap.example.com/INBOX;UID=1" \
|
|
--user "$USER:$PASSWORD"
|
|
'';
|
|
};
|
|
in
|
|
{
|
|
basic = shb.test.runNixOSTest {
|
|
name = "mailserver_basic";
|
|
|
|
# Connect to the running VM started with driverInteractive:
|
|
# ssh-keygen -R 'vsock-mux//run/user/1000/tmpcf3hs4yp/server_host.socket'; ssh -o User=root vsock-mux//run/user/1000/tmpcf3hs4yp/server_host.socket
|
|
interactive.sshBackdoor.enable = true;
|
|
|
|
nodes.server =
|
|
{ config, ... }:
|
|
{
|
|
imports = [
|
|
../../modules/blocks/ssl.nix
|
|
../../modules/services/mailserver.nix
|
|
];
|
|
|
|
networking.hosts = {
|
|
"127.0.0.1" = [ fqdn ];
|
|
};
|
|
|
|
shb.certs.cas.selfsigned.myca = {
|
|
name = "My CA";
|
|
};
|
|
shb.certs.certs.selfsigned = {
|
|
${domain} = {
|
|
ca = config.shb.certs.cas.selfsigned.myca;
|
|
|
|
domain = "*.${domain}";
|
|
group = "nginx";
|
|
};
|
|
};
|
|
|
|
shb.mailserver = {
|
|
enable = true;
|
|
inherit subdomain domain;
|
|
stateVersion = 4;
|
|
ssl = config.shb.certs.certs.selfsigned.${domain};
|
|
|
|
# imapSync = {
|
|
# # syncTimer = "10s";
|
|
# # debug = false;
|
|
# # accounts.fastmail = {
|
|
# # host = "imap.fastmail.com";
|
|
# # port = 993;
|
|
# # username = email;
|
|
# # password.result = config.shb.sops.secret."mailserver/imap/fastmail/password".result;
|
|
# # mapSpecialJunk = "Spam";
|
|
# # };
|
|
# };
|
|
|
|
# smtpRelay = {
|
|
# host = "smtp.fastmail.com";
|
|
# port = 587;
|
|
# username = email;
|
|
# password.result = config.shb.sops.secret."mailserver/smtp/fastmail/password".result;
|
|
# };
|
|
|
|
};
|
|
|
|
mailserver.mailboxes = {
|
|
Junk = {
|
|
auto = "subscribe";
|
|
special_use = "\\Junk";
|
|
};
|
|
};
|
|
|
|
environment.systemPackages = [
|
|
pkgs.openssl
|
|
pkgs.swaks
|
|
trySendMail
|
|
tryRcvMail
|
|
];
|
|
|
|
specialisation = {
|
|
ldap.configuration =
|
|
{ config, ... }:
|
|
{
|
|
imports = [
|
|
../../modules/blocks/hardcodedsecret.nix
|
|
../../modules/blocks/lldap.nix
|
|
];
|
|
|
|
networking.hosts = {
|
|
"127.0.0.1" = [ "ldap.${domain}" ];
|
|
};
|
|
|
|
environment.systemPackages = [
|
|
pkgs.openldap
|
|
];
|
|
|
|
shb.hardcodedsecret.ldapUserPassword = {
|
|
request = config.shb.lldap.ldapUserPassword.request;
|
|
settings.content = "ldapUserPassword";
|
|
};
|
|
shb.hardcodedsecret.jwtSecret = {
|
|
request = config.shb.lldap.jwtSecret.request;
|
|
settings.content = "jwtSecrets";
|
|
};
|
|
shb.hardcodedsecret.alice = {
|
|
request = config.shb.lldap.ensureUsers.alice.password.request;
|
|
settings.content = "AlicePassword";
|
|
};
|
|
shb.hardcodedsecret.charlie = {
|
|
request = config.shb.lldap.ensureUsers.charlie.password.request;
|
|
settings.content = "CharliePassword";
|
|
};
|
|
|
|
shb.lldap = {
|
|
enable = true;
|
|
inherit domain;
|
|
subdomain = "ldap";
|
|
ldapPort = 3890;
|
|
webUIListenPort = 17170;
|
|
dcdomain = "dc=example,dc=com";
|
|
ldapUserPassword.result = config.shb.hardcodedsecret.ldapUserPassword.result;
|
|
jwtSecret.result = config.shb.hardcodedsecret.jwtSecret.result;
|
|
debug = true;
|
|
|
|
ensureUsers = {
|
|
alice = {
|
|
email = "alice@example.com";
|
|
groups = [ "user_group" ];
|
|
password.result = config.shb.hardcodedsecret.alice.result;
|
|
};
|
|
charlie = {
|
|
email = "charlie@example.com";
|
|
groups = [ "other_group" ];
|
|
password.result = config.shb.hardcodedsecret.charlie.result;
|
|
};
|
|
};
|
|
|
|
ensureGroups = {
|
|
user_group = { };
|
|
admin_group = { };
|
|
other_group = { };
|
|
};
|
|
};
|
|
|
|
shb.mailserver = {
|
|
ldap = {
|
|
enable = true;
|
|
host = "127.0.0.1";
|
|
port = config.shb.lldap.ldapPort;
|
|
dcdomain = config.shb.lldap.dcdomain;
|
|
adminName = "admin";
|
|
adminPassword.result = config.shb.hardcodedsecret.ldapUserPassword.result;
|
|
account = "fastmail";
|
|
userGroup = "user_group";
|
|
};
|
|
};
|
|
};
|
|
};
|
|
};
|
|
|
|
testScript =
|
|
{ nodes, ... }:
|
|
let
|
|
specialisations = "${nodes.server.system.build.toplevel}/specialisation";
|
|
switch = name: "${specialisations}/${name}/bin/switch-to-configuration test";
|
|
|
|
ldapSearch =
|
|
let
|
|
config = nodes.server.specialisation.ldap.configuration;
|
|
in
|
|
lib.concatStringsSep " " [
|
|
"ldapsearch"
|
|
"-H ldap://ldap.example.com:${toString config.shb.lldap.ldapPort}"
|
|
];
|
|
ldapSearchAdmin =
|
|
let
|
|
config = nodes.server.specialisation.ldap.configuration;
|
|
in
|
|
lib.concatStringsSep " " [
|
|
"ldapsearch"
|
|
"-H ldap://ldap.example.com:${toString config.shb.lldap.ldapPort}"
|
|
"-D uid=admin,ou=people,${config.shb.lldap.dcdomain}"
|
|
"-w ${config.shb.hardcodedsecret.ldapUserPassword.settings.content}"
|
|
];
|
|
in
|
|
''
|
|
server.wait_for_unit("multi-user.target")
|
|
server.wait_for_unit("dovecot")
|
|
|
|
with subtest("ldap"):
|
|
server.succeed("${switch "ldap"}")
|
|
|
|
server.wait_for_unit("lldap")
|
|
print(server.succeed("${ldapSearch} -LLL -D uid=alice,ou=people,dc=example,dc=com -w AlicePassword -b cn=user_group,ou=groups,dc=example,dc=com | grep uniquemember | grep alice"))
|
|
print(server.succeed("${ldapSearchAdmin} -LLL -b cn=user_group,ou=groups,dc=example,dc=com | grep uniquemember | grep alice"))
|
|
|
|
server.wait_for_unit("dovecot")
|
|
print(server.fail("doveadm auth test auser@example.com apassword"))
|
|
print(server.fail("doveadm auth test charlie@example.com CharliePassword"))
|
|
print(server.succeed("doveadm auth test alice@example.com AlicePassword"))
|
|
|
|
server.wait_for_unit("postfix")
|
|
print(server.fail("trySendMail alice@example.com"))
|
|
print(server.fail("trySendMail auser@example.com apassword"))
|
|
print(server.fail("trySendMail charlie@example.com CharliePassword"))
|
|
print(server.succeed("trySendMail alice@example.com AlicePassword"))
|
|
|
|
print(server.fail("tryRcvMail charlie@example.com CharliePassword"))
|
|
print(server.succeed("tryRcvMail alice@example.com AlicePassword"))
|
|
|
|
print(server.succeed("find /var/vmail"))
|
|
print(server.succeed("find /var/vmail/fastmail/alice@example.com"))
|
|
'';
|
|
};
|
|
}
|