feat(hosts/bagel-box): enable secrets-agent on this machine

And we use it for RabbitMQ mTLS authentication.

Signed-off-by: Raito Bezarius <masterancpp@gmail.com>
This commit is contained in:
raito 2025-01-01 02:58:19 +01:00
parent c2b1d29cb6
commit 21fca37bce
2 changed files with 48 additions and 16 deletions

View file

@ -52,6 +52,15 @@
# FIXME: plug into our prometheus stack. # FIXME: plug into our prometheus stack.
stats.enable = true; stats.enable = true;
}; };
secrets-agent = {
enable = true;
methods.token = {
enable = true;
tenancy = "floral";
identifier = "bagel-box";
};
};
}; };
bagel.sysadmin.enable = true; bagel.sysadmin.enable = true;

View file

@ -21,8 +21,7 @@ let
RuntimeDirectory = "ofborg"; RuntimeDirectory = "ofborg";
WorkingDirectory = "/var/lib/ofborg"; WorkingDirectory = "/var/lib/ofborg";
LoadCredential = LoadCredential =
optional (hasAttr "rabbitmq-password" config.age.secrets) "rabbitmq-password:${config.age.secrets.rabbitmq-password.path}" optional (hasAttr "gerrit-event-listener-ssh-key" config.age.secrets) "gerrit-ssh-key:${config.age.secrets.gerrit-event-listener-ssh-key.path}";
++ optional (hasAttr "gerrit-event-listener-ssh-key" config.age.secrets) "gerrit-ssh-key:${config.age.secrets.gerrit-event-listener-ssh-key.path}";
Environment = [ Environment = [
"XDG_STATE_HOME=/run/ofborg" "XDG_STATE_HOME=/run/ofborg"
]; ];
@ -45,6 +44,20 @@ in {
settings = mkOption { settings = mkOption {
type = generators.type; type = generators.type;
}; };
pki = {
cacertFile = mkOption {
type = types.path;
description = "CA certificate file for mTLS in OfBorg";
default = config.bagel.pki.cacertFile;
};
rootPath = mkOption {
type = types.str;
description = "Root mountpoint for PKI issuing in the Vault cluster";
example = "floral_systems/v1/infra/v1";
default = config.bagel.pki.rootPath;
};
};
}; };
config = mkMerge [ config = mkMerge [
@ -97,27 +110,37 @@ in {
}; };
} }
(mkIf cfg.rabbitmq.enable { (mkIf cfg.rabbitmq.enable {
age.secrets.rabbitmq-password.file = ../../secrets/floral/rabbitmq-password.age; systemd.services.rabbitmq.vault = {
services.nginx.enable = true; # TODO: Reloading implies rabbitmqctl eval -n [target-node@hostname] 'ssl:clear_pem_cache().'
template = ''
{{ with pkiCert "${cfg.pki.rootPath}/issue/rabbitmq-server" "common_name=${amqpHost}" }}
{{ scratch.MapSet "secrets" "server.pem" .Data.Cert }}
{{ scratch.MapSet "secrets" "server.key" .Data.Key }}
{{ end }}
{{ scratch.Get "secrets" | explodeMap | toJSON }}
'';
secrets = {
"server.pem" = {};
"server.key" = {};
};
};
services.rabbitmq = { services.rabbitmq = {
enable = true; enable = true;
configItems = { configItems = {
"listeners.tcp" = "none"; "listeners.tcp" = "none";
"listeners.ssl.default" = builtins.toString amqpPort; "listeners.ssl.default" = builtins.toString amqpPort;
"ssl_options.certfile" = "${config.security.acme.certs.${amqpHost}.directory}/cert.pem"; # TODO(upstream): this should accept path as well…
"ssl_options.keyfile" = "${config.security.acme.certs.${amqpHost}.directory}/key.pem"; "ssl_options.cacertfile" = "${cfg.pki.cacertFile}";
"ssl_options.certfile" = "/run/credentials/rabbitmq.service/server.pem";
"ssl_options.keyfile" = "/run/credentials/rabbitmq.service/server.key";
"ssl_options.verify" = "verify_peer";
# TODO(upstream): …
"ssl_options.fail_if_no_peer_cert" = "true";
# TLS authentication via X.509
"auth_mechanisms.1" = "EXTERNAL";
"ssl_cert_login_from" = "common_name";
}; };
}; };
security.acme.certs.${amqpHost} = {
webroot = "/var/lib/acme/.challenges";
group = "rabbitmq";
};
services.nginx.virtualHosts.${amqpHost}.locations."/.well-known/acme-challenge".root =
"/var/lib/acme/.challenges";
systemd.services.rabbitmq.requires = ["acme-finished-${amqpHost}.target"];
networking.firewall.allowedTCPPorts = [ amqpPort ];
}) })
(mkIf cfg.pastebin.enable { (mkIf cfg.pastebin.enable {
systemd.services.ofborg-pastebin = mkOfborgWorker "pastebin-worker" { }; systemd.services.ofborg-pastebin = mkOfborgWorker "pastebin-worker" { };