at 23.11-pre 3.5 kB view raw
1{config, pkgs, lib, ...}: 2let 3 cfg = config.services.nghttpx; 4 5 # renderHost :: Either ServerOptions Path -> String 6 renderHost = server: 7 if builtins.isString server 8 then "unix://${server}" 9 else "${server.host},${builtins.toString server.port}"; 10 11 # Filter out submodule parameters whose value is null or false or is 12 # the key _module. 13 # 14 # filterParams :: ParamsSubmodule -> ParamsSubmodule 15 filterParams = p: 16 lib.filterAttrs 17 (n: v: ("_module" != n) && (null != v) && (false != v)) 18 (lib.optionalAttrs (null != p) p); 19 20 # renderBackend :: BackendSubmodule -> String 21 renderBackend = backend: 22 let 23 host = renderHost backend.server; 24 patterns = lib.concatStringsSep ":" backend.patterns; 25 26 # Render a set of backend parameters, this is somewhat 27 # complicated because nghttpx backend patterns can be entirely 28 # omitted and the params may be given as a mixed collection of 29 # 'key=val' pairs or atoms (e.g: 'proto=h2;tls') 30 params = 31 lib.mapAttrsToList 32 (n: v: 33 if builtins.isBool v 34 then n 35 else if builtins.isString v 36 then "${n}=${v}" 37 else "${n}=${builtins.toString v}") 38 (filterParams backend.params); 39 40 # NB: params are delimited by a ";" which is the same delimiter 41 # to separate the host;[pattern];[params] sections of a backend 42 sections = 43 builtins.filter (e: "" != e) ([ 44 host 45 patterns 46 ]++params); 47 formattedSections = lib.concatStringsSep ";" sections; 48 in 49 "backend=${formattedSections}"; 50 51 # renderFrontend :: FrontendSubmodule -> String 52 renderFrontend = frontend: 53 let 54 host = renderHost frontend.server; 55 params0 = 56 lib.mapAttrsToList 57 (n: v: if builtins.isBool v then n else v) 58 (filterParams frontend.params); 59 60 # NB: nghttpx doesn't accept "tls", you must omit "no-tls" for 61 # the default behavior of turning on TLS. 62 params1 = lib.remove "tls" params0; 63 64 sections = [ host] ++ params1; 65 formattedSections = lib.concatStringsSep ";" sections; 66 in 67 "frontend=${formattedSections}"; 68 69 configurationFile = pkgs.writeText "nghttpx.conf" '' 70 ${lib.optionalString (null != cfg.tls) ("private-key-file="+cfg.tls.key)} 71 ${lib.optionalString (null != cfg.tls) ("certificate-file="+cfg.tls.crt)} 72 73 user=nghttpx 74 75 ${lib.concatMapStringsSep "\n" renderFrontend cfg.frontends} 76 ${lib.concatMapStringsSep "\n" renderBackend cfg.backends} 77 78 backlog=${builtins.toString cfg.backlog} 79 backend-address-family=${cfg.backend-address-family} 80 81 workers=${builtins.toString cfg.workers} 82 rlimit-nofile=${builtins.toString cfg.rlimit-nofile} 83 84 ${lib.optionalString cfg.single-thread "single-thread=yes"} 85 ${lib.optionalString cfg.single-process "single-process=yes"} 86 87 ${cfg.extraConfig} 88 ''; 89in 90{ imports = [ 91 ./nghttpx-options.nix 92 ]; 93 94 config = lib.mkIf cfg.enable { 95 96 users.groups.nghttpx = { }; 97 users.users.nghttpx = { 98 group = config.users.groups.nghttpx.name; 99 isSystemUser = true; 100 }; 101 102 103 systemd.services = { 104 nghttpx = { 105 wantedBy = [ "multi-user.target" ]; 106 after = [ "network.target" ]; 107 script = '' 108 ${pkgs.nghttp2}/bin/nghttpx --conf=${configurationFile} 109 ''; 110 111 serviceConfig = { 112 Restart = "on-failure"; 113 RestartSec = 60; 114 }; 115 }; 116 }; 117 }; 118}