146 lines
3.2 KiB
Nix
146 lines
3.2 KiB
Nix
{ config, lib, ... }:
|
|
|
|
let
|
|
inherit (lib)
|
|
attrsToList
|
|
concatStringsSep
|
|
filterAttrs
|
|
getAttr
|
|
mapAttrs
|
|
mapAttrs'
|
|
mkEnableOption
|
|
mkIf
|
|
mkOption
|
|
nameValuePair
|
|
recursiveUpdate
|
|
;
|
|
|
|
inherit (lib.types)
|
|
attrs
|
|
attrsOf
|
|
bool
|
|
port
|
|
str
|
|
submodule
|
|
;
|
|
|
|
cfg = config.dgn-web;
|
|
in
|
|
{
|
|
options.dgn-web = {
|
|
enable = mkEnableOption "sane defaults for web services.";
|
|
|
|
internalPorts = mkOption {
|
|
type = attrsOf port;
|
|
default = { };
|
|
description = ''
|
|
Map from the web services to their internal ports, it should avoid port clashes.
|
|
'';
|
|
};
|
|
|
|
simpleProxies = mkOption {
|
|
type = attrsOf (submodule {
|
|
options = {
|
|
port = mkOption {
|
|
type = port;
|
|
description = ''
|
|
Port where the service will listen.
|
|
'';
|
|
};
|
|
|
|
host = mkOption {
|
|
type = str;
|
|
description = ''
|
|
Hostname of the service.
|
|
'';
|
|
};
|
|
|
|
proxyWebsockets = mkOption {
|
|
type = bool;
|
|
default = false;
|
|
description = ''
|
|
Whether to support proxying websocket connections with HTTP/1.1.
|
|
'';
|
|
};
|
|
|
|
vhostConfig = mkOption {
|
|
type = attrs;
|
|
default = { };
|
|
description = ''
|
|
Additional virtualHost settings.
|
|
'';
|
|
};
|
|
};
|
|
});
|
|
};
|
|
};
|
|
|
|
config = mkIf cfg.enable {
|
|
assertions = [
|
|
(
|
|
let
|
|
duplicates = builtins.attrValues (
|
|
builtins.mapAttrs (p: serv: "${p}: ${concatStringsSep ", " serv}") (
|
|
filterAttrs (_: ls: builtins.length ls != 1) (
|
|
builtins.foldl' (
|
|
rev:
|
|
{ name, value }:
|
|
let
|
|
str = builtins.toString value;
|
|
in
|
|
rev // { ${str} = (rev.${str} or [ ]) ++ [ name ]; }
|
|
) { } (attrsToList cfg.internalPorts)
|
|
)
|
|
)
|
|
);
|
|
in
|
|
{
|
|
assertion = duplicates == [ ];
|
|
message = ''
|
|
Internal ports cannot be used for multiple services, the clashes are:
|
|
${concatStringsSep "\n " duplicates}
|
|
'';
|
|
}
|
|
)
|
|
];
|
|
|
|
dgn-web.internalPorts = mapAttrs (_: getAttr "port") cfg.simpleProxies;
|
|
|
|
services.nginx = {
|
|
enable = true;
|
|
|
|
virtualHosts = mapAttrs' (
|
|
_:
|
|
{
|
|
host,
|
|
port,
|
|
proxyWebsockets,
|
|
vhostConfig,
|
|
}:
|
|
nameValuePair host (
|
|
recursiveUpdate {
|
|
forceSSL = true;
|
|
enableACME = true;
|
|
|
|
locations."/" = {
|
|
proxyPass = "http://127.0.0.1:${builtins.toString port}";
|
|
inherit proxyWebsockets;
|
|
};
|
|
} vhostConfig
|
|
)
|
|
) cfg.simpleProxies;
|
|
|
|
recommendedBrotliSettings = true;
|
|
recommendedGzipSettings = true;
|
|
recommendedOptimisation = true;
|
|
recommendedProxySettings = true;
|
|
recommendedTlsSettings = true;
|
|
recommendedZstdSettings = true;
|
|
};
|
|
|
|
networking.firewall.allowedTCPPorts = [
|
|
80
|
|
443
|
|
];
|
|
};
|
|
}
|