]> Git — Sourcephile - sourcephile-nix.git/blob - nixos/modules/services/networking/knot.nix
knot: replace nsd as authoritative DNS
[sourcephile-nix.git] / nixos / modules / services / networking / knot.nix
1 { config, lib, pkgs, ... }:
2
3 with lib;
4
5 let
6 cfg = config.services.knot;
7
8 configFile = pkgs.writeText "knot.conf" cfg.extraConfig;
9 socketFile = "/run/knot/knot.sock";
10
11 knotConfCheck = file: pkgs.runCommand "knot-config-checked"
12 { buildInputs = [ cfg.package ]; } ''
13 ln -s ${configFile} $out
14 knotc --config=${configFile} conf-check
15 '';
16 keymgr = pkgs.writeShellScriptBin "keymgr" ''
17 ${pkgs.systemd}/bin/systemd-run --pipe \
18 --uid knot --working-directory="$PWD" \
19 -p DynamicUser=yes -p StateDirectory=knot \
20 ${cfg.package}/bin/keymgr --config=${configFile} "$@"
21 '';
22 knot-cli-wrappers = pkgs.stdenv.mkDerivation {
23 name = "knot-cli-wrappers";
24 buildInputs = [ pkgs.makeWrapper ];
25 buildCommand = ''
26 mkdir -p $out/bin
27 makeWrapper ${cfg.package}/bin/knotc "$out/bin/knotc" \
28 --add-flags "--config=${configFile}" \
29 --add-flags "--socket=${socketFile}"
30 for executable in kdig khost kjournalprint knsec3hash knsupdate kzonecheck
31 do
32 ln -s "${cfg.package}/bin/$executable" "$out/bin/$executable"
33 done
34 mkdir -p "$out/share"
35 ln -s '${cfg.package}/share/man' "$out/share/"
36 '';
37 };
38 in {
39 options = {
40 services.knot = {
41 enable = mkEnableOption "Knot authoritative-only DNS server";
42
43 extraArgs = mkOption {
44 type = types.listOf types.str;
45 default = [];
46 description = ''
47 List of additional command line paramters for knotd
48 '';
49 };
50
51 extraConfig = mkOption {
52 type = types.lines;
53 default = "";
54 description = ''
55 Extra lines to be added verbatim to knot.conf
56 '';
57 };
58
59 package = mkOption {
60 type = types.package;
61 default = pkgs.knot-dns;
62 defaultText = "pkgs.knot-dns";
63 description = ''
64 Which Knot DNS package to use
65 '';
66 };
67 };
68 };
69
70 config = mkIf config.services.knot.enable {
71 systemd.services.knot = {
72 unitConfig.Documentation = "man:knotd(8) man:knot.conf(5) man:knotc(8) https://www.knot-dns.cz/docs/${cfg.package.version}/html/";
73 description = cfg.package.meta.description;
74 wantedBy = [ "multi-user.target" ];
75 wants = [ "network.target" ];
76 after = ["network.target" ];
77
78 serviceConfig = {
79 Type = "notify";
80 ExecStart = "${cfg.package}/bin/knotd --config=${knotConfCheck configFile} --socket=${socketFile} ${concatStringsSep " " cfg.extraArgs}";
81 ExecReload = "${knot-cli-wrappers}/bin/knotc reload";
82 CapabilityBoundingSet = "CAP_NET_BIND_SERVICE CAP_SETPCAP";
83 AmbientCapabilities = "CAP_NET_BIND_SERVICE CAP_SETPCAP";
84 NoNewPrivileges = true;
85 DynamicUser = "yes";
86 RuntimeDirectory = "knot";
87 StateDirectory = "knot";
88 StateDirectoryMode = "0700";
89 PrivateDevices = true;
90 RestrictAddressFamilies = "AF_UNIX AF_INET AF_INET6";
91 SystemCallArchitectures = "native";
92 Restart = "on-abort";
93 };
94 };
95
96 environment.systemPackages = [ knot-cli-wrappers keymgr ];
97 };
98 }