vuls: init at 0.27.0
[NixPkgs.git] / nixos / modules / programs / rust-motd.nix
blob19f98868ee344fcb5a4b65a761e02b7562478695
1 { config, lib, pkgs, ... }:
3 let
4   cfg = config.programs.rust-motd;
5   format = pkgs.formats.toml { };
7   # Order the sections in the TOML according to the order of sections
8   # in `cfg.order`.
9   motdConf = pkgs.runCommand "motd.conf"
10     {
11       __structuredAttrs = true;
12       inherit (cfg) order settings;
13       nativeBuildInputs = [ pkgs.remarshal pkgs.jq ];
14     }
15     ''
16       cat "$NIX_ATTRS_JSON_FILE" \
17         | jq '.settings as $settings
18               | .order
19               | map({ key: ., value: $settings."\(.)" })
20               | from_entries' -r \
21         | json2toml /dev/stdin "$out"
22     '';
23 in {
24   options.programs.rust-motd = {
25     enable = lib.mkEnableOption "rust-motd, a Message Of The Day (MOTD) generator";
26     enableMotdInSSHD = lib.mkOption {
27       default = true;
28       type = lib.types.bool;
29       description = ''
30         Whether to let `openssh` print the
31         result when entering a new `ssh`-session.
32         By default either nothing or a static file defined via
33         [](#opt-users.motd) is printed. Because of that,
34         the latter option is incompatible with this module.
35       '';
36     };
37     refreshInterval = lib.mkOption {
38       default = "*:0/5";
39       type = lib.types.str;
40       description = ''
41         Interval in which the {manpage}`motd(5)` file is refreshed.
42         For possible formats, please refer to {manpage}`systemd.time(7)`.
43       '';
44     };
45     order = lib.mkOption {
46       type = lib.types.listOf lib.types.str;
47       default = builtins.attrNames cfg.settings;
48       defaultText = lib.literalExpression "attrNames cfg.settings";
49       description = ''
50         The order of the sections in [](#opt-programs.rust-motd.settings).
51         By default they are ordered alphabetically.
53         Context: since attribute sets in Nix are always
54         ordered alphabetically internally this means that
56         ```nix
57         {
58           uptime = { /* ... */ };
59           banner = { /* ... */ };
60         }
61         ```
63         will still have `banner` displayed before `uptime`.
65         To work around that, this option can be used to define the order of all keys,
66         i.e.
68         ```nix
69         {
70           order = [
71             "uptime"
72             "banner"
73           ];
74         }
75         ```
77         makes sure that `uptime` is placed before `banner` in the motd.
78       '';
79     };
80     settings = lib.mkOption {
81       type = lib.types.attrsOf format.type;
82       description = ''
83         Settings on what to generate. Please read the
84         [upstream documentation](https://github.com/rust-motd/rust-motd/blob/main/README.md#configuration)
85         for further information.
86       '';
87     };
88   };
89   config = lib.mkIf cfg.enable {
90     assertions = [
91       { assertion = config.users.motd == "";
92         message = ''
93           `programs.rust-motd` is incompatible with `users.motd`!
94         '';
95       }
96       { assertion = builtins.sort (a: b: a < b) cfg.order == builtins.attrNames cfg.settings;
97         message = ''
98           Please ensure that every section from `programs.rust-motd.settings` is present in
99           `programs.rust-motd.order`.
100         '';
101       }
102     ];
103     systemd.services.rust-motd = {
104       path = with pkgs; [ bash ];
105       documentation = [ "https://github.com/rust-motd/rust-motd/blob/v${pkgs.rust-motd.version}/README.md" ];
106       description = "motd generator";
107       wantedBy = [ "multi-user.target" ];
108       serviceConfig = {
109         ExecStart = "${pkgs.writeShellScript "update-motd" ''
110           ${pkgs.rust-motd}/bin/rust-motd ${motdConf} > motd
111         ''}";
112         CapabilityBoundingSet = [ "" ];
113         LockPersonality = true;
114         MemoryDenyWriteExecute = true;
115         NoNewPrivileges = true;
116         PrivateDevices = true;
117         PrivateTmp = true;
118         ProtectClock = true;
119         ProtectControlGroups = true;
120         ProtectHome = true;
121         ProtectHostname = true;
122         ProtectKernelModules = true;
123         ProtectKernelLogs = true;
124         ProtectKernelTunables = true;
125         ProtectSystem = "full";
126         StateDirectory = "rust-motd";
127         RestrictAddressFamilies = [ "AF_UNIX" ];
128         RestrictNamespaces = true;
129         RestrictRealtime = true;
130         RestrictSUIDSGID = true;
131         RemoveIPC = true;
132         WorkingDirectory = "/var/lib/rust-motd";
133       };
134     };
135     systemd.timers.rust-motd = {
136       wantedBy = [ "timers.target" ];
137       timerConfig.OnCalendar = cfg.refreshInterval;
138     };
139     security.pam.services.sshd.text = lib.mkIf cfg.enableMotdInSSHD (lib.mkDefault (lib.mkAfter ''
140       session optional ${pkgs.pam}/lib/security/pam_motd.so motd=/var/lib/rust-motd/motd
141     ''));
142     services.openssh.extraConfig = lib.mkIf (cfg.settings ? last_login && cfg.settings.last_login != {}) ''
143       PrintLastLog no
144     '';
145   };
146   meta.maintainers = with lib.maintainers; [ ma27 ];