feat: convert all microvms to use nginx

This commit is contained in:
oddlama 2023-06-22 00:51:45 +02:00
parent edb1d8791d
commit f0d2475f74
No known key found for this signature in database
GPG key ID: 14EFE510775FE39A
9 changed files with 114 additions and 125 deletions

View file

@ -376,9 +376,8 @@
file, file,
}: '' }: ''
echo " -> Aggregating "${lib.escapeShellArg host}":"${lib.escapeShellArg name}"" >&2 echo " -> Aggregating "${lib.escapeShellArg host}":"${lib.escapeShellArg name}"" >&2
echo -n ${lib.escapeShellArg host}"+"${lib.escapeShellArg name}" "
${decrypt} ${lib.escapeShellArg file} \ ${decrypt} ${lib.escapeShellArg file} \
| ${pkgs.caddy}/bin/caddy hash-password --algorithm bcrypt \ | ${pkgs.apacheHttpd}/bin/htpasswd -niBC 12 ${lib.escapeShellArg host}"+"${lib.escapeShellArg name}" " \
|| die "Failure while aggregating caddy basic auth hashes" || die "Failure while aggregating caddy basic auth hashes"
''); '');

View file

@ -6,7 +6,7 @@
... ...
}: let }: let
sentinelCfg = nodes.sentinel.config; sentinelCfg = nodes.sentinel.config;
adguardDomain = "adguardhome.${sentinelCfg.repo.secrets.local.personalDomain}"; adguardhomeDomain = "adguardhome.${sentinelCfg.repo.secrets.local.personalDomain}";
in { in {
imports = [ imports = [
../../../../modules/proxy-via-sentinel.nix ../../../../modules/proxy-via-sentinel.nix
@ -22,27 +22,25 @@ in {
}; };
nodes.sentinel = { nodes.sentinel = {
proxiedDomains.adguard = adguardDomain; proxiedDomains.adguard = adguardhomeDomain;
globalConfig = '' extra.oauth2_proxy.nginx.virtualHosts."${adguardhomeDomain}".allowedGroups = ["adguardhome"];
security { services.nginx = {
authorization policy mypolicy { upstreams.adguardhome = {
set auth url https://auth.myfiosgateway.com:8443/ servers."${config.services.adguardhome.settings.bind_host}:${toString config.services.adguardhome.settings.bind_port}" = {};
allow roles authp/user extraConfig = ''
crypto key verify {env.JWT_SHARED_KEY} zone adguardhome 64k;
} keepalive 2;
} '';
''; };
virtualHosts.${adguardhomeDomain} = {
services.caddy.virtualHosts.${adguardDomain} = { forceSSL = true;
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert adguardDomain; useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert adguardhomeDomain;
extraConfig = '' locations."/" = {
import common proxyPass = "https://adguardhome";
reverse_proxy { proxyWebsockets = true;
to http://${config.services.adguardhome.settings.bind_host}:${toString config.services.adguardhome.settings.bind_port} };
header_up X-Real-IP {remote_host} };
}
'';
}; };
}; };

View file

@ -1 +1 @@
ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAICDDvvF3+KwfoZrPAUAt2HS7y5FM9S5Mr1iRkBUqoXno ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIFgqg9aDuyMY+Hmk+++FnoIJRnztJhhj2LfGv4vDhSXG

View file

@ -42,15 +42,22 @@ in {
proxiedDomains.grafana = grafanaDomain; proxiedDomains.grafana = grafanaDomain;
services.caddy.virtualHosts.${grafanaDomain} = { services.nginx = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert grafanaDomain; upstreams.grafana = {
extraConfig = '' servers."${config.services.grafana.settings.server.http_addr}:${toString config.services.grafana.settings.server.http_port}" = {};
import common extraConfig = ''
reverse_proxy { zone grafana 64k;
to http://${config.services.grafana.settings.server.http_addr}:${toString config.services.grafana.settings.server.http_port} keepalive 2;
header_up X-Real-IP {remote_host} '';
} };
''; virtualHosts.${grafanaDomain} = {
forceSSL = true;
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert grafanaDomain;
locations."/" = {
proxyPass = "https://grafana";
proxyWebsockets = true;
};
};
}; };
}; };

View file

@ -38,18 +38,24 @@ in {
nodes.sentinel = { nodes.sentinel = {
proxiedDomains.kanidm = kanidmDomain; proxiedDomains.kanidm = kanidmDomain;
services.caddy.virtualHosts.${kanidmDomain} = { services.nginx = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert kanidmDomain; upstreams.kanidm = {
extraConfig = '' servers."${config.services.kanidm.serverSettings.bindaddress}" = {};
import common extraConfig = ''
reverse_proxy { zone kanidm 64k;
to https://${config.services.kanidm.serverSettings.bindaddress} keepalive 2;
header_up X-Real-IP {remote_host} '';
transport http { };
tls_insecure_skip_verify virtualHosts.${kanidmDomain} = {
} forceSSL = true;
} useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert kanidmDomain;
''; locations."/".proxyPass = "https://kanidm";
# Allow using self-signed certs to satisfy kanidm's requirement
# for TLS connections. (Although this is over wireguard anyway)
extraConfig = ''
proxy_ssl_verify off;
'';
};
}; };
}; };

View file

@ -30,22 +30,41 @@ in {
# that define passwords (using distributed-config). # that define passwords (using distributed-config).
generator.script = config.age.generators.basic-auth.script; generator.script = config.age.generators.basic-auth.script;
mode = "440"; mode = "440";
group = "caddy"; group = "nginx";
}; };
services.caddy.virtualHosts.${lokiDomain} = { services.nginx = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert lokiDomain; upstreams.loki = {
extraConfig = '' servers."${config.services.loki.configuration.server.http_listen_address}:${toString config.services.loki.configuration.server.http_listen_port}" = {};
import common extraConfig = ''
skip_log zone loki 64k;
basicauth { keepalive 2;
import ${sentinelCfg.age.secrets.loki-basic-auth-hashes.path} '';
} };
reverse_proxy { virtualHosts.${lokiDomain} = {
to http://${config.services.loki.configuration.server.http_listen_address}:${toString config.services.loki.configuration.server.http_listen_port} forceSSL = true;
header_up X-Real-IP {remote_host} useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert lokiDomain;
} locations."/" = {
''; proxyPass = "https://loki";
proxyWebsockets = true;
extraConfig = ''
auth_basic "Authentication required";
auth_basic_user_file ${sentinelCfg.age.secrets.loki-basic-auth-hashes.path};
proxy_read_timeout 1800s;
proxy_connect_timeout 1600s;
access_log off;
'';
};
locations."= /ready" = {
proxyPass = "https://loki";
extraConfig = ''
auth_basic off;
access_log off;
'';
};
};
}; };
}; };

View file

@ -33,26 +33,35 @@ in {
nodes.sentinel = { nodes.sentinel = {
proxiedDomains.vaultwarden = vaultwardenDomain; proxiedDomains.vaultwarden = vaultwardenDomain;
services.caddy.virtualHosts.${vaultwardenDomain} = { upstreams.vaultwarden = {
servers."${config.services.vaultwarden.config.rocketAddress}:${toString config.services.vaultwarden.config.rocketPort}" = {};
extraConfig = ''
zone vaultwarden 64k;
keepalive 2;
'';
};
upstreams.vaultwarden-websocket = {
servers."${config.services.vaultwarden.config.websocketAddress}:${toString config.services.vaultwarden.config.websocketPort}" = {};
extraConfig = ''
zone vaultwarden-websocket 64k;
keepalive 2;
'';
};
virtualHosts.${vaultwardenDomain} = {
forceSSL = true;
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert vaultwardenDomain; useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert vaultwardenDomain;
extraConfig = '' extraConfig = ''
import common client_max_body_size 256M;
reverse_proxy {
to http://${config.services.vaultwarden.config.rocketAddress}:${toString config.services.vaultwarden.config.rocketPort}
header_up X-Real-IP {remote_host}
}
reverse_proxy /notifications/hub {
to http://${config.services.vaultwarden.config.websocketAddress}:${toString config.services.vaultwarden.config.websocketPort}
header_up X-Real-IP {remote_host}
}
reverse_proxy /notifications/hub/negotiate {
to http://${config.services.vaultwarden.config.rocketAddress}:${toString config.services.vaultwarden.config.rocketPort}
header_up X-Real-IP {remote_host}
}
''; '';
locations."/".proxyPass = "http://vaultwarden";
locations."/notifications/hub" = {
proxyPass = "http://vaultwarden-websocket";
proxyWebsockets = true;
};
locations."/notifications/hub/negotiate" = {
proxyPass = "http://vaultwarden";
proxyWebsockets = true;
};
}; };
}; };

View file

@ -35,36 +35,6 @@ in {
individually for each cert by the user or via `security.acme.defaults`. individually for each cert by the user or via `security.acme.defaults`.
''; '';
}; };
nginx.proxiedDomains = mkOption {
default = {};
description = mdDoc "Simplified reverse proxy setup.";
type = types.attrsOf (types.submodule (submod: {
options = {
domain = mkOption {
type = types.str;
description = mdDoc "The public domain for the virtual host.";
};
upstream = mkOption {
type = types.str;
description = mdDoc "The upstream server to which requests are forwarded.";
};
scheme = mkOption {
type = types.str;
default = "http";
description = mdDoc "The scheme to use when connecting to upstream.";
};
useACMEHost = mkOption {
type = types.str;
default = config.lib.extra.matchingWildcardCert submod.config.domain;
description = mdDoc "The acme host certificate to use for the virtual host.";
};
};
}));
};
}; };
config = { config = {
@ -121,25 +91,6 @@ in {
add_header X-Frame-Options "DENY"; add_header X-Frame-Options "DENY";
add_header X-Content-Type-Options "nosniff"; add_header X-Content-Type-Options "nosniff";
''; '';
upstreams =
flip mapAttrs config.extra.nginx.proxiedDomains
(name: cfg: {
servers."${cfg.upstream}" = {};
extraConfig = ''
zone ${name} 64k;
keepalive 2;
'';
});
virtualHosts =
flip mapAttrs' config.extra.nginx.proxiedDomains
(name: cfg:
nameValuePair cfg.domain {
forceSSL = true;
inherit (cfg) useACMEHost;
locations."/".proxyPass = "${cfg.scheme}://${name}";
});
}; };
networking.firewall.allowedTCPPorts = optionals config.services.nginx.enable [80 443]; networking.firewall.allowedTCPPorts = optionals config.services.nginx.enable [80 443];