about summary refs log tree commit diff
path: root/nixpkgs/nixos/modules/security/krb5/krb5-conf-format.nix
blob: d01e47a40be059a5d654c9822f3f528d8c7f637f (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
{ pkgs, lib, ... }:

# Based on
# - https://web.mit.edu/kerberos/krb5-1.12/doc/admin/conf_files/krb5_conf.html
# - https://manpages.debian.org/unstable/heimdal-docs/krb5.conf.5heimdal.en.html

let
  inherit (lib) boolToString concatMapStringsSep concatStringsSep filter
    isAttrs isBool isList mapAttrsToList mdDoc mkOption singleton splitString;
  inherit (lib.types) attrsOf bool coercedTo either int listOf oneOf path
    str submodule;
in
{ }: {
  type = let
    section = attrsOf relation;
    relation = either (attrsOf value) value;
    value = either (listOf atom) atom;
    atom = oneOf [int str bool];
  in submodule {
    freeformType = attrsOf section;
    options = {
      include = mkOption {
        default = [ ];
        description = mdDoc ''
          Files to include in the Kerberos configuration.
        '';
        type = coercedTo path singleton (listOf path);
      };
      includedir = mkOption {
        default = [ ];
        description = mdDoc ''
          Directories containing files to include in the Kerberos configuration.
        '';
        type = coercedTo path singleton (listOf path);
      };
      module = mkOption {
        default = [ ];
        description = mdDoc ''
          Modules to obtain Kerberos configuration from.
        '';
        type = coercedTo path singleton (listOf path);
      };
    };
  };

  generate = let
    indent = str: concatMapStringsSep "\n" (line: "  " + line) (splitString "\n" str);

    formatToplevel = args @ {
      include ? [ ],
      includedir ? [ ],
      module ? [ ],
      ...
    }: let
      sections = removeAttrs args [ "include" "includedir" "module" ];
    in concatStringsSep "\n" (filter (x: x != "") [
      (concatStringsSep "\n" (mapAttrsToList formatSection sections))
      (concatMapStringsSep "\n" (m: "module ${m}") module)
      (concatMapStringsSep "\n" (i: "include ${i}") include)
      (concatMapStringsSep "\n" (i: "includedir ${i}") includedir)
    ]);

    formatSection = name: section: ''
      [${name}]
      ${indent (concatStringsSep "\n" (mapAttrsToList formatRelation section))}
    '';

    formatRelation = name: relation:
      if isAttrs relation
      then ''
        ${name} = {
        ${indent (concatStringsSep "\n" (mapAttrsToList formatValue relation))}
        }''
      else formatValue name relation;

    formatValue = name: value:
      if isList value
      then concatMapStringsSep "\n" (formatAtom name) value
      else formatAtom name value;

    formatAtom = name: atom: let
      v = if isBool atom then boolToString atom else toString atom;
    in "${name} = ${v}";
  in
    name: value: pkgs.writeText name ''
      ${formatToplevel value}
    '';
}