diff --git a/modules/programs/himalaya.nix b/modules/programs/himalaya.nix index 9b5a1e39..a05782b0 100644 --- a/modules/programs/himalaya.nix +++ b/modules/programs/himalaya.nix @@ -8,14 +8,24 @@ let # attrs util that removes entries containing a null value compactAttrs = lib.filterAttrs (_: val: !isNull val); - # Needed for notmuch config, because the DB is here, and not in each account's dir + # needed for notmuch config, because the DB is here, and not in each + # account's dir maildirBasePath = config.accounts.email.maildirBasePath; - # make a himalaya config from a home-manager email account config + # make encryption config based on the given home-manager email + # account TLS config + mkEncryptionConfig = tls: + if tls.useStartTls then + "start-tls" + else if tls.enable then + "tls" + else + "none"; + + # make a himalaya account config based on the given home-manager + # email account config mkAccountConfig = _: account: let - # Use notmuch if it's enabled, otherwise fallback to IMAP then maildir - # Maildir is always set, so there's no easy way to detect if it's being used notmuchEnabled = account.notmuch.enable; imapEnabled = !isNull account.imap && !notmuchEnabled; maildirEnabled = !isNull account.maildir && !imapEnabled @@ -25,7 +35,7 @@ let email = account.address; display-name = account.realName; default = account.primary; - folder-aliases = { + folder.alias = { inbox = account.folders.inbox; sent = account.folders.sent; drafts = account.folders.drafts; @@ -43,202 +53,107 @@ let imapConfig = lib.optionalAttrs imapEnabled (compactAttrs { backend = "imap"; - imap-host = account.imap.host; - imap-port = account.imap.port; - imap-ssl = account.imap.tls.enable; - imap-starttls = account.imap.tls.useStartTls; - imap-login = account.userName; - imap-auth = "passwd"; - imap-passwd.cmd = builtins.concatStringsSep " " account.passwordCommand; + imap.host = account.imap.host; + imap.port = account.imap.port; + imap.encryption = mkEncryptionConfig account.imap.tls; + imap.login = account.userName; + imap.passwd.cmd = builtins.concatStringsSep " " account.passwordCommand; }); maildirConfig = lib.optionalAttrs maildirEnabled (compactAttrs { backend = "maildir"; - maildir-root-dir = account.maildir.absPath; + maildir.root-dir = account.maildir.absPath; }); notmuchConfig = lib.optionalAttrs notmuchEnabled (compactAttrs { backend = "notmuch"; - notmuch-db-path = maildirBasePath; + notmuch.database-path = maildirBasePath; }); smtpConfig = lib.optionalAttrs (!isNull account.smtp) (compactAttrs { - sender = "smtp"; - smtp-host = account.smtp.host; - smtp-port = account.smtp.port; - smtp-ssl = account.smtp.tls.enable; - smtp-starttls = account.smtp.tls.useStartTls; - smtp-login = account.userName; - smtp-auth = "passwd"; - smtp-passwd.cmd = builtins.concatStringsSep " " account.passwordCommand; + message.send.backend = "smtp"; + smtp.host = account.smtp.host; + smtp.port = account.smtp.port; + smtp.encryption = mkEncryptionConfig account.smtp.tls; + smtp.login = account.userName; + smtp.passwd.cmd = builtins.concatStringsSep " " account.passwordCommand; }); sendmailConfig = lib.optionalAttrs (isNull account.smtp && !isNull account.msmtp) { sender = "sendmail"; - sendmail-cmd = "${pkgs.msmtp}/bin/msmtp"; + sendmail.cmd = "${pkgs.msmtp}/bin/msmtp"; }; - config = globalConfig // signatureConfig // imapConfig // maildirConfig - // notmuchConfig // smtpConfig // sendmailConfig; + config = lib.attrsets.mergeAttrsList [ + globalConfig + signatureConfig + imapConfig + maildirConfig + notmuchConfig + smtpConfig + sendmailConfig + ]; in lib.recursiveUpdate config account.himalaya.settings; - # make a systemd service config from a name and a description - mkServiceConfig = name: desc: - let - inherit (config.services."himalaya-${name}") enable environment settings; - optionalArg = key: - if (key ? settings && !isNull settings."${key}") then - [ "--${key} ${settings."${key}"}" ] - else - [ ]; - in { - "himalaya-${name}" = lib.mkIf enable { - Unit = { - Description = desc; - After = [ "network.target" ]; - }; - Install = { WantedBy = [ "default.target" ]; }; - Service = { - ExecStart = lib.concatStringsSep " " - ([ "${himalaya.package}/bin/himalaya" ] ++ optionalArg "account" - ++ [ name ] ++ optionalArg "keepalive"); - ExecSearchPath = "/bin"; - Environment = - lib.mapAttrsToList (key: val: "${key}=${val}") environment; - Restart = "always"; - RestartSec = 10; - }; - }; - }; - in { meta.maintainers = with lib.hm.maintainers; [ soywod toastal ]; options = { programs.himalaya = { - enable = lib.mkEnableOption "the Himalaya email client"; + enable = lib.mkEnableOption "the email client Himalaya CLI"; package = lib.mkPackageOption pkgs "himalaya" { }; settings = lib.mkOption { type = lib.types.submodule { freeformType = tomlFormat.type; }; default = { }; description = '' - Himalaya global configuration. - See for supported values. + Himalaya CLI global configuration. + See for supported values. ''; }; }; - services = { - himalaya-notify = { - enable = lib.mkEnableOption "the Himalaya new emails notifier service"; + services.himalaya-watch = { + enable = lib.mkEnableOption + "the email client Himalaya CLI envelopes watcher service"; - environment = lib.mkOption { - type = with lib.types; attrsOf str; - default = { }; - example = lib.literalExpression '' - { - "PASSWORD_STORE_DIR" = "~/.password-store"; - } - ''; - description = '' - Extra environment variables to be exported in the service. - ''; - }; - - settings = { - account = lib.mkOption { - type = with lib.types; nullOr str; - default = null; - example = "gmail"; - description = '' - Name of the account the notifier should be started for. If - no account is given, the default one is used. - ''; - }; - - keepalive = lib.mkOption { - type = with lib.types; nullOr int; - default = null; - example = "500"; - description = '' - Notifier lifetime of the IDLE session (in seconds). - ''; - }; - }; + environment = lib.mkOption { + type = with lib.types; attrsOf str; + default = { }; + example = lib.literalExpression '' + { + "PASSWORD_STORE_DIR" = "~/.password-store"; + } + ''; + description = '' + Extra environment variables to be exported in the service. + ''; }; - himalaya-watch = { - enable = - lib.mkEnableOption "the Himalaya folder changes watcher service"; - - environment = lib.mkOption { - type = with lib.types; attrsOf str; - default = { }; - example = lib.literalExpression '' - { - "PASSWORD_STORE_DIR" = "~/.password-store"; - } - ''; - description = '' - Extra environment variables to be exported in the service. - ''; - }; - - settings = { - account = lib.mkOption { - type = with lib.types; nullOr str; - default = null; - example = "gmail"; - description = '' - Name of the account the watcher should be started for. If - no account is given, the default one is used. - ''; - }; - - keepalive = lib.mkOption { - type = with lib.types; nullOr int; - default = null; - example = "500"; - description = '' - Watcher lifetime of the IDLE session (in seconds). - ''; - }; - }; + settings.account = lib.mkOption { + type = with lib.types; nullOr str; + default = null; + example = "personal"; + description = '' + Name of the account the watcher should be started for. + If no account is given, the default one is used. + ''; }; }; accounts.email.accounts = lib.mkOption { type = lib.types.attrsOf (lib.types.submodule { options.himalaya = { - enable = lib.mkEnableOption "Himalaya for this email account"; - - # TODO: remove me for the next release - backend = lib.mkOption { - type = with lib.types; nullOr str; - default = null; - description = '' - Specifying {option}`accounts.email.accounts.*.himalaya.backend` is deprecated, - set {option}`accounts.email.accounts.*.himalaya.settings.backend` instead. - ''; - }; - - # TODO: remove me for the next release - sender = lib.mkOption { - type = with lib.types; nullOr str; - description = '' - Specifying {option}`accounts.email.accounts.*.himalaya.sender` is deprecated, - set {option}'accounts.email.accounts.*.himalaya.settings.sender' instead. - ''; - }; + enable = lib.mkEnableOption + "the email client Himalaya CLI for this email account"; settings = lib.mkOption { type = lib.types.submodule { freeformType = tomlFormat.type; }; default = { }; description = '' - Himalaya configuration for this email account. - See for supported values. + Himalaya CLI configuration for this email account. + See for supported values. ''; }; }; @@ -256,15 +171,31 @@ in { globalConfig = compactAttrs himalaya.settings; allConfig = globalConfig // accountsConfig; in tomlFormat.generate "himalaya-config.toml" allConfig; - - systemd.user.services = { } - // mkServiceConfig "notify" "Himalaya new emails notifier service" - // mkServiceConfig "watch" "Himalaya folder changes watcher service"; - - # TODO: remove me for the next release - warnings = (lib.optional ("backend" ? himalaya && !isNull himalaya.backend) - "Specifying 'accounts.email.accounts.*.himalaya.backend' is deprecated, set 'accounts.email.accounts.*.himalaya.settings.backend' instead") - ++ (lib.optional ("sender" ? himalaya && !isNull himalaya.sender) - "Specifying 'accounts.email.accounts.*.himalaya.sender' is deprecated, set 'accounts.email.accounts.*.himalaya.settings.sender' instead."); + systemd.user.services = let + inherit (config.services.himalaya-watch) enable environment settings; + optionalArg = key: + if (key ? settings && !isNull settings."${key}") then + [ "--${key} ${settings."${key}"}" ] + else + [ ]; + in { + himalaya-watch = lib.mkIf enable { + Unit = { + Description = "Email client Himalaya CLI envelopes watcher service"; + After = [ "network.target" ]; + }; + Install = { WantedBy = [ "default.target" ]; }; + Service = { + ExecStart = lib.concatStringsSep " " + ([ "${himalaya.package}/bin/himalaya" "envelopes" "watch" ] + ++ optionalArg "account"); + ExecSearchPath = "/bin"; + Environment = + lib.mapAttrsToList (key: val: "${key}=${val}") environment; + Restart = "always"; + RestartSec = 10; + }; + }; + }; }; } diff --git a/tests/modules/programs/himalaya/basic-expected.toml b/tests/modules/programs/himalaya/basic-expected.toml index 2df6b85f..55906e15 100644 --- a/tests/modules/programs/himalaya/basic-expected.toml +++ b/tests/modules/programs/himalaya/basic-expected.toml @@ -3,28 +3,30 @@ backend = "imap" default = true display-name = "H. M. Test" email = "hm@example.com" -imap-auth = "passwd" -imap-host = "imap.example.com" -imap-login = "home.manager" -imap-port = 993 -imap-ssl = true -imap-starttls = false -sender = "smtp" -smtp-auth = "passwd" -smtp-host = "smtp.example.com" -smtp-login = "home.manager" -smtp-port = 465 -smtp-ssl = true -smtp-starttls = false -["hm@example.com".folder-aliases] +["hm@example.com".folder.alias] drafts = "Drafts" inbox = "Inbox" sent = "Sent" trash = "Trash" -["hm@example.com".imap-passwd] +["hm@example.com".imap] +encryption = "tls" +host = "imap.example.com" +login = "home.manager" +port = 993 + +["hm@example.com".imap.passwd] cmd = "password-command" -["hm@example.com".smtp-passwd] +["hm@example.com".message.send] +backend = "smtp" + +["hm@example.com".smtp] +encryption = "tls" +host = "smtp.example.com" +login = "home.manager" +port = 465 + +["hm@example.com".smtp.passwd] cmd = "password-command" diff --git a/tests/modules/programs/himalaya/basic.nix b/tests/modules/programs/himalaya/basic.nix index 1555d1e9..f31a8464 100644 --- a/tests/modules/programs/himalaya/basic.nix +++ b/tests/modules/programs/himalaya/basic.nix @@ -10,8 +10,6 @@ with lib; imap.port = 993; smtp.port = 465; himalaya.enable = true; - himalaya.backend = test.asserts.warnings.expected; - himalaya.sender = test.asserts.warnings.expected; }; }; diff --git a/tests/modules/programs/himalaya/default.nix b/tests/modules/programs/himalaya/default.nix index b357361e..1cc08705 100644 --- a/tests/modules/programs/himalaya/default.nix +++ b/tests/modules/programs/himalaya/default.nix @@ -1,6 +1 @@ -{ - himalaya-basic = ./basic.nix; - himalaya-imap-smtp = ./imap-smtp.nix; - himalaya-maildir-sendmail = ./maildir-sendmail.nix; - himalaya-notmuch-sendmail = ./notmuch-sendmail.nix; -} +{ himalaya-basic = ./basic.nix; } diff --git a/tests/modules/programs/himalaya/imap-smtp-expected.toml b/tests/modules/programs/himalaya/imap-smtp-expected.toml deleted file mode 100644 index 6db2542d..00000000 --- a/tests/modules/programs/himalaya/imap-smtp-expected.toml +++ /dev/null @@ -1,35 +0,0 @@ -email-listing-page-size = 40 - -["hm@example.com"] -backend = "imap" -default = true -display-name = "H. M. Test" -email = "hm@example.com" -email-listing-page-size = 50 -folder-listing-page-size = 50 -imap-auth = "passwd" -imap-host = "imap.example.com" -imap-login = "home.manager" -imap-port = 143 -imap-ssl = false -imap-starttls = false -sender = "smtp" -smtp-auth = "passwd" -smtp-host = "smtp.example.com" -smtp-login = "home.manager" -smtp-port = 465 -smtp-ssl = true -smtp-starttls = true - -["hm@example.com".folder-aliases] -custom = "Custom" -drafts = "D" -inbox = "In2" -sent = "Out" -trash = "Trash" - -["hm@example.com".imap-passwd] -cmd = "password-command" - -["hm@example.com".smtp-passwd] -cmd = "password-command" diff --git a/tests/modules/programs/himalaya/imap-smtp.nix b/tests/modules/programs/himalaya/imap-smtp.nix deleted file mode 100644 index c1347d23..00000000 --- a/tests/modules/programs/himalaya/imap-smtp.nix +++ /dev/null @@ -1,58 +0,0 @@ -{ config, lib, pkgs, ... }: - -with lib; - -{ - accounts.email.accounts = { - "hm@example.com" = { - primary = true; - address = "hm@example.com"; - userName = "home.manager"; - realName = "H. M. Test"; - passwordCommand = "password-command"; - imap = { - host = "imap.example.com"; - port = 143; - tls = { enable = false; }; - }; - smtp = { - host = "smtp.example.com"; - port = 465; - tls = { - enable = true; - useStartTls = true; - }; - }; - folders = { - inbox = "In"; - sent = "Out"; - drafts = "D"; - }; - himalaya = { - enable = true; - settings = { - folder-listing-page-size = 50; - email-listing-page-size = 50; - folder-aliases = { - inbox = "In2"; - custom = "Custom"; - }; - }; - }; - }; - }; - - programs.himalaya = { - enable = true; - settings = { email-listing-page-size = 40; }; - }; - - test.stubs.himalaya = { }; - - nmt.script = '' - assertFileExists home-files/.config/himalaya/config.toml - assertFileContent home-files/.config/himalaya/config.toml ${ - ./imap-smtp-expected.toml - } - ''; -} diff --git a/tests/modules/programs/himalaya/maildir-sendmail-expected.toml b/tests/modules/programs/himalaya/maildir-sendmail-expected.toml deleted file mode 100644 index 61ae940d..00000000 --- a/tests/modules/programs/himalaya/maildir-sendmail-expected.toml +++ /dev/null @@ -1,16 +0,0 @@ -email-listing-page-size = 50 - -["hm@example.com"] -backend = "maildir" -default = true -display-name = "H. M. Test" -email = "hm@example.com" -maildir-root-dir = "/home/hm-user/Maildir/hm@example.com" -sender = "sendmail" -sendmail-cmd = "msmtp" - -["hm@example.com".folder-aliases] -drafts = "Drafts" -inbox = "Inbox" -sent = "Sent" -trash = "Deleted" diff --git a/tests/modules/programs/himalaya/maildir-sendmail.nix b/tests/modules/programs/himalaya/maildir-sendmail.nix deleted file mode 100644 index d40f39ba..00000000 --- a/tests/modules/programs/himalaya/maildir-sendmail.nix +++ /dev/null @@ -1,35 +0,0 @@ -{ config, lib, pkgs, ... }: - -with lib; - -{ - accounts.email.accounts = { - "hm@example.com" = { - primary = true; - address = "hm@example.com"; - userName = "home.manager"; - realName = "H. M. Test"; - passwordCommand = "password-command"; - folders = { trash = "Deleted"; }; - msmtp.enable = true; - himalaya = { - enable = true; - settings = { sendmail-cmd = "msmtp"; }; - }; - }; - }; - - programs.himalaya = { - enable = true; - settings = { email-listing-page-size = 50; }; - }; - - test.stubs.himalaya = { }; - - nmt.script = '' - assertFileExists home-files/.config/himalaya/config.toml - assertFileContent home-files/.config/himalaya/config.toml ${ - ./maildir-sendmail-expected.toml - } - ''; -} diff --git a/tests/modules/programs/himalaya/notmuch-sendmail-expected.toml b/tests/modules/programs/himalaya/notmuch-sendmail-expected.toml deleted file mode 100644 index fcc00c7c..00000000 --- a/tests/modules/programs/himalaya/notmuch-sendmail-expected.toml +++ /dev/null @@ -1,16 +0,0 @@ -email-listing-page-size = 50 - -["hm@example.com"] -backend = "notmuch" -default = true -display-name = "H. M. Test" -email = "hm@example.com" -notmuch-db-path = "/home/hm-user/Maildir" -sender = "sendmail" -sendmail-cmd = "msmtp" - -["hm@example.com".folder-aliases] -drafts = "Drafts" -inbox = "Inbox" -sent = "Sent" -trash = "Deleted" diff --git a/tests/modules/programs/himalaya/notmuch-sendmail.nix b/tests/modules/programs/himalaya/notmuch-sendmail.nix deleted file mode 100644 index ff96dfd1..00000000 --- a/tests/modules/programs/himalaya/notmuch-sendmail.nix +++ /dev/null @@ -1,36 +0,0 @@ -{ config, lib, pkgs, ... }: - -with lib; - -{ - accounts.email.accounts = { - "hm@example.com" = { - primary = true; - address = "hm@example.com"; - userName = "home.manager"; - realName = "H. M. Test"; - passwordCommand = "password-command"; - folders = { trash = "Deleted"; }; - notmuch.enable = true; - msmtp.enable = true; - himalaya = { - enable = true; - settings = { sendmail-cmd = "msmtp"; }; - }; - }; - }; - - programs.himalaya = { - enable = true; - settings = { email-listing-page-size = 50; }; - }; - - test.stubs.himalaya = { }; - - nmt.script = '' - assertFileExists home-files/.config/himalaya/config.toml - assertFileContent home-files/.config/himalaya/config.toml ${ - ./notmuch-sendmail-expected.toml - } - ''; -}