diff options
Diffstat (limited to 'sys/web/sites')
| -rw-r--r-- | sys/web/sites/default.nix | 7 | ||||
| -rw-r--r-- | sys/web/sites/home.nix | 38 | ||||
| -rw-r--r-- | sys/web/sites/host.nix | 106 | ||||
| -rw-r--r-- | sys/web/sites/portal.nix | 37 |
4 files changed, 188 insertions, 0 deletions
diff --git a/sys/web/sites/default.nix b/sys/web/sites/default.nix new file mode 100644 index 0000000..ba2835c --- /dev/null +++ b/sys/web/sites/default.nix @@ -0,0 +1,7 @@ +{ + imports = [ + ./home.nix + ./host.nix + ./portal.nix + ]; +} diff --git a/sys/web/sites/home.nix b/sys/web/sites/home.nix new file mode 100644 index 0000000..fed9b84 --- /dev/null +++ b/sys/web/sites/home.nix @@ -0,0 +1,38 @@ +{ + config, + lib, + ... +}: +with lib; let + cfg = config.local.web.sites.home; + inherit (config.local) domains; +in { + options.local.web.sites.home = { + enable = mkEnableOption "home site"; + + proxyUrl = mkOption { + type = types.str; + }; + }; + + config = mkIf cfg.enable { + local.web = { + enable = mkDefault true; + ownedCerts = ["home"]; + }; + + services.nginx.virtualHosts.${domains.home.main} = { + forceSSL = true; + useACMEHost = domains.home.main; + + locations."/".extraConfig = '' + proxy_pass ${cfg.proxyUrl}; + proxy_redirect http:// https://; + + # Necesario debido a websockets + proxy_set_header Upgrade $http_upgrade; + proxy_set_header Connection $connection_upgrade; + ''; + }; + }; +} diff --git a/sys/web/sites/host.nix b/sys/web/sites/host.nix new file mode 100644 index 0000000..ea6cc23 --- /dev/null +++ b/sys/web/sites/host.nix @@ -0,0 +1,106 @@ +{ + config, + lib, + ... +}: +with lib; let + cfg = config.local.web.sites.host; + + inherit (config.local) domains; + inherit (config.local.net) hostname; + + users = filterAttrs (_: user: user.install) config.local.users; + hostDomain = domains.${hostDomainName}; + hostDomainName = "host-${hostname}"; + + userCerts = flatten (flatten (mapAttrsToList + (name: user: + map + (cert: { + fprint = config.local.pki.byPath.${cert}.fingerprint.sha1-lower; + inherit name; + }) + user.mail.certs) + users)); +in { + options.local.web.sites.host = { + enable = mkEnableOption "host site, restricted to per-user client certs"; + }; + + config = mkIf cfg.enable { + local.web = { + enable = mkDefault true; + ownedCerts = [hostDomainName]; + }; + + services = { + nginx = { + appendHttpConfig = '' + map $ssl_client_fingerprint $host_user_from_fprint { + default ""; + ${concatMapStringsSep "\n " (pair: "\"${escapeRegex pair.fprint}\" \"${pair.name}\";") userCerts} + } + ''; + + virtualHosts = { + ${hostDomain.main} = { + forceSSL = true; + useACMEHost = hostDomain.main; + + extraConfig = '' + ssl_verify_depth 2; + ssl_verify_client optional; + ssl_client_certificate ${config.local.pki.ca.mail.fullchain}; + + #if ($ssl_client_verify != "SUCCESS") { + #return 403; + #} + ''; + + locations = + { + "/".return = 403; + } + // concatMapAttrs + (name: user: let + userLocation = config: { + extraConfig = + '' + if ($host_user_from_fprint != "${name}") { + return 403; + } + '' + + config; + }; + + userLocations = + { + "/${name}" = '' + return 404; + ''; + } + // optionalAttrs user.mail.dav { + "/${name}/dav" = '' + proxy_pass http://unix:/run/host-www/${name}/dav.sock; + ''; + }; + in + mapAttrs (_: userLocation) userLocations) + (filterAttrs (_: user: user.mail.certs != []) users); + }; + }; + }; + }; + + systemd.tmpfiles.settings."10-run-host-www" = + concatMapAttrs + (name: _: { + "/run/host-www/${name}".d = { + mode = "0750"; + user = name; + group = "nginx"; + }; + }) + users; + }; +} diff --git a/sys/web/sites/portal.nix b/sys/web/sites/portal.nix new file mode 100644 index 0000000..4b5f704 --- /dev/null +++ b/sys/web/sites/portal.nix @@ -0,0 +1,37 @@ +{ + config, + lib, + ... +}: +with lib; let + cfg = config.local.web.sites.portal; + inherit (config.local) domains; +in { + options.local.web.sites.portal = { + enable = mkEnableOption "public non-fqdn portal"; + }; + + config = mkIf cfg.enable { + local.web = { + enable = mkDefault true; + ownedCerts = ["host" "sysret"]; + defaultACMEHost = domains.host.main; + }; + + services.nginx.virtualHosts = { + ${domains.host.www} = { + forceSSL = true; + useACMEHost = domains.host.main; + serverAliases = [domains.host.main]; + }; + + ${domains.sysret.main} = { + forceSSL = true; + useACMEHost = domains.sysret.main; + serverAliases = [domains.sysret.www]; + + locations."/fsociety".return = "301 https://meet.posixlycorrect.com/%C6%92%C6%A8%C5%8F%C4%8B%D3%80%C9%99%CF%AE%D0%A3"; + }; + }; + }; +} |
