1{ config, lib, pkgs, ... }:
2
3with lib;
4
5let
6 cfg = config.programs.rust-motd;
7 format = pkgs.formats.toml { };
8in {
9 options.programs.rust-motd = {
10 enable = mkEnableOption (lib.mdDoc "rust-motd");
11 enableMotdInSSHD = mkOption {
12 default = true;
13 type = types.bool;
14 description = mdDoc ''
15 Whether to let `openssh` print the
16 result when entering a new `ssh`-session.
17 By default either nothing or a static file defined via
18 [](#opt-users.motd) is printed. Because of that,
19 the latter option is incompatible with this module.
20 '';
21 };
22 refreshInterval = mkOption {
23 default = "*:0/5";
24 type = types.str;
25 description = mdDoc ''
26 Interval in which the {manpage}`motd(5)` file is refreshed.
27 For possible formats, please refer to {manpage}`systemd.time(7)`.
28 '';
29 };
30 settings = mkOption {
31 type = types.submodule {
32 freeformType = format.type;
33 };
34 description = mdDoc ''
35 Settings on what to generate. Please read the
36 [upstream documentation](https://github.com/rust-motd/rust-motd/blob/main/README.md#configuration)
37 for further information.
38 '';
39 };
40 };
41 config = mkIf cfg.enable {
42 assertions = [
43 { assertion = config.users.motd == null;
44 message = ''
45 `programs.rust-motd` is incompatible with `users.motd`!
46 '';
47 }
48 ];
49 systemd.services.rust-motd = {
50 path = with pkgs; [ bash ];
51 documentation = [ "https://github.com/rust-motd/rust-motd/blob/v${pkgs.rust-motd.version}/README.md" ];
52 description = "motd generator";
53 serviceConfig = {
54 ExecStart = "${pkgs.writeShellScript "update-motd" ''
55 ${pkgs.rust-motd}/bin/rust-motd ${format.generate "motd.conf" cfg.settings} > motd
56 ''}";
57 CapabilityBoundingSet = [ "" ];
58 LockPersonality = true;
59 MemoryDenyWriteExecute = true;
60 NoNewPrivileges = true;
61 PrivateDevices = true;
62 PrivateTmp = true;
63 ProtectClock = true;
64 ProtectControlGroups = true;
65 ProtectHome = true;
66 ProtectHostname = true;
67 ProtectKernelModules = true;
68 ProtectKernelLogs = true;
69 ProtectKernelTunables = true;
70 ProtectSystem = "full";
71 StateDirectory = "rust-motd";
72 RestrictAddressFamilies = [ "AF_UNIX" ];
73 RestrictNamespaces = true;
74 RestrictRealtime = true;
75 RestrictSUIDSGID = true;
76 RemoveIPC = true;
77 WorkingDirectory = "/var/lib/rust-motd";
78 };
79 };
80 systemd.timers.rust-motd = {
81 wantedBy = [ "timers.target" ];
82 timerConfig.OnCalendar = cfg.refreshInterval;
83 };
84 security.pam.services.sshd.text = mkIf cfg.enableMotdInSSHD (mkDefault (mkAfter ''
85 session optional ${pkgs.pam}/lib/security/pam_motd.so motd=/var/lib/rust-motd/motd
86 ''));
87 services.openssh.extraConfig = mkIf (cfg.settings ? last_login && cfg.settings.last_login != {}) ''
88 PrintLastLog no
89 '';
90 };
91 meta.maintainers = with maintainers; [ ma27 ];
92}