191 lines
6.0 KiB
Nix
191 lines
6.0 KiB
Nix
{
|
|
lib,
|
|
host,
|
|
dsl,
|
|
commonModule,
|
|
}:
|
|
pkgs:
|
|
let
|
|
inherit (host.specialArgs.hostInfo) paths;
|
|
serverDataDir = paths.data;
|
|
serverSecretsDir = paths.secrets;
|
|
|
|
testContainers = dsl.filterDeployments (c: c.includedInTests) host.containers;
|
|
|
|
it = dsl.mkIntegrationTest { inherit host testContainers pkgs; };
|
|
|
|
nginxAcmeDomains = [
|
|
"devenv.floweytf.com"
|
|
"maven.floweytf.com"
|
|
"git.floweytf.com"
|
|
"utils.floweytf.com"
|
|
"mail.floweytf.com"
|
|
];
|
|
|
|
nginxAcmeDir = domain: "${serverDataDir}/core/nginx/acme/${domain}";
|
|
|
|
fakeCert =
|
|
domain:
|
|
pkgs.runCommand "fake-cert-${domain}"
|
|
{
|
|
nativeBuildInputs = [ pkgs.openssl ];
|
|
}
|
|
''
|
|
mkdir -p "$out"
|
|
openssl req -x509 -newkey rsa:2048 -nodes -days 1 \
|
|
-subj "/CN=${domain}" \
|
|
-keyout "$out/key.pem" -out "$out/fullchain.pem" 2>/dev/null
|
|
'';
|
|
|
|
mkdirAcmeDirs = lib.concatMapStrings (
|
|
domain: ''mkdir -p "${nginxAcmeDir domain}"'' + "\n"
|
|
) nginxAcmeDomains;
|
|
|
|
installFakeCerts = lib.concatMapStrings (
|
|
domain:
|
|
let
|
|
dir = nginxAcmeDir domain;
|
|
cert = fakeCert domain;
|
|
in
|
|
''
|
|
if [[ ! -f "${dir}/fullchain.pem" ]]; then
|
|
install -m 644 ${cert}/fullchain.pem "${dir}/fullchain.pem"
|
|
install -m 600 ${cert}/key.pem "${dir}/key.pem"
|
|
fi
|
|
''
|
|
) nginxAcmeDomains;
|
|
|
|
# used in ssh-admin
|
|
testSshKey =
|
|
pkgs.runCommand "test-ssh-key"
|
|
{
|
|
nativeBuildInputs = [ pkgs.openssh ];
|
|
}
|
|
''
|
|
mkdir -p "$out"
|
|
ssh-keygen -q -t ed25519 -N "" -f "$out/key" -C test
|
|
'';
|
|
sshpiperTestUser = "admin";
|
|
|
|
hostExporterPort = 9100;
|
|
hostCadvisorPort = 9200;
|
|
hostSshdPort = 5952;
|
|
in
|
|
{
|
|
name = "integration-${host.hostName}";
|
|
|
|
nodes = {
|
|
internet = it.internetNode;
|
|
|
|
server =
|
|
{ pkgs, lib, ... }:
|
|
{
|
|
imports = [
|
|
commonModule
|
|
host.specialArgs.inputs.microvm.nixosModules.host
|
|
(dsl.mkHostFromContainers {
|
|
containers = testContainers;
|
|
inherit (host) ctx;
|
|
})
|
|
it.serverModule
|
|
];
|
|
|
|
containers.nginx.config = {
|
|
systemd.services = lib.genAttrs (map (d: "acme-order-renew-${d}") nginxAcmeDomains) (_: {
|
|
enable = lib.mkForce false;
|
|
});
|
|
};
|
|
|
|
system.activationScripts.test-secrets =
|
|
# bash
|
|
''
|
|
mkdir -p /nix/var/nix/db /nix/var/nix/daemon-socket
|
|
|
|
mkdir -p /var/log/journal
|
|
|
|
${mkdirAcmeDirs}
|
|
mkdir -p "${serverSecretsDir}" \
|
|
"${serverDataDir}/core/sshpiper" \
|
|
"${serverDataDir}/core/mail" \
|
|
"${serverDataDir}/overseer/loki/data" \
|
|
"${serverDataDir}/overseer/prometheus/data" \
|
|
"${serverDataDir}/overseer/grafana" \
|
|
"${serverDataDir}/web/git" \
|
|
"${serverDataDir}/web/git-ci-runner/nix-rw-store" \
|
|
"${serverDataDir}/web/git-ci-runner/docker" \
|
|
"${serverDataDir}/web/git-ci-runner/runner-state" \
|
|
"${serverSecretsDir}/ci-runner" \
|
|
"${serverDataDir}/web/reposilite" \
|
|
"${serverDataDir}/web/devenv/config" \
|
|
"${serverDataDir}/web/devenv/workspace" \
|
|
"${serverDataDir}/ssh/generic" \
|
|
"${serverDataDir}/ssh/nyaa" \
|
|
"${serverDataDir}/mc/botm" \
|
|
"${serverDataDir}/mc/rogule-dev" \
|
|
"${serverDataDir}/mc/rogule-build" \
|
|
"${serverDataDir}/mc/starwalker" \
|
|
"${serverDataDir}/mc/tl"
|
|
|
|
chown -R 1000:1000 \
|
|
"${serverDataDir}/web/git" \
|
|
"${serverDataDir}/web/reposilite" \
|
|
"${serverDataDir}/web/devenv/config" \
|
|
"${serverDataDir}/web/devenv/workspace" \
|
|
"${serverDataDir}/core/mail" \
|
|
"${serverDataDir}/ssh/generic" \
|
|
"${serverDataDir}/mc/botm" \
|
|
"${serverDataDir}/mc/rogule-dev" \
|
|
"${serverDataDir}/mc/rogule-build" \
|
|
"${serverDataDir}/mc/starwalker" \
|
|
"${serverDataDir}/mc/tl"
|
|
|
|
for keytype in ed25519 rsa ecdsa; do
|
|
keyfile="${serverSecretsDir}/ssh_host_''${keytype}_key"
|
|
if [[ ! -f "$keyfile" ]]; then
|
|
${lib.getExe' pkgs.openssh "ssh-keygen"} -q -t "$keytype" -f "$keyfile" -N ""
|
|
fi
|
|
done
|
|
|
|
# stalwart rejects weak/dictionary passwords
|
|
for f in mail-admin-password mail-account-password; do
|
|
target="${serverSecretsDir}/$f"
|
|
if [[ ! -f "$target" ]]; then
|
|
head -c 32 /dev/urandom | base64 | tr -d '\n' > "$target"
|
|
chmod 600 "$target"
|
|
fi
|
|
done
|
|
|
|
if [[ ! -f "${serverSecretsDir}/ci-runner/token" ]]; then
|
|
echo "TOKEN=test-registration-token" > "${serverSecretsDir}/ci-runner/token"
|
|
chmod 600 "${serverSecretsDir}/ci-runner/token"
|
|
fi
|
|
|
|
if [[ ! -f "${serverSecretsDir}/code-server-env" ]]; then
|
|
echo "test-secret" > "${serverSecretsDir}/code-server-env"
|
|
chmod 600 "${serverSecretsDir}/code-server-env"
|
|
fi
|
|
|
|
${installFakeCerts}
|
|
mkdir -p "${serverDataDir}/core/sshpiper/user_${sshpiperTestUser}"
|
|
install -m 644 ${testSshKey}/key.pub \
|
|
"${serverDataDir}/core/sshpiper/user_${sshpiperTestUser}/authorized_keys"
|
|
'';
|
|
};
|
|
};
|
|
|
|
testScript =
|
|
it.testScriptPreamble
|
|
+ ''
|
|
# store paths are world-readable; ssh refuses a key with those permissions
|
|
SSH_KEY = "/root/test-ssh-key"
|
|
SSH_OPTS = f"-o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null -o ConnectTimeout=5 -i {SSH_KEY}"
|
|
TEST_SSH_KEY_STORE = "${testSshKey}/key"
|
|
|
|
SSHPIPER_TEST_USER = "${sshpiperTestUser}"
|
|
HOST_EXPORTER_PORT = ${toString hostExporterPort}
|
|
HOST_CADVISOR_PORT = ${toString hostCadvisorPort}
|
|
HOST_SSHD_PORT = ${toString hostSshdPort}
|
|
''
|
|
+ builtins.readFile ./integration.py;
|
|
}
|