about summary refs log tree commit diff
path: root/nixos/modules/services/matrix
diff options
context:
space:
mode:
authorFrédéric Christ <frederic.christ@secunet.com>2023-07-15 21:20:55 +0200
committerFrédéric Christ <frederic.christ@secunet.com>2023-08-02 21:06:41 +0200
commitb443a4d9406b83ea7819e9ea4d9dedb8a17821c5 (patch)
tree686e0a1f2e09813a97d05b8647669df08f97e0b2 /nixos/modules/services/matrix
parent641d717acedd9a468c762b77fa15b5d8a3728600 (diff)
downloadnixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar.gz
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar.bz2
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar.lz
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar.xz
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.tar.zst
nixlib-b443a4d9406b83ea7819e9ea4d9dedb8a17821c5.zip
mautrix-whatsapp: Apply suggestions
This contribution applies suggestions made by Luflosi in
https://github.com/NixOS/nixpkgs/pull/176025#issuecomment-1237338551
as well as some general refactoring.

Co-authored-by: Luflosi <Luflosi@users.noreply.github.com>
Diffstat (limited to 'nixos/modules/services/matrix')
-rw-r--r--nixos/modules/services/matrix/mautrix-whatsapp.nix145
1 files changed, 89 insertions, 56 deletions
diff --git a/nixos/modules/services/matrix/mautrix-whatsapp.nix b/nixos/modules/services/matrix/mautrix-whatsapp.nix
index 8ba7fe752ca0..1a959bc96e9d 100644
--- a/nixos/modules/services/matrix/mautrix-whatsapp.nix
+++ b/nixos/modules/services/matrix/mautrix-whatsapp.nix
@@ -7,41 +7,25 @@
 with lib; let
   cfg = config.services.mautrix-whatsapp;
   dataDir = "/var/lib/mautrix-whatsapp";
-  settingsFormat = pkgs.formats.json {};
-
   registrationFile = "${dataDir}/whatsapp-registration.yaml";
-  settingsFile = settingsFormat.generate "config.json" cfg.settings;
-
-  startupScript = ''
-    ${pkgs.yq}/bin/yq -s '.[0].appservice.as_token = .[1].as_token
-      | .[0].appservice.hs_token = .[1].hs_token
-      | .[0]' ${settingsFile} ${registrationFile} \
-      > ${dataDir}/config.yml
-
-    ${pkgs.mautrix-whatsapp}/bin/mautrix-whatsapp \
-      --config='${dataDir}/config.yml' \
-      --registration='${registrationFile}'
-  '';
+  settingsFile = "${dataDir}/config.json";
+  settingsFileUnsubstituted = settingsFormat.generate "mautrix-whatsapp-config-unsubstituted.json" cfg.settings;
+  settingsFormat = pkgs.formats.json {};
 in {
   options.services.mautrix-whatsapp = {
-    enable = mkEnableOption "Mautrix-whatsapp, a puppeting bridge between Matrix and WhatsApp.";
+    enable = mkEnableOption "mautrix-whatsapp, a puppeting/relaybot bridge between Matrix and WhatsApp.";
 
     settings = mkOption rec {
       apply = recursiveUpdate default;
       inherit (settingsFormat) type;
 
-      description = lib.mdDoc ''
-        {file}`config.yaml` configuration as a Nix attribute set.
-        Configuration options should match those described in
-        [example-config.yaml](https://github.com/mautrix/whatsapp/blob/master/example-config.yaml).
-      '';
       default = {
         homeserver = {
           domain = config.services.matrix-synapse.settings.server_name;
         };
         appservice = rec {
-          address = "http://localhost:29318";
-          hostname = "0.0.0.0";
+          address = "http://localhost:${toString port}";
+          hostname = "[::]";
           port = 29318;
           database = {
             type = "sqlite3";
@@ -50,38 +34,62 @@ in {
           id = "whatsapp";
           bot = {
             username = "whatsappbot";
-            displayname = "WhatsApp Bot";
+            displayname = "WhatsApp Bridge Bot";
           };
           as_token = "";
           hs_token = "";
         };
         bridge = {
           username_template = "whatsapp_{{.}}";
-          displayname_template = "{{if .Notify}}{{.Notify}}{{else}}{{.Jid}}{{end}}";
+          displayname_template = "{{if .BusinessName}}{{.BusinessName}}{{else if .PushName}}{{.PushName}}{{else}}{{.JID}}{{end}} (WA)";
+          double_puppet_server_map = {};
+          login_shared_secret_map = {};
           command_prefix = "!wa";
           permissions."*" = "relay";
-        };
-        relay = {
-          enabled = true;
-          management = "!whatsappbot:${toString (config.services.matrix-synapse.settings.server_name)}";
+          relay = {
+            enabled = true;
+          };
         };
         logging = {
-          directory = "${dataDir}/logs";
-          file_name_format = "{{.Date}}-{{.Index}}.log";
-          file_date_format = "2006-01-02";
-          file_mode = 0384;
-          timestamp_format = "Jan _2, 2006 15:04:05";
-          print_level = "info";
+          min_level = "info";
+          writers = [
+            {
+              type = "stdout";
+              format = "pretty-colored";
+            }
+            {
+              type = "file";
+              format = "json";
+            }
+          ];
         };
       };
       example = {
         settings = {
-          homeserver.address = https://matrix.myhomeserver.org;
+          homeserver.address = "https://matrix.myhomeserver.org";
           bridge.permissions = {
             "@admin:myhomeserver.org" = "admin";
           };
         };
       };
+      description = lib.mdDoc ''
+        {file}`config.yaml` configuration as a Nix attribute set.
+        Configuration options should match those described in
+        [example-config.yaml](https://github.com/mautrix/whatsapp/blob/master/example-config.yaml).
+
+        Secret tokens should be specified using {option}`environmentFile`
+        instead of this world-readable attribute set.
+      '';
+    };
+
+    environmentFile = mkOption {
+      type = types.nullOr types.path;
+      default = null;
+      description = lib.mdDoc ''
+        File containing environment variables to be passed to the mautrix-whatsapp service,
+        in which secret tokens can be specified securely by optionally defining a value for
+        `MAUTRIX_WHATSAPP_BRIDGE_LOGIN_SHARED_SECRET`.
+      '';
     };
 
     serviceDependencies = mkOption {
@@ -105,6 +113,16 @@ in {
       after = ["network-online.target"] ++ cfg.serviceDependencies;
 
       preStart = ''
+        # substitute the settings file by environment variables
+        # in this case read from EnvironmentFile
+        test -f '${settingsFile}' && rm -f '${settingsFile}'
+        old_umask=$(umask)
+        umask 0177
+        ${pkgs.envsubst}/bin/envsubst \
+          -o '${settingsFile}' \
+          -i '${settingsFileUnsubstituted}'
+        umask $old_umask
+
         # generate the appservice's registration file if absent
         if [ ! -f '${registrationFile}' ]; then
           ${pkgs.mautrix-whatsapp}/bin/mautrix-whatsapp \
@@ -113,36 +131,51 @@ in {
             --registration='${registrationFile}'
         fi
         chmod 640 ${registrationFile}
-      '';
 
-      script = startupScript;
+        umask 0177
+        ${pkgs.yq}/bin/yq -s '.[0].appservice.as_token = .[1].as_token
+          | .[0].appservice.hs_token = .[1].hs_token
+          | .[0]' '${settingsFile}' '${registrationFile}' \
+          > '${settingsFile}.tmp'
+        mv '${settingsFile}.tmp' '${settingsFile}'
+        umask $old_umask
+      '';
 
       serviceConfig = {
-        Type = "simple";
-        #DynamicUser = true;
-        PrivateTmp = true;
+        DynamicUser = true;
+        EnvironmentFile = cfg.environmentFile;
         StateDirectory = baseNameOf dataDir;
         WorkingDirectory = "${dataDir}";
-
-        ProtectSystem = "strict";
+        ExecStart = ''
+          ${pkgs.mautrix-whatsapp}/bin/mautrix-whatsapp \
+          --config='${settingsFile}' \
+          --registration='${registrationFile}'
+        '';
+        LockPersonality = true;
+        MemoryDenyWriteExecute = true;
+        NoNewPrivileges = true;
+        PrivateDevices = true;
+        PrivateTmp = true;
+        PrivateUsers = true;
+        ProtectClock = true;
+        ProtectControlGroups = true;
         ProtectHome = true;
-        ProtectKernelTunables = true;
+        ProtectHostname = true;
+        ProtectKernelLogs = true;
         ProtectKernelModules = true;
-        ProtectControlGroups = true;
-        User = "mautrix-whatsapp";
-        Group = "matrix-synapse";
-        SupplementaryGroups = "matrix-synapse";
+        ProtectKernelTunables = true;
+        ProtectSystem = "strict";
+        Restart = "on-failure";
+        RestartSec = "30s";
+        RestrictRealtime = true;
+        RestrictSUIDSGID = true;
+        SystemCallArchitectures = "native";
+        SystemCallErrorNumber = "EPERM";
+        SystemCallFilter = ["@system-service"];
+        Type = "simple";
         UMask = 0027;
-        Restart = "always";
       };
+      restartTriggers = [settingsFileUnsubstituted];
     };
-
-    users.groups.mautrix-whatsapp = {};
-    users.users.mautrix-whatsapp = {
-      isSystemUser = true;
-      group = "mautrix-whatsapp";
-      home = dataDir;
-    };
-    services.matrix-synapse.settings.app_service_config_files = ["${registrationFile}"];
   };
 }