:PROPERTIES: :ID: da416dd3-d7bb-4a81-83fb-a5543817b462 :END: #+title: azos/mail #+filetags: :project: :knowledge: :mail: ** Architecture - 3 accounts defined in =features/mail/default.nix=: =zakobar= (primary, aner@zakobar.com via privateemail.com IMAP/SMTP), =gmail= (anerisgreat@gmail.com), =bgu= (anerz@post.bgu.ac.il, gmail-flavor IMAP) - Sync stack: =mbsync= (isync) pulls IMAP → =~/Maildir=, =msmtp= sends, =mu= indexes for search/mu4e. Confirmed by live inspection (2026-10-08): generated =~/.config/isyncrc= and =~/.config/msmtp/config= are fully populated and actively syncing (recent =.mbsyncstate= timestamps); mu4e's =mu4e-get-mail-command= is literally =mbsync -a=. - lieer was declared (=services.lieer.enable=/=programs.lieer.enable=) but had zero real footprint (no =.gmailieer.json= anywhere, no systemd units) — vestigial, removed from =features/mail/default.nix=. - Credentials via =pass=: =mbsync/anerisgreat@gmail.com=, =mbsync/anerz@post.bgu.ac.il=, =privateemail.com= (zakobar account). All decrypt through the same GPG smartcard (yubikey) key. - Periodic sync: =systemd.user.timers.mbsync-timer= runs every 5 min (2 min after login, then every =OnUnitActiveSec=). Guarded by a =gpg --card-status= presence check in the =mbsyncSafe= wrapper script so a missing yubikey skips the sync silently instead of triggering a pinentry "insert card" prompt — =gpg --card-status= only queries the reader and never itself invokes pinentry, making it a safe non-interactive gate. - Mail client is mu4e in Emacs (=azos-core/features/station/emacs/config.org=), not notmuch (a =notmuch-hello= mode reference exists only in a linum-disable list, appears vestigial/unused) ** Conventions - mu4e contexts match by maildir prefix: =/zakobar=, =/gmail=, =/bgu=; each sets its own sent/drafts/trash/archive (archive = "All Mail" for gmail-flavor accounts) - No user-defined tagging system — "tags" in this setup means mu4e flags (unread/trashed/replied) and Gmail labels, which arrive as IMAP folders under =[Gmail]/= rather than mu4e-native tags - Bookmarks (saved searches) defined in config: Inbox (all 3 combined), Unread, Today, Week - Maildir shortcuts: =z=/=g=/=b= keys jump to each account's inbox - Mail opens in a dedicated singleton tab via =azos/mail/open= (bound under the "open" keymap) ** Gotchas - mbsync's =remove=/=expunge= home-manager options (per-account =mbsync.remove=/=mbsync.expunge=) default to ="none"= and were never set — =\Deleted= flags synced down from IMAP but never actually got removed/expunged on either side, so trashed messages lingered forever in the local Maildir and showed up (struck-through) in any mu4e bookmark that didn't explicitly filter =flag:trashed=. Fixed 2026-10-08 by setting =mbsync.remove = "both"=/=mbsync.expunge = "both"= in =features/mail/default.nix= default_account_params, for all 3 accounts. Caveat: for Gmail-flavor accounts (=gmail=/=bgu=), Gmail's IMAP quirk means expunging any folder other than =[Gmail]/Trash= just removes that one label — the message survives under other labels (e.g. All Mail). =zakobar= (plain IMAP, no label system) has no such safety net: expunge there is a real, permanent, unrecoverable delete. - BGU's Workspace account (=anerz@post.bgu.ac.il=) localizes/renames the Gmail "Trash" special-use label to =[Gmail]/Bin= instead of =[Gmail]/Trash= — caused mbsync error "channel bgu: far side box [Gmail]/Trash cannot be opened" plus a stale local =[Gmail]/Trash= maildir with orphaned messages. =mu4e-trash-folder= for the BGU context must be =/bgu/[Gmail]/Bin=. Fixed 2026-10-08 (merged stale local messages into Bin, updated context). Don't assume standard Gmail folder names for Workspace/edu accounts — verify via IMAP LIST per account. - mu4e's "Inbox" bookmark historically did NOT exclude =flag:trashed= (unlike Unread/Today/Week) — direct cause of visibly crossed-out mail in Inbox. =flag:trashed= only reflects the literal Maildir =T= flag; it does NOT mean "located in a Trash/Bin/Spam-named folder." Because of Gmail's multi-label model, a genuinely-unread message filed anywhere also has a duplicate unread copy under =[Gmail]/All Mail= (same Message-ID, separate local file) — this inflated Unread-bookmark counts by ~2x. Fixed 2026-10-08: all four bookmarks (config.org, =mu4e-bookmarks=, ~line 95) now share one =let=-bound exclusion string filtering =flag:trashed= plus the Trash/Bin/Spam/All-Mail/"Deleted Messages" maildirs per account. - Live Emacs session state and the on-disk literate config drift independently: a nix rebuild (=azos-lauretta-update=) only regenerates files on disk, it does NOT reload anything into an already-running Emacs — =mu4e-contexts=/=mu4e-bookmarks= etc. stay at whatever was last =load-file='d or evaluated at startup. After editing =config.org=, hot-reload the *specific* top-level form that changed via =emacsclient -e '(load-file "/tmp/x.el")'= (extract just that sexp with exact matching parens — off-by-one line ranges silently truncate the form and error "End of file during parsing"). Forgetting to reload =mu4e-contexts= after fixing =mu4e-trash-folder= briefly almost recreated the just-deleted stale =/bgu/[Gmail]/Trash= folder, because the live session's BGU context still pointed at the old path and mu4e prompted "create trash folder?" on trash-mark-apply. - Debugging mu4e live via =emacsclient -e=: =(with-current-buffer "*mu4e-headers*" mu4e--search-last-query)= shows the active search; =(gethash docid mu4e--mark-map)= on a buffer's message-at-point shows the exact pending mark+target before applying; =(mu4e-context-vars (mu4e-context-current))= shows live (not file) context vars. Caution: if Emacs is blocked on a blocking minibuffer prompt (e.g. a =y-or-n-p= "create folder?" confirmation), queued =emacsclient -e= calls will hang/timeout rather than error — that's a sign a prompt is open and needs a human to answer it, not a crash. - BGU mailing list =cs_msc@mlists.cs.bgu.ac.il= (List-Id: =cs_msc.mlists.cs.bgu.ac.il=) floods =/bgu/logistics-cs-msc= with announcement mail that's essentially never read (backlog since Jan 2024, ~330 messages). Intended fix is a Gmail filter in the BGU Workspace webclient (Settings → Filters and Blocked Addresses, matching =list:cs_msc.mlists.cs.bgu.ac.il=, action "mark as read", optionally applied retroactively to existing matches) — not a local/mu4e-side fix, since it's about delivery-time read-state for mail the user doesn't want to individually triage. ** Key Files - =features/mail/default.nix= — accounts, mbsync/msmtp/mu config, mu init activation script, mbsync-timer systemd service/timer - =azos-core/features/station/emacs/config.org= (search "mu4e") — mu4e contexts, bookmarks, shortcuts, signing blacklist logic - =azos-core/features/station/emacs/_pkg.nix= — mu4e package dependency