Begin reworking some things around oauth apps
This commit is contained in:
parent
3d81e585db
commit
2064b4b006
14 changed files with 692 additions and 528 deletions
|
@ -24,10 +24,12 @@ in
|
|||
};
|
||||
|
||||
config = lib.mkIf cfg.enable {
|
||||
disko = lib.khscodes.disko-root-lvm-uefi {
|
||||
device = "/dev/sda";
|
||||
diskName = cfg.diskName;
|
||||
};
|
||||
disko = lib.mkDefault (
|
||||
lib.khscodes.disko-root-lvm-uefi {
|
||||
device = "/dev/sda";
|
||||
diskName = cfg.diskName;
|
||||
}
|
||||
);
|
||||
|
||||
boot.tmp.cleanOnBoot = lib.mkDefault true;
|
||||
boot.initrd.kernelModules = lib.mkIf (system == "aarch64-linux") [ "virtio_gpu" ];
|
||||
|
|
|
@ -124,7 +124,6 @@ in
|
|||
description = "The server type to create";
|
||||
default = null;
|
||||
};
|
||||
|
||||
extraFirewallRules = lib.mkOption {
|
||||
type = lib.types.listOf lib.types.attrs;
|
||||
description = "Extra firewall rules added to the instance";
|
||||
|
|
|
@ -0,0 +1,53 @@
|
|||
{ config, lib, ... }:
|
||||
let
|
||||
cfg = config.khscodes.infrastructure.kanidm-client-application;
|
||||
in
|
||||
{
|
||||
options.khscodes.infrastructure.kanidm-client-application = {
|
||||
enable = lib.mkEnableOption "Enables securing client credentials for oauth2 application in kanidm";
|
||||
appName = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
};
|
||||
secretFile = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
default = "/run/secret/kanidm/${cfg.appName}";
|
||||
};
|
||||
secretOwner = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
};
|
||||
secretGroup = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
default = cfg.secretOwner;
|
||||
};
|
||||
reloadOrRestartUnits = lib.mkOption {
|
||||
type = lib.types.listOf lib.types.str;
|
||||
default = [ ];
|
||||
};
|
||||
restartUnits = lib.mkOption {
|
||||
type = lib.types.listOf lib.types.str;
|
||||
default = [ ];
|
||||
};
|
||||
};
|
||||
|
||||
config = lib.mkIf cfg.enable {
|
||||
khscodes.services.vault-agent.templates = [
|
||||
{
|
||||
inherit (cfg) reloadOrRestartUnits restartUnits;
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/${cfg.appName}" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = cfg.secretFile;
|
||||
owner = cfg.secretOwner;
|
||||
group = cfg.secretGroup;
|
||||
perms = "0600";
|
||||
}
|
||||
];
|
||||
khscodes.infrastructure.vault-server-approle.policy = {
|
||||
"kanidm/data/apps/${cfg.appName}" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
};
|
||||
};
|
||||
}
|
|
@ -60,18 +60,11 @@ in
|
|||
};
|
||||
khscodes.infrastructure.vault-prometheus-sender.exporters.enabled = [ "postfix" ];
|
||||
services.fail2ban.jails = {
|
||||
postfix-sasl = {
|
||||
settings = {
|
||||
filter = "postfix[mode=auth]";
|
||||
port = "smtp,submission,imap,imaps,pop3,pop3s";
|
||||
findtime = 600;
|
||||
maxretry = 5;
|
||||
};
|
||||
};
|
||||
postfix = {
|
||||
settings = {
|
||||
enabled = true;
|
||||
mode = "aggressive";
|
||||
port = "smtp,submission,imap,imaps,pop3,pop3s";
|
||||
findtime = 600;
|
||||
bantime = "1d";
|
||||
maxretry = 3;
|
||||
|
@ -86,7 +79,7 @@ in
|
|||
maxretry = 3;
|
||||
};
|
||||
};
|
||||
roundcube-atuh = {
|
||||
roundcube-auth = {
|
||||
settings = {
|
||||
enabled = true;
|
||||
findtime = 600;
|
||||
|
|
|
@ -25,6 +25,7 @@ pkgs.writeShellApplication {
|
|||
echo "No preprovisioning needed"
|
||||
exit 0
|
||||
fi
|
||||
echo -n "tempkey" | ssh -o UserKnownHostsFile=/dev/null -o StrictHostKeyChecking=no "$username@$host" -- "cat >/tmp/tempkey"
|
||||
nixos-anywhere --flake "${inputs.self}#$hostname" --target-host "$username@$host"
|
||||
'';
|
||||
}
|
||||
|
|
|
@ -5,7 +5,6 @@
|
|||
...
|
||||
}:
|
||||
let
|
||||
oauthSecretIdFile = "/run/forgejo/oauth_secret_id";
|
||||
setApp = pkgs.writeShellApplication {
|
||||
name = "forgejo-set-oauth-app";
|
||||
runtimeInputs = [
|
||||
|
@ -14,7 +13,7 @@ let
|
|||
];
|
||||
text = ''
|
||||
config="${config.services.forgejo.stateDir}/custom/conf/app.ini"
|
||||
secret="$(cat ${oauthSecretIdFile})"
|
||||
secret="$(cat ${config.khscodes.infrastructure.kanidm-client-application.secretFile})"
|
||||
|
||||
options=(
|
||||
"--name" "Kanidm" \
|
||||
|
@ -43,26 +42,11 @@ let
|
|||
};
|
||||
in
|
||||
{
|
||||
khscodes.services.vault-agent.templates = [
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/forgejo" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = oauthSecretIdFile;
|
||||
perms = "0600";
|
||||
owner = "git";
|
||||
group = "git";
|
||||
restartUnits = [
|
||||
"forgejo-setup-oauth.service"
|
||||
];
|
||||
}
|
||||
];
|
||||
khscodes.infrastructure.vault-server-approle.policy = {
|
||||
"kanidm/data/apps/forgejo" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
khscodes.infrastructure.kanidm-client-application = {
|
||||
enable = true;
|
||||
appName = "forgejo";
|
||||
secretOwner = "git";
|
||||
restartUnits = [ "forgejo-setup-oauth.service" ];
|
||||
};
|
||||
systemd.services.forgejo-setup-oauth = {
|
||||
enable = true;
|
||||
|
@ -73,7 +57,7 @@ in
|
|||
"vault-agent-openbao.service"
|
||||
];
|
||||
unitConfig = {
|
||||
ConditionPathExists = [ oauthSecretIdFile ];
|
||||
ConditionPathExists = [ config.infrastructure.kanidm-client-application.secretFile ];
|
||||
};
|
||||
serviceConfig = {
|
||||
Type = "oneshot";
|
||||
|
|
|
@ -1,64 +0,0 @@
|
|||
{
|
||||
inputs,
|
||||
config,
|
||||
...
|
||||
}:
|
||||
{
|
||||
imports = [
|
||||
"${inputs.self}/nix/profiles/nixos/hetzner-server.nix"
|
||||
./testuser.nix
|
||||
];
|
||||
khscodes.infrastructure.provisioning.pre.modules = [
|
||||
{
|
||||
khscodes.vault = {
|
||||
enable = true;
|
||||
mount."mail.kaareskovgaard.net" = {
|
||||
path = "mail.kaareskovgaard.net";
|
||||
type = "kv";
|
||||
options = {
|
||||
version = "2";
|
||||
};
|
||||
description = "Secrets used for mail.kaareskovgaard.net";
|
||||
};
|
||||
};
|
||||
}
|
||||
];
|
||||
khscodes.infrastructure = {
|
||||
hetzner-instance = {
|
||||
enable = true;
|
||||
mapRdns = true;
|
||||
server_type = "cax11";
|
||||
};
|
||||
mailserver = {
|
||||
enable = true;
|
||||
domains = [
|
||||
"agerlin-skovgaard.dk"
|
||||
"agerlinskovgaard.dk"
|
||||
];
|
||||
dkim = {
|
||||
vault = {
|
||||
mount = "mail.kaareskovgaard.net";
|
||||
prefixPath = "dkim";
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
services.roundcube = {
|
||||
enable = true;
|
||||
hostName = "mail.kaareskovgaard.net";
|
||||
configureNginx = true;
|
||||
extraConfig = ''
|
||||
# starttls needed for authentication, so the fqdn required to match
|
||||
# the certificate
|
||||
$config['smtp_host'] = "tls://${config.mailserver.fqdn}";
|
||||
$config['smtp_user'] = "%u";
|
||||
$config['smtp_pass'] = "%p";
|
||||
'';
|
||||
};
|
||||
khscodes.services.nginx = {
|
||||
enable = true;
|
||||
virtualHosts."mail.kaareskovgaard.net" = { };
|
||||
};
|
||||
khscodes.networking.fqdn = "mail.kaareskovgaard.net";
|
||||
system.stateVersion = "25.05";
|
||||
}
|
71
nix/systems/aarch64-linux/mx.kaareskovgaard.net/default.nix
Normal file
71
nix/systems/aarch64-linux/mx.kaareskovgaard.net/default.nix
Normal file
|
@ -0,0 +1,71 @@
|
|||
{
|
||||
inputs,
|
||||
...
|
||||
}:
|
||||
{
|
||||
imports = [
|
||||
"${inputs.self}/nix/profiles/nixos/hetzner-server.nix"
|
||||
# ./testuser.nix
|
||||
];
|
||||
khscodes.infrastructure.provisioning.pre.modules = [
|
||||
(
|
||||
{ config, ... }:
|
||||
{
|
||||
khscodes.vault = {
|
||||
enable = true;
|
||||
mount."mx.kaareskovgaard.net" = {
|
||||
path = "mx.kaareskovgaard.net";
|
||||
type = "kv";
|
||||
options = {
|
||||
version = "2";
|
||||
};
|
||||
description = "Secrets used for mx.kaareskovgaard.net";
|
||||
};
|
||||
};
|
||||
resource.hcloud_volume.mail_disk = {
|
||||
name = "mx.kaareskovgaard.net-mail1";
|
||||
size = 20;
|
||||
server_id = config.khscodes.output.server.compute.id;
|
||||
};
|
||||
}
|
||||
)
|
||||
];
|
||||
khscodes.infrastructure = {
|
||||
hetzner-instance = {
|
||||
enable = true;
|
||||
mapRdns = true;
|
||||
server_type = "cax11";
|
||||
};
|
||||
mailserver = {
|
||||
enable = true;
|
||||
domains = [
|
||||
"agerlin-skovgaard.dk"
|
||||
"agerlinskovgaard.dk"
|
||||
];
|
||||
dkim = {
|
||||
vault = {
|
||||
mount = "mx.kaareskovgaard.net";
|
||||
prefixPath = "dkim";
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
# services.roundcube = {
|
||||
# enable = true;
|
||||
# hostName = "mail.kaareskovgaard.net";
|
||||
# configureNginx = true;
|
||||
# extraConfig = ''
|
||||
# # starttls needed for authentication, so the fqdn required to match
|
||||
# # the certificate
|
||||
# $config['smtp_host'] = "tls://${config.mailserver.fqdn}";
|
||||
# $config['smtp_user'] = "%u";
|
||||
# $config['smtp_pass'] = "%p";
|
||||
# '';
|
||||
# };
|
||||
khscodes.services.nginx = {
|
||||
enable = true;
|
||||
# virtualHosts."mail.kaareskovgaard.net" = { };
|
||||
};
|
||||
khscodes.networking.fqdn = "mx.kaareskovgaard.net";
|
||||
system.stateVersion = "25.05";
|
||||
}
|
168
nix/systems/aarch64-linux/mx.kaareskovgaard.net/disko.nix
Normal file
168
nix/systems/aarch64-linux/mx.kaareskovgaard.net/disko.nix
Normal file
|
@ -0,0 +1,168 @@
|
|||
{ pkgs, lib, ... }:
|
||||
let
|
||||
diskName = "nixos";
|
||||
espSize = "500M";
|
||||
bootPartName = "ESP";
|
||||
rootPartName = "primary";
|
||||
volumeGroupName = "mainpool";
|
||||
rootLvName = "root";
|
||||
zrootKey = "/run/secret/zroot.key";
|
||||
zfsLoadKeyScript = pkgs.writeShellApplication {
|
||||
name = "load-zfs-key";
|
||||
runtimeInputs = [ pkgs.zfs ];
|
||||
text = ''
|
||||
if ! zfs load-key -L ${zrootKey} zroot; then
|
||||
echo -n "tempkey" /tmp/tempkey
|
||||
zfs load-key -L /temp/tempkey zroot
|
||||
zfs change-key -o keylocation=${zrootKey} zroot
|
||||
fi
|
||||
'';
|
||||
};
|
||||
in
|
||||
{
|
||||
khscodes.services.vault-agent.templates = [
|
||||
{
|
||||
contents = ''
|
||||
{{- with pkiCert "mx.kaareskovgaard.net/data/zroot_encryption" -}}
|
||||
{{ .Data.data.key }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = zrootKey;
|
||||
owner = "root";
|
||||
group = "root";
|
||||
perms = "0600";
|
||||
exec = lib.getExe zfsLoadKeyScript;
|
||||
restartUnits = [
|
||||
"postfix.service"
|
||||
"dovecot.service"
|
||||
"rspamd.service"
|
||||
];
|
||||
}
|
||||
];
|
||||
khscodes.infrastructure.provisioning.pre.modules = [
|
||||
{
|
||||
resource.random_password.zroot_encryption_key = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
resource.vault_kv_secret_v2.test = {
|
||||
mount = "mx.kaareskovgaard.net";
|
||||
name = "zroot_encryption";
|
||||
data_json = ''
|
||||
{
|
||||
"key": ''${ jsonencode(resource.random_password.zroot_encryption_key.result) }
|
||||
}
|
||||
'';
|
||||
};
|
||||
}
|
||||
];
|
||||
khscodes.infrastructure.vault-server-approle.policy = {
|
||||
"mx.kaareskovgaard.net/data/zroot_encryption" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
};
|
||||
disko.devices.disk = {
|
||||
"${diskName}" = {
|
||||
device = "/dev/sda";
|
||||
type = "disk";
|
||||
content = {
|
||||
type = "gpt";
|
||||
partitions = {
|
||||
"${bootPartName}" = {
|
||||
size = espSize;
|
||||
type = "EF00";
|
||||
content = {
|
||||
type = "filesystem";
|
||||
format = "vfat";
|
||||
mountpoint = "/boot";
|
||||
mountOptions = [ "umask=0077" ];
|
||||
};
|
||||
};
|
||||
"${rootPartName}" = {
|
||||
size = "100%";
|
||||
content = {
|
||||
type = "lvm_pv";
|
||||
vg = volumeGroupName;
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
zroot1 = {
|
||||
device = "/dev/sdb";
|
||||
type = "disk";
|
||||
content = {
|
||||
type = "gpt";
|
||||
partitions = {
|
||||
zfs = {
|
||||
size = "100%";
|
||||
content = {
|
||||
type = "zfs";
|
||||
pool = "zroot";
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
devices.lvm_vg = {
|
||||
"${volumeGroupName}" = {
|
||||
type = "lvm_vg";
|
||||
lvs = {
|
||||
"${rootLvName}" = {
|
||||
size = "100%";
|
||||
content = {
|
||||
type = "filesystem";
|
||||
format = "ext4";
|
||||
mountpoint = "/";
|
||||
mountOptions = [ "defaults" ];
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
zpool = {
|
||||
zroot = {
|
||||
type = "zpool";
|
||||
rootFsOptions = {
|
||||
mountpoint = "none";
|
||||
compression = "zstd";
|
||||
acltype = "posixacl";
|
||||
xattr = "sa";
|
||||
"com.sun:auto-snapshot" = "true";
|
||||
};
|
||||
options.ashift = "12";
|
||||
datasets = {
|
||||
"mailserver" = {
|
||||
type = "zfs_fs";
|
||||
options = {
|
||||
encryption = "aes-256-gcm";
|
||||
keyformat = "passphrase";
|
||||
keylocation = "file:///tmp/tempkey";
|
||||
};
|
||||
};
|
||||
"mailserver/vmail" = {
|
||||
type = "zfs_fs";
|
||||
mountpoint = "/var/mailserver/vmail";
|
||||
};
|
||||
"mailserver/indices" = {
|
||||
type = "zfs_fs";
|
||||
mountpoint = "/var/mailserver/indices";
|
||||
};
|
||||
};
|
||||
mode = {
|
||||
topology = {
|
||||
type = "topology";
|
||||
vdev = [
|
||||
{
|
||||
members = [ "zroot1" ];
|
||||
}
|
||||
];
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
}
|
|
@ -1,22 +1,11 @@
|
|||
{
|
||||
config,
|
||||
pkgs,
|
||||
lib,
|
||||
...
|
||||
}:
|
||||
let
|
||||
domain = "login.kaareskovgaard.net";
|
||||
bootstrapping = config.khscodes."security.kaareskovgaard.net".bootstrap.enable;
|
||||
openbaoAppBasicSecretFile = "/run/kanidm/openbao_basic_secret";
|
||||
openbaoCliAppBasicSecretFile = "/run/kanidm/openbao_cli_basic_secret";
|
||||
monitoringAppBasicSecretFile = "/run/kanidm/monitoring_basic_secret";
|
||||
forgejoAppBasicSecretFile = "/run/kanidm/forgejo_basic_secret";
|
||||
secretFiles = [
|
||||
openbaoAppBasicSecretFile
|
||||
openbaoCliAppBasicSecretFile
|
||||
monitoringAppBasicSecretFile
|
||||
forgejoAppBasicSecretFile
|
||||
];
|
||||
openbaoDomain = config.khscodes.infrastructure.openbao.domain;
|
||||
openbaoAllowedRedirectUrls = [
|
||||
"https://${openbaoDomain}/ui/vault/auth/kanidm/oidc/callback"
|
||||
|
@ -51,424 +40,285 @@ let
|
|||
};
|
||||
in
|
||||
{
|
||||
services.kanidm = {
|
||||
enableServer = true;
|
||||
# Verify upgrade will be successful by running `kanidmd domain upgrade-check` before bumping package version.
|
||||
package = pkgs.kanidmWithSecretProvisioning_1_6;
|
||||
serverSettings = {
|
||||
inherit domain;
|
||||
tls_chain = "${config.security.acme.certs.${domain}.directory}/fullchain.pem";
|
||||
tls_key = "${config.security.acme.certs.${domain}.directory}/key.pem";
|
||||
origin = "https://${domain}";
|
||||
trust_x_forward_for = true;
|
||||
};
|
||||
provision = {
|
||||
enable = true;
|
||||
idmAdminPasswordFile = null;
|
||||
adminPasswordFile = null;
|
||||
acceptInvalidCerts = true;
|
||||
persons.khs = {
|
||||
present = true;
|
||||
mailAddresses = [
|
||||
"kaare@kaareskovgaard.net"
|
||||
"kaare@agerlin-skovgaard.dk"
|
||||
"kaare@agerlinskovgaard.dk"
|
||||
];
|
||||
legalName = "Kaare Skovgaard";
|
||||
displayName = "khs";
|
||||
};
|
||||
groups.openbao_admin = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_user = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_comitter = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_admin = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
# We cannot add oauth2 apps before the secrets for them are generated.
|
||||
systems.oauth2 = lib.mkIf (!bootstrapping) {
|
||||
openbao = {
|
||||
present = true;
|
||||
public = false;
|
||||
preferShortUsername = true;
|
||||
basicSecretFile = lib.mkIf (!bootstrapping) openbaoAppBasicSecretFile;
|
||||
originUrl = openbaoAllowedRedirectUrls;
|
||||
originLanding = "https://${openbaoDomain}";
|
||||
displayName = "OpenBAO";
|
||||
scopeMaps = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"openbao_admin" = [
|
||||
"openbao_writer"
|
||||
"openbao_cli_writer"
|
||||
];
|
||||
};
|
||||
};
|
||||
imports = [ ./kanidm_application.nix ];
|
||||
config = {
|
||||
khscodes.security.kanidm.applications = {
|
||||
openbao = {
|
||||
allowedRedirectUris = openbaoAllowedRedirectUrls;
|
||||
landingUri = "https://${openbaoDomain}";
|
||||
displayName = "OpenBAO";
|
||||
scopeMaps = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
openbao-cli = {
|
||||
present = true;
|
||||
public = false;
|
||||
preferShortUsername = true;
|
||||
basicSecretFile = lib.mkIf (!bootstrapping) openbaoCliAppBasicSecretFile;
|
||||
originUrl = [ "http://localhost:8250/oidc/callback" ];
|
||||
originLanding = "http://localhost:8250";
|
||||
displayName = "OpenBAO CLI";
|
||||
scopeMaps = {
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"openbao_admin" = [
|
||||
"openbao_writer"
|
||||
];
|
||||
};
|
||||
};
|
||||
};
|
||||
monitoring = {
|
||||
present = true;
|
||||
public = false;
|
||||
preferShortUsername = true;
|
||||
basicSecretFile = lib.mkIf (!bootstrapping) monitoringAppBasicSecretFile;
|
||||
originUrl = [ "https://monitoring.kaareskovgaard.net/login/generic_oauth" ];
|
||||
originLanding = "http://monitoring.kaareskovgaard.net";
|
||||
displayName = "Monitoring";
|
||||
scopeMaps = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
"openbao_writer"
|
||||
"openbao_cli_writer"
|
||||
];
|
||||
};
|
||||
};
|
||||
forgejo = {
|
||||
present = true;
|
||||
public = false;
|
||||
preferShortUsername = true;
|
||||
basicSecretFile = lib.mkIf (!bootstrapping) forgejoAppBasicSecretFile;
|
||||
originUrl = [ "https://kas.codes/user/oauth2/Kanidm/callback" ];
|
||||
originLanding = "http://kas.codes";
|
||||
displayName = "KAS: Codes";
|
||||
scopeMaps = {
|
||||
"forgejo_user" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
};
|
||||
openbao-cli = {
|
||||
terranixName = "openbao_cli";
|
||||
allowedRedirectUris = [ "http://localhost:8250/oidc/callback" ];
|
||||
landingUri = "http://localhost:8250";
|
||||
displayName = "OpenBAO CLI";
|
||||
scopeMaps = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"openbao_admin" = [
|
||||
"openbao_writer"
|
||||
];
|
||||
};
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"forgejo_comitter" = [
|
||||
"comitter"
|
||||
];
|
||||
"forgejo_admin" = [
|
||||
"admin"
|
||||
];
|
||||
};
|
||||
};
|
||||
};
|
||||
monitoring = {
|
||||
allowedRedirectUris = [ "https://monitoring.kaareskovgaard.net/login/generic_oauth" ];
|
||||
landingUri = "http://monitoring.kaareskovgaard.net";
|
||||
displayName = "Monitoring";
|
||||
scopeMaps = {
|
||||
"openbao_admin" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
};
|
||||
forgejo = {
|
||||
allowedRedirectUris = [ "https://kas.codes/user/oauth2/Kanidm/callback" ];
|
||||
landingUri = "http://kas.codes";
|
||||
displayName = "KAS: Codes";
|
||||
scopeMaps = {
|
||||
"forgejo_user" = [
|
||||
"profile"
|
||||
"email"
|
||||
"openid"
|
||||
];
|
||||
};
|
||||
claimMaps.groups = {
|
||||
joinType = "array";
|
||||
valuesByGroup = {
|
||||
"forgejo_comitter" = [
|
||||
"comitter"
|
||||
];
|
||||
"forgejo_admin" = [
|
||||
"admin"
|
||||
];
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
# Don't add dependencies from bootstrapping when not bootstrapping.
|
||||
systemd.services.kanidm = lib.mkIf (!bootstrapping) {
|
||||
unitConfig = {
|
||||
ConditionPathExists = secretFiles;
|
||||
services.kanidm = {
|
||||
enableServer = true;
|
||||
# Verify upgrade will be successful by running `kanidmd domain upgrade-check` before bumping package version.
|
||||
package = pkgs.kanidmWithSecretProvisioning_1_6;
|
||||
serverSettings = {
|
||||
inherit domain;
|
||||
tls_chain = "${config.security.acme.certs.${domain}.directory}/fullchain.pem";
|
||||
tls_key = "${config.security.acme.certs.${domain}.directory}/key.pem";
|
||||
origin = "https://${domain}";
|
||||
trust_x_forward_for = true;
|
||||
};
|
||||
provision = {
|
||||
enable = true;
|
||||
idmAdminPasswordFile = null;
|
||||
adminPasswordFile = null;
|
||||
acceptInvalidCerts = true;
|
||||
persons.khs = {
|
||||
present = true;
|
||||
mailAddresses = [
|
||||
"kaare@kaareskovgaard.net"
|
||||
"kaare@agerlin-skovgaard.dk"
|
||||
"kaare@agerlinskovgaard.dk"
|
||||
];
|
||||
legalName = "Kaare Skovgaard";
|
||||
displayName = "khs";
|
||||
};
|
||||
groups.openbao_admin = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_user = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_comitter = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
groups.forgejo_admin = {
|
||||
present = true;
|
||||
members = [ "khs" ];
|
||||
};
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
# Allow the server to read the secrets for its own apps
|
||||
khscodes.infrastructure.vault-server-approle.policy."kanidm/data/apps/*" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
|
||||
khscodes.infrastructure.provisioning.post.modules = [
|
||||
# Creates mount for kanidm apps and generates random passwords for the apps
|
||||
(
|
||||
{ config, ... }:
|
||||
{
|
||||
terraform.required_providers.random = {
|
||||
source = "hashicorp/random";
|
||||
version = "3.7.2";
|
||||
};
|
||||
provider.random = { };
|
||||
# NOTE: This gets stored in the state file
|
||||
resource.random_password.openbao_secret = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
khscodes.vault = {
|
||||
enable = true;
|
||||
mount.kanidm = {
|
||||
path = "kanidm";
|
||||
type = "kv";
|
||||
options = {
|
||||
version = "2";
|
||||
};
|
||||
description = "Secrets used for kanidm";
|
||||
};
|
||||
};
|
||||
resource.vault_kv_secret_v2.openbao_secret = {
|
||||
mount = config.khscodes.vault.output.mount.kanidm.path;
|
||||
name = "apps/openbao";
|
||||
data_json = ''
|
||||
{ "basic_secret": "''${ resource.random_password.openbao_secret.result }" }
|
||||
'';
|
||||
};
|
||||
resource.random_password.openbao_cli_secret = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
resource.vault_kv_secret_v2.openbao_cli_secret = {
|
||||
mount = config.khscodes.vault.output.mount.kanidm.path;
|
||||
name = "apps/openbao_cli";
|
||||
data_json = ''
|
||||
{ "basic_secret": "''${ resource.random_password.openbao_cli_secret.result }" }
|
||||
'';
|
||||
};
|
||||
resource.random_password.monitoring = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
resource.vault_kv_secret_v2.monitoring_secret = {
|
||||
mount = config.khscodes.vault.output.mount.kanidm.path;
|
||||
name = "apps/monitoring";
|
||||
data_json = ''
|
||||
{ "basic_secret": "''${ resource.random_password.monitoring.result }" }
|
||||
'';
|
||||
};
|
||||
resource.random_password.forgejo = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
resource.vault_kv_secret_v2.forgejo_secret = {
|
||||
mount = config.khscodes.vault.output.mount.kanidm.path;
|
||||
name = "apps/forgejo";
|
||||
data_json = ''
|
||||
{ "basic_secret": "''${ resource.random_password.forgejo.result }" }
|
||||
'';
|
||||
};
|
||||
}
|
||||
)
|
||||
# Sets up OIDC authentication within OpenBAO.
|
||||
# OpenBAO queries the openid url for its configuration when adding it, so it is not possible,
|
||||
# to add this before
|
||||
(
|
||||
if bootstrapping then
|
||||
{ }
|
||||
else
|
||||
khscodes.infrastructure.provisioning.post.modules = [
|
||||
(
|
||||
{ ... }:
|
||||
{
|
||||
resource.vault_jwt_auth_backend.kanidm_cli = {
|
||||
description = "Kanidm cli auth backend";
|
||||
path = "oidc";
|
||||
type = "oidc";
|
||||
oidc_discovery_url = "https://${domain}/oauth2/openid/openbao-cli";
|
||||
oidc_client_id = "openbao-cli";
|
||||
oidc_client_secret = "\${ resource.random_password.openbao_cli_secret.result }";
|
||||
default_role = "kanidm_cli_writer";
|
||||
jwt_supported_algs = [
|
||||
"ES256"
|
||||
];
|
||||
tune = [
|
||||
{
|
||||
listing_visibility = "hidden";
|
||||
default_lease_ttl = "2h";
|
||||
max_lease_ttl = "2h";
|
||||
token_type = "default-service";
|
||||
passthrough_request_headers = [ ];
|
||||
allowed_response_headers = [ ];
|
||||
audit_non_hmac_request_keys = [ ];
|
||||
audit_non_hmac_response_keys = [ ];
|
||||
}
|
||||
];
|
||||
};
|
||||
resource.vault_jwt_auth_backend.kanidm = {
|
||||
description = "Kanidm auth backend";
|
||||
path = "kanidm";
|
||||
type = "oidc";
|
||||
oidc_discovery_url = "https://${domain}/oauth2/openid/openbao";
|
||||
oidc_client_id = "openbao";
|
||||
oidc_client_secret = "\${ resource.random_password.openbao_secret.result }";
|
||||
default_role = "kanidm_writer";
|
||||
jwt_supported_algs = [
|
||||
"ES256"
|
||||
];
|
||||
tune = [
|
||||
{
|
||||
listing_visibility = "unauth";
|
||||
default_lease_ttl = "2h";
|
||||
max_lease_ttl = "2h";
|
||||
token_type = "default-service";
|
||||
passthrough_request_headers = [ ];
|
||||
allowed_response_headers = [ ];
|
||||
audit_non_hmac_request_keys = [ ];
|
||||
audit_non_hmac_response_keys = [ ];
|
||||
}
|
||||
];
|
||||
};
|
||||
|
||||
resource.vault_jwt_auth_backend_role.kanidm_cli_writer = {
|
||||
backend = "\${ resource.vault_jwt_auth_backend.kanidm_cli.path }";
|
||||
role_name = "kanidm_cli_writer";
|
||||
bound_audiences = [ "openbao-cli" ];
|
||||
allowed_redirect_uris = [ "http://localhost:8250/oidc/callback" ];
|
||||
user_claim = "sub";
|
||||
token_policies = [ "writer" ];
|
||||
groups_claim = "groups";
|
||||
oidc_scopes = [
|
||||
"openid"
|
||||
"profile"
|
||||
"email"
|
||||
];
|
||||
};
|
||||
|
||||
resource.vault_jwt_auth_backend_role.kanidm_writer = {
|
||||
backend = "\${ resource.vault_jwt_auth_backend.kanidm.path }";
|
||||
role_name = "kanidm_writer";
|
||||
bound_audiences = [ "openbao" ];
|
||||
allowed_redirect_uris = openbaoAllowedRedirectUrls;
|
||||
user_claim = "sub";
|
||||
token_policies = [ "writer" ];
|
||||
groups_claim = "groups";
|
||||
oidc_scopes = [
|
||||
"openid"
|
||||
"profile"
|
||||
"email"
|
||||
];
|
||||
};
|
||||
|
||||
resource.vault_identity_group.kanidm_writer = {
|
||||
name = "kanidm_writer";
|
||||
policies = [ "writer" ];
|
||||
type = "external";
|
||||
};
|
||||
|
||||
resource.vault_identity_group.kanidm_cli_writer = {
|
||||
name = "kanidm_cli_writer";
|
||||
policies = [ "writer" ];
|
||||
type = "external";
|
||||
};
|
||||
|
||||
resource.vault_identity_group_alias.oidc_writer = {
|
||||
name = "openbao_cli_writer";
|
||||
mount_accessor = "\${ vault_jwt_auth_backend.kanidm_cli.accessor }";
|
||||
canonical_id = "\${ vault_identity_group.kanidm_cli_writer.id }";
|
||||
};
|
||||
|
||||
resource.vault_identity_group_alias.kanidm_writer = {
|
||||
name = "openbao_writer";
|
||||
mount_accessor = "\${ vault_jwt_auth_backend.kanidm.accessor }";
|
||||
canonical_id = "\${ vault_identity_group.kanidm_writer.id }";
|
||||
};
|
||||
|
||||
resource.vault_policy.writer = {
|
||||
name = "writer";
|
||||
|
||||
policy = ''
|
||||
path "*" {
|
||||
capabilities = ["create", "update", "patch", "read", "delete", "list"]
|
||||
}
|
||||
'';
|
||||
khscodes.vault = {
|
||||
enable = true;
|
||||
mount.kanidm = {
|
||||
path = "kanidm";
|
||||
type = "kv";
|
||||
options = {
|
||||
version = "2";
|
||||
};
|
||||
description = "Secrets used for kanidm";
|
||||
};
|
||||
};
|
||||
}
|
||||
)
|
||||
];
|
||||
)
|
||||
# Sets up OIDC authentication within OpenBAO.
|
||||
# OpenBAO queries the openid url for its configuration when adding it, so it is not possible,
|
||||
# to add this before
|
||||
(
|
||||
if bootstrapping then
|
||||
{ }
|
||||
else
|
||||
{
|
||||
resource.vault_jwt_auth_backend.kanidm_cli = {
|
||||
description = "Kanidm cli auth backend";
|
||||
path = "oidc";
|
||||
type = "oidc";
|
||||
oidc_discovery_url = "https://${domain}/oauth2/openid/openbao-cli";
|
||||
oidc_client_id = "openbao-cli";
|
||||
oidc_client_secret = "\${ resource.random_password.openbao_cli_secret.result }";
|
||||
default_role = "kanidm_cli_writer";
|
||||
jwt_supported_algs = [
|
||||
"ES256"
|
||||
];
|
||||
tune = [
|
||||
{
|
||||
listing_visibility = "hidden";
|
||||
default_lease_ttl = "2h";
|
||||
max_lease_ttl = "2h";
|
||||
token_type = "default-service";
|
||||
passthrough_request_headers = [ ];
|
||||
allowed_response_headers = [ ];
|
||||
audit_non_hmac_request_keys = [ ];
|
||||
audit_non_hmac_response_keys = [ ];
|
||||
}
|
||||
];
|
||||
};
|
||||
resource.vault_jwt_auth_backend.kanidm = {
|
||||
description = "Kanidm auth backend";
|
||||
path = "kanidm";
|
||||
type = "oidc";
|
||||
oidc_discovery_url = "https://${domain}/oauth2/openid/openbao";
|
||||
oidc_client_id = "openbao";
|
||||
oidc_client_secret = "\${ resource.random_password.openbao_secret.result }";
|
||||
default_role = "kanidm_writer";
|
||||
jwt_supported_algs = [
|
||||
"ES256"
|
||||
];
|
||||
tune = [
|
||||
{
|
||||
listing_visibility = "unauth";
|
||||
default_lease_ttl = "2h";
|
||||
max_lease_ttl = "2h";
|
||||
token_type = "default-service";
|
||||
passthrough_request_headers = [ ];
|
||||
allowed_response_headers = [ ];
|
||||
audit_non_hmac_request_keys = [ ];
|
||||
audit_non_hmac_response_keys = [ ];
|
||||
}
|
||||
];
|
||||
};
|
||||
|
||||
khscodes.services.vault-agent.templates = [
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/openbao" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = openbaoAppBasicSecretFile;
|
||||
perms = "0600";
|
||||
owner = "kanidm";
|
||||
group = "kanidm";
|
||||
reloadOrRestartUnits = [ "kanidm.service" ];
|
||||
}
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/openbao_cli" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = openbaoCliAppBasicSecretFile;
|
||||
perms = "0600";
|
||||
owner = "kanidm";
|
||||
group = "kanidm";
|
||||
reloadOrRestartUnits = [ "kanidm.service" ];
|
||||
}
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/monitoring" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = monitoringAppBasicSecretFile;
|
||||
perms = "0600";
|
||||
owner = "kanidm";
|
||||
group = "kanidm";
|
||||
reloadOrRestartUnits = [ "kanidm.service" ];
|
||||
}
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/forgejo" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = forgejoAppBasicSecretFile;
|
||||
perms = "0600";
|
||||
owner = "kanidm";
|
||||
group = "kanidm";
|
||||
reloadOrRestartUnits = [ "kanidm.service" ];
|
||||
}
|
||||
];
|
||||
resource.vault_jwt_auth_backend_role.kanidm_cli_writer = {
|
||||
backend = "\${ resource.vault_jwt_auth_backend.kanidm_cli.path }";
|
||||
role_name = "kanidm_cli_writer";
|
||||
bound_audiences = [ "openbao-cli" ];
|
||||
allowed_redirect_uris = [ "http://localhost:8250/oidc/callback" ];
|
||||
user_claim = "sub";
|
||||
token_policies = [ "writer" ];
|
||||
groups_claim = "groups";
|
||||
oidc_scopes = [
|
||||
"openid"
|
||||
"profile"
|
||||
"email"
|
||||
];
|
||||
};
|
||||
|
||||
security.acme.certs.${domain}.reloadServices = [ "kanidm.service" ];
|
||||
# Allow kanidm to read the certificate file
|
||||
users.groups.nginx.members = [ "kanidm" ];
|
||||
resource.vault_jwt_auth_backend_role.kanidm_writer = {
|
||||
backend = "\${ resource.vault_jwt_auth_backend.kanidm.path }";
|
||||
role_name = "kanidm_writer";
|
||||
bound_audiences = [ "openbao" ];
|
||||
allowed_redirect_uris = openbaoAllowedRedirectUrls;
|
||||
user_claim = "sub";
|
||||
token_policies = [ "writer" ];
|
||||
groups_claim = "groups";
|
||||
oidc_scopes = [
|
||||
"openid"
|
||||
"profile"
|
||||
"email"
|
||||
];
|
||||
};
|
||||
|
||||
khscodes.services.nginx.virtualHosts.${domain} = {
|
||||
locations."/" = {
|
||||
proxyPass = "https://${config.services.kanidm.serverSettings.bindaddress}/";
|
||||
recommendedProxySettings = true;
|
||||
resource.vault_identity_group.kanidm_writer = {
|
||||
name = "kanidm_writer";
|
||||
policies = [ "writer" ];
|
||||
type = "external";
|
||||
};
|
||||
|
||||
resource.vault_identity_group.kanidm_cli_writer = {
|
||||
name = "kanidm_cli_writer";
|
||||
policies = [ "writer" ];
|
||||
type = "external";
|
||||
};
|
||||
|
||||
resource.vault_identity_group_alias.oidc_writer = {
|
||||
name = "openbao_cli_writer";
|
||||
mount_accessor = "\${ vault_jwt_auth_backend.kanidm_cli.accessor }";
|
||||
canonical_id = "\${ vault_identity_group.kanidm_cli_writer.id }";
|
||||
};
|
||||
|
||||
resource.vault_identity_group_alias.kanidm_writer = {
|
||||
name = "openbao_writer";
|
||||
mount_accessor = "\${ vault_jwt_auth_backend.kanidm.accessor }";
|
||||
canonical_id = "\${ vault_identity_group.kanidm_writer.id }";
|
||||
};
|
||||
|
||||
resource.vault_policy.writer = {
|
||||
name = "writer";
|
||||
|
||||
policy = ''
|
||||
path "*" {
|
||||
capabilities = ["create", "update", "patch", "read", "delete", "list"]
|
||||
}
|
||||
'';
|
||||
};
|
||||
}
|
||||
)
|
||||
];
|
||||
security.acme.certs.${domain}.reloadServices = [ "kanidm.service" ];
|
||||
# Allow kanidm to read the certificate file
|
||||
users.groups.nginx.members = [ "kanidm" ];
|
||||
|
||||
khscodes.services.nginx.virtualHosts.${domain} = {
|
||||
locations."/" = {
|
||||
proxyPass = "https://${config.services.kanidm.serverSettings.bindaddress}/";
|
||||
recommendedProxySettings = true;
|
||||
};
|
||||
};
|
||||
};
|
||||
|
||||
environment.systemPackages = [
|
||||
kanidm-reset-password
|
||||
];
|
||||
environment.systemPackages = [
|
||||
kanidm-reset-password
|
||||
];
|
||||
};
|
||||
}
|
||||
|
|
|
@ -0,0 +1,115 @@
|
|||
{
|
||||
config,
|
||||
lib,
|
||||
...
|
||||
}:
|
||||
let
|
||||
cfg = config.khscodes.security.kanidm;
|
||||
secretFileForApplication = key: "/run/kanidm/${key}_secret";
|
||||
secretFiles = lib.attrsets.mapAttrsToList (
|
||||
key: value: secretFileForApplication key
|
||||
) cfg.applications;
|
||||
vaultAgentTemplates = lib.attrsets.mapAttrsToList (key: value: {
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/${key}" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = secretFileForApplication key;
|
||||
perms = "0600";
|
||||
owner = "kanidm";
|
||||
group = "kanidm";
|
||||
reloadOrRestartUnits = [ "kanidm.service" ];
|
||||
}) cfg.applications;
|
||||
terranixModules = lib.attrsets.mapAttrsToList (
|
||||
key: value:
|
||||
{ config, ... }:
|
||||
let
|
||||
sanitizedKey = lib.khscodes.sanitize-terraform-name (
|
||||
if value.terranixName == null then key else value.terranixName
|
||||
);
|
||||
in
|
||||
{
|
||||
resource.random_password."${sanitizedKey}_secret" = {
|
||||
length = 48;
|
||||
numeric = true;
|
||||
lower = true;
|
||||
upper = true;
|
||||
special = false;
|
||||
};
|
||||
resource.vault_kv_secret_v2."${sanitizedKey}_secret" = {
|
||||
mount = config.khscodes.vault.output.mount.kanidm.path;
|
||||
name = "apps/${key}";
|
||||
data_json = ''
|
||||
{ "basic_secret": "''${ resource.random_password.${sanitizedKey}_secret.result }" }
|
||||
'';
|
||||
};
|
||||
}
|
||||
) cfg.applications;
|
||||
systemsOauth2 = lib.attrsets.mapAttrs (key: value: {
|
||||
inherit (value) scopeMaps claimMaps;
|
||||
present = true;
|
||||
public = false;
|
||||
preferShortUsername = true;
|
||||
basicSecretFile = lib.mkIf (!bootstrapping) (secretFileForApplication key);
|
||||
originUrl = value.allowedRedirectUris;
|
||||
originLanding = value.landingUri;
|
||||
displayName = value.displayName;
|
||||
}) cfg.applications;
|
||||
kanidmApplication = lib.khscodes.mkSubmodule {
|
||||
description = "Kanidm application";
|
||||
options = {
|
||||
terranixName = lib.mkOption {
|
||||
type = lib.types.nullOr lib.types.str;
|
||||
default = null;
|
||||
};
|
||||
displayName = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
};
|
||||
scopeMaps = lib.mkOption {
|
||||
type = lib.types.attrsOf (lib.types.listOf lib.types.str);
|
||||
};
|
||||
allowedRedirectUris = lib.mkOption {
|
||||
type = lib.types.listOf lib.types.str;
|
||||
};
|
||||
landingUri = lib.mkOption {
|
||||
type = lib.types.str;
|
||||
};
|
||||
claimMaps = lib.mkOption {
|
||||
type = lib.types.anything;
|
||||
default = { };
|
||||
};
|
||||
};
|
||||
};
|
||||
bootstrapping = config.khscodes."security.kaareskovgaard.net".bootstrap.enable;
|
||||
in
|
||||
{
|
||||
options.khscodes.security.kanidm.applications = lib.mkOption {
|
||||
type = lib.types.attrsOf kanidmApplication;
|
||||
};
|
||||
|
||||
config = {
|
||||
# Allow the server to read the secrets for its own apps
|
||||
khscodes.infrastructure.vault-server-approle.policy."kanidm/data/apps/*" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
# Don't add dependencies from bootstrapping when not bootstrapping.
|
||||
systemd.services.kanidm = lib.mkIf (!bootstrapping) {
|
||||
unitConfig = {
|
||||
ConditionPathExists = secretFiles;
|
||||
};
|
||||
};
|
||||
khscodes.services.vault-agent.templates = vaultAgentTemplates;
|
||||
khscodes.infrastructure.provisioning.post.modules = terranixModules ++ [
|
||||
{
|
||||
terraform.required_providers.random = {
|
||||
source = "hashicorp/random";
|
||||
version = "3.7.2";
|
||||
};
|
||||
provider.random = { };
|
||||
}
|
||||
];
|
||||
# We cannot add oauth2 apps before the secrets for them are generated.
|
||||
services.kanidm.provision.systems.oauth2 = lib.mkIf (!bootstrapping) systemsOauth2;
|
||||
};
|
||||
}
|
|
@ -42,6 +42,9 @@ in
|
|||
};
|
||||
|
||||
khscodes.services.nginx.virtualHosts.${domain} = {
|
||||
rateLimit = {
|
||||
burst = 100;
|
||||
};
|
||||
locations."/" = {
|
||||
proxyPass = "https://${config.services.openbao.settings.listener.tcp.address}/";
|
||||
recommendedProxySettings = true;
|
||||
|
|
|
@ -52,7 +52,7 @@ in
|
|||
token_url = "https://login.kaareskovgaard.net/oauth2/token";
|
||||
api_url = "https://login.kaareskovgaard.net/oauth2/openid/monitoring/userinfo";
|
||||
client_id = "monitoring";
|
||||
client_secret = "$__file{/var/lib/vault-agent/grafana/kanidm_client_secret}";
|
||||
client_secret = "$__file{${config.khscodes.infrastructure.kanidm-client-application.secretFile}}";
|
||||
scopes = "openid profile email";
|
||||
use_pkce = true;
|
||||
skip_org_role_sync = false;
|
||||
|
@ -252,23 +252,12 @@ in
|
|||
perms = "0644";
|
||||
reloadOrRestartUnits = [ "nginx.service" ];
|
||||
}
|
||||
{
|
||||
contents = ''
|
||||
{{- with secret "kanidm/data/apps/monitoring" -}}
|
||||
{{ .Data.data.basic_secret }}
|
||||
{{- end -}}
|
||||
'';
|
||||
destination = "/var/lib/vault-agent/grafana/kanidm_client_secret";
|
||||
owner = "grafana";
|
||||
group = "grafana";
|
||||
perms = "0600";
|
||||
reloadOrRestartUnits = [ "grafana.service" ];
|
||||
}
|
||||
];
|
||||
infrastructure.vault-server-approle.policy = {
|
||||
"kanidm/data/apps/monitoring" = {
|
||||
capabilities = [ "read" ];
|
||||
};
|
||||
infrastructure.kanidm-client-application = {
|
||||
enable = true;
|
||||
appName = "monitoring";
|
||||
secretOwner = "grafana";
|
||||
reloadOrRestartUnits = [ "grafana.service" ];
|
||||
};
|
||||
};
|
||||
khscodes.networking.fqdn = "monitoring.kaareskovgaard.net";
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue