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