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,
}: ''
echo " -> Aggregating "${lib.escapeShellArg host}":"${lib.escapeShellArg name}"" >&2
echo -n ${lib.escapeShellArg host}"+"${lib.escapeShellArg name}" "
${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"
'');

View file

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

View file

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

View file

@ -42,15 +42,22 @@ in {
proxiedDomains.grafana = grafanaDomain;
services.caddy.virtualHosts.${grafanaDomain} = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert grafanaDomain;
extraConfig = ''
import common
reverse_proxy {
to http://${config.services.grafana.settings.server.http_addr}:${toString config.services.grafana.settings.server.http_port}
header_up X-Real-IP {remote_host}
}
'';
services.nginx = {
upstreams.grafana = {
servers."${config.services.grafana.settings.server.http_addr}:${toString config.services.grafana.settings.server.http_port}" = {};
extraConfig = ''
zone grafana 64k;
keepalive 2;
'';
};
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 = {
proxiedDomains.kanidm = kanidmDomain;
services.caddy.virtualHosts.${kanidmDomain} = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert kanidmDomain;
extraConfig = ''
import common
reverse_proxy {
to https://${config.services.kanidm.serverSettings.bindaddress}
header_up X-Real-IP {remote_host}
transport http {
tls_insecure_skip_verify
}
}
'';
services.nginx = {
upstreams.kanidm = {
servers."${config.services.kanidm.serverSettings.bindaddress}" = {};
extraConfig = ''
zone kanidm 64k;
keepalive 2;
'';
};
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).
generator.script = config.age.generators.basic-auth.script;
mode = "440";
group = "caddy";
group = "nginx";
};
services.caddy.virtualHosts.${lokiDomain} = {
useACMEHost = sentinelCfg.lib.extra.matchingWildcardCert lokiDomain;
extraConfig = ''
import common
skip_log
basicauth {
import ${sentinelCfg.age.secrets.loki-basic-auth-hashes.path}
}
reverse_proxy {
to http://${config.services.loki.configuration.server.http_listen_address}:${toString config.services.loki.configuration.server.http_listen_port}
header_up X-Real-IP {remote_host}
}
'';
services.nginx = {
upstreams.loki = {
servers."${config.services.loki.configuration.server.http_listen_address}:${toString config.services.loki.configuration.server.http_listen_port}" = {};
extraConfig = ''
zone loki 64k;
keepalive 2;
'';
};
virtualHosts.${lokiDomain} = {
forceSSL = true;
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 = {
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;
extraConfig = ''
import common
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}
}
client_max_body_size 256M;
'';
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`.
'';
};
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 = {
@ -121,25 +91,6 @@ in {
add_header X-Frame-Options "DENY";
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];