at 24.11-pre 3.8 kB view raw
1{ lib, pkgs, config, ... }: 2 3let 4 inherit (lib) mkEnableOption mkPackageOption mkOption types; 5 6 cfg = config.services.c2fmzq-server; 7 8 argsFormat = { 9 type = with lib.types; attrsOf (nullOr (oneOf [ bool int str ])); 10 generate = lib.cli.toGNUCommandLineShell { 11 mkBool = k: v: [ 12 "--${k}=${if v then "true" else "false"}" 13 ]; 14 }; 15 }; 16in { 17 options.services.c2fmzq-server = { 18 enable = mkEnableOption "c2fmzq-server"; 19 20 bindIP = mkOption { 21 type = types.str; 22 default = "127.0.0.1"; 23 description = "The local address to use."; 24 }; 25 26 port = mkOption { 27 type = types.port; 28 default = 8080; 29 description = "The local port to use."; 30 }; 31 32 passphraseFile = mkOption { 33 type = types.str; 34 example = "/run/secrets/c2fmzq/pwfile"; 35 description = "Path to file containing the database passphrase"; 36 }; 37 38 package = mkPackageOption pkgs "c2fmzq" { }; 39 40 settings = mkOption { 41 type = types.submodule { 42 freeformType = argsFormat.type; 43 44 options = { 45 address = mkOption { 46 internal = true; 47 type = types.str; 48 default = "${cfg.bindIP}:${toString cfg.port}"; 49 }; 50 51 database = mkOption { 52 type = types.str; 53 default = "%S/c2fmzq-server/data"; 54 description = "Path of the database"; 55 }; 56 57 verbose = mkOption { 58 type = types.ints.between 1 3; 59 default = 2; 60 description = "The level of logging verbosity: 1:Error 2:Info 3:Debug"; 61 }; 62 }; 63 }; 64 description = '' 65 Configuration for c2FmZQ-server passed as CLI arguments. 66 Run {command}`c2FmZQ-server help` for supported values. 67 ''; 68 example = { 69 verbose = 3; 70 allow-new-accounts = true; 71 auto-approve-new-accounts = true; 72 encrypt-metadata = true; 73 enable-webapp = true; 74 }; 75 }; 76 }; 77 78 config = lib.mkIf cfg.enable { 79 systemd.services.c2fmzq-server = { 80 description = "c2FmZQ-server"; 81 documentation = [ "https://github.com/c2FmZQ/c2FmZQ/blob/main/README.md" ]; 82 wantedBy = [ "multi-user.target" ]; 83 wants = [ "network-online.target" ]; 84 after = [ "network.target" "network-online.target" ]; 85 86 serviceConfig = { 87 ExecStart = "${lib.getExe cfg.package} ${argsFormat.generate cfg.settings}"; 88 AmbientCapabilities = ""; 89 CapabilityBoundingSet = ""; 90 DynamicUser = true; 91 Environment = "C2FMZQ_PASSPHRASE_FILE=%d/passphrase-file"; 92 IPAccounting = true; 93 IPAddressAllow = cfg.bindIP; 94 IPAddressDeny = "any"; 95 LoadCredential = "passphrase-file:${cfg.passphraseFile}"; 96 LockPersonality = true; 97 MemoryDenyWriteExecute = true; 98 NoNewPrivileges = true; 99 PrivateDevices = true; 100 PrivateIPC = true; 101 PrivateTmp = true; 102 PrivateUsers = true; 103 ProtectClock = true; 104 ProtectControlGroups = true; 105 ProtectHome = true; 106 ProtectHostname = true; 107 ProtectKernelLogs = true; 108 ProtectKernelModules = true; 109 ProtectKernelTunables = true; 110 ProtectProc = "invisible"; 111 ProtectSystem = "strict"; 112 RemoveIPC = true; 113 RestrictAddressFamilies = [ "AF_INET" "AF_INET6" ]; 114 RestrictNamespaces = true; 115 RestrictRealtime = true; 116 RestrictSUIDSGID = true; 117 SocketBindAllow = cfg.port; 118 SocketBindDeny = "any"; 119 StateDirectory = "c2fmzq-server"; 120 SystemCallArchitectures = "native"; 121 SystemCallFilter = [ "@system-service" "~@privileged @obsolete" ]; 122 }; 123 }; 124 }; 125 126 meta = { 127 doc = ./c2fmzq-server.md; 128 maintainers = with lib.maintainers; [ hmenke ]; 129 }; 130}