

Configure Doom Emacs as an Email Client
source link: https://spin.atomicobject.com/doom-emacs-email-client/
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

I recently spent some time configuring Doom Emacs to be my email client. It took a lot of trial and error, but I finally have a working configuration. Why did I do this? Because the Emacs bug has bitten me, and the fever has taken over. Let’s go over my configuration and talk through some pain points I encountered.
Emacs for the Uninitiated
Excuse the hyperbole, but Emacs can do everything. At its core is a Lisp interpreter that one can script to do most computing tasks. And, over its 40+ year lifespan, Emacs has grown. It’s now configurable to integrate with the most popular development tools and environments. I’ve been using it for many things these days, from project management to switching my music to the next track. I’ve even used it to control my Twitch stream. Yes, it’s that capable.
It appeals to me not because it can do everything. Rather, I’m impressed with the consistent approach across all these applications. The ability to configure workflows across all my computing use cases has been game-changing.
Batteries Included
Out of the box, Emacs is very capable, but both learning and configuring are quite a time investment. I started my journey with a pre-configured framework, for lack of a better word, called Doom Emacs. Doom provides a curated experience with pre-configured packages. giving newcomers and the time-restrained a head start.
Even with the running head start, I found setting up email to be less than easy. The Doom documentation, while great in some respects, is lacking in this area. A pain point in my acclimation to the Emacs environment: it’s quite fragmented. Quite a bit of Googling showed me learning resources close to my specific needs. But there was nothing 100% in the hand-holding territory.
The Steps
Enough preamble. Let’s walk through the setup and configuration of mbsync, mu, and mu4e with multiple Gmail SMTP/IMAP accounts. It seemed to me that Gmail presented more challenges than configuring other providers. Gmail presents SMTP in a different way than most. Conventionally, one would sync folders between one’s provider and a local email store. Gmail has “labels” disguised as SMTP folders.
Dependencies
First, let’s grab our dependencies, of which there are a few. This post assumes you’re running some flavor of Linux or MacOS and know how to use its package manager. (It also assumes an installation of Doom Emacs itself, which is outside the scope of this particular post.)
Grab yourself a copy of mbsync
and mu
. These are for syncing our mailboxes and their content. Here’s some convenient hand-holding.
# For Debian / Ubuntu flavors
sudo apt install mbsync
sudo apt install mu
#For Arch / Manjaro flavors
sudo pacman -S mbsync
sudo pacman -S mu
#For MacOS users
brew install isync
brew install mu
Configure
Now it’s time to configure mbsync
. Create a file called .mbsyncrc
and place it in your $HOME
directory. I’ll include the content of my .mbsyncrc
below. Make sure to replace every instance of the email address/account nicknames with your own.
# ACCOUNT INFORMATION
Create Both
Expunge Both
SyncState *
IMAPAccount youraddress@gmail
Host imap.gmail.com
User [email protected]
# You can also provide a plain text passwork like so:
# Password yourpasswordwithoutquotes
PassCmd "gpg --quiet --for-your-eyes-only --no-tty --decrypt \~/Mail\/[email protected]"
AuthMechs LOGIN
SSLType IMAPS
CertificateFile ~/.ssh/mu4e/cert.pem
IMAPStore account1@gmail-remote
Account youraddress@gmail
MaildirStore youraddress@gmail-local
Path ~/Mail/youraddress@gmail/
Inbox ~/Mail/youraddress@gmail/INBOX
Channel youraddress@gmail-inbox
Far :youraddress@gmail-remote:
Near :youraddress@gmail-local:
Patterns INBOX
Channel youraddress@gmail-sent
Far :youraddress@gmail-remote:"[Gmail]/Sent Mail"
Near :youraddress@gmail-local:"[Gmail].Sent Mail"
Channel youraddress@gmail-trash
Far :youraddress@gmail-remote:"[Gmail]/Trash"
Near :youraddress@gmail-local:"[Gmail].Trash"
Channel youraddress@gmail-archive
Far :youraddress@gmail-remote:"[Gmail]/All Mail"
Near :youraddress@gmail-local:"[Gmail].All Mail"
Channel youraddress@gmail-drafts
Far :youraddress@gmail-remote:"[Gmail]/Drafts"
Near :youraddress@gmail-local:"[Gmail].Drafts"
Group youraddress@gmail
Channel youraddress@gmail-inbox
Channel youraddress@gmail-trash
Channel youraddress@gmail-archive
Channel youraddress@gmail-sent
Channel youraddress@gmail-drafts
#############################################.
For brevity, I’ve only included one account above. However, the provided config should work for as many accounts as you need so long as you give them unique names. Be sure to replace the content with your own addresses, etc.
Directory
Next, you’ll need to create a directory for your mailboxes to live.
mkdir -p ~/Mail/youraddress@gmail
If you’ve had your account for 10+ years like I have, this may take a while. Keep in mind that this will pull in every email you ever sent or received. Mine was 5 gigs. If this is an issue, you may consider omitting the “Sent Mail” and “All Mail” folders.
Within Gmail, be sure to enable IMAP under the setting page’s Forwarding and IMAP/SMTP tab.
Now it’s time to fetch our mailboxes. Run the following command:
mbsync --all
Now go make some coffee, since this might take several minutes. Once your emails have finished downloading, run the following command:
mu init --maildir ~/Mail --my-address [email protected] --my-address [email protected] # for each email address youre adding.
Now tell mu to index your mailboxes with:
mu index
Now that we have the groundwork finished, we can finally start to configure mu4e
, our Emacs email client.
(require 'mu4e)
;; list of your email adresses:
(setq mu4e-personal-addresses '("[email protected]"
"[email protected]"))
(setq mu4e-contexts
`(,(make-mu4e-context
:name "Gmail" ;; Give it a unique name. I recommend they start with a different letter than the second one.
:enter-func (lambda () (mu4e-message "Entering gmail context"))
:leave-func (lambda () (mu4e-message "Leaving gmail context"))
:match-func (lambda (msg)
(when msg
(string= (mu4e-message-field msg :maildir) "/address1@gmail")))
:vars '((user-mail-address . "[email protected]")
(user-full-name . "Your Name Here")
(mu4e-drafts-folder . "/address1@gmail/[Gmail].Drafts")
(mu4e-refile-folder . "/address1@gmail/[Gmail].All Mail")
(mu4e-sent-folder . "/address1@gmail/[Gmail].Sent Mail")
(mu4e-trash-folder . "/address1@gmail/[Gmail].Trash")
;; SMTP configuration
(starttls-use-gnutls . t)
(smtpmail-starttls-credentials . '(("smtp.gmail.com" 587 nil nil)))
(smtpmail-smtp-user . "[email protected]")
(smtpmail-auth-credentials .
'(("smtp.gmail.com" 587 "[email protected]" nil)))
(smtpmail-default-smtp-server . "smtp.gmail.com")
(smtpmail-smtp-server . "smtp.gmail.com")
(smtpmail-smtp-service . 587)))
,(make-mu4e-context
:name "Business Address" ;; Or any other name you like.
:enter-func (lambda () (mu4e-message "Entering cablecar context"))
:leave-func (lambda () (mu4e-message "Leaving cablecar context"))
:match-func (lambda (msg)
(when msg
(string= (mu4e-message-field msg :maildir) "/address2@gmail")))
:vars '((user-mail-address . "[email protected]")
(user-full-name . "Your Name Here")
(mu4e-drafts-folder . "/address2@gmail/[Gmail].Drafts")
(mu4e-refile-folder . "/address2@gmail/[Gmail].All Mail")
(mu4e-sent-folder . "/address2@gmail/[Gmail].Sent Mail")
(mu4e-trash-folder . "/address2@gmail/[Gmail].Trash")
;; SMTP configuration
(starttls-use-gnutls . t)
(smtpmail-starttls-credentials . '(("smtp.gmail.com" 587 nil nil)))
(smtpmail-smtp-user . "[email protected]")
(smtpmail-auth-credentials .
'(("smtp.gmail.com" 587 "[email protected]" nil)))
(smtpmail-default-smtp-server . "smtp.gmail.com")
(smtpmail-smtp-server . "smtp.gmail.com")
(smtpmail-smtp-service . 587)))
))
(setq mu4e-maildir-shortcuts '((:maildir "/address2@gmail/INBOX" :key ?i)
(:maildir "/address2@gmail/[Gmail].Sent Mail" :key ?s)
(:maildir "/address2@gmail/[Gmail].Drafts" :key ?d)
(:maildir "/address2@gmail/[Gmail].Trash" :key ?t)
(:maildir "/address2@gmail/[Gmail].All Mail" :key ?a)
(:maildir "/address1@gmail/INBOX" :key ?I)
(:maildir "/address1@gmail/[Gmail].Sent Mail" :key ?S)
(:maildir "/address1@gmail/[Gmail].Drafts" :key ?D)
(:maildir "/address1@gmail/[Gmail].Trash" :key ?T)
(:maildir "/address1@gmail/[Gmail].All Mail" :key ?A)))
And with that, you can try to fetch your email with mu4e. In Doom, that’s a keystroke of SPC o m b u , which will land you in the “Today” box and fetch any fresh messages.
Note that above, when we configure our contexts, we give them unique names. In Doom Emacs, you can switch contexts with the ; key and then enter the first letter of the name of the context.
Configuring Doom Emacs as an Email Client: Wrapping Up
I hope this post will save you a good bit of the time and frustration I experienced. My biggest piece of advice would be to follow the mailbox naming conventions laid out here. Naming them something else will cause the creation of those Mailbox names inside Gmail, duplicating their contents. It took me several tries to get that right, wasting a lot of time and bandwidth in the meantime.
Recommend
-
97
GitHub is where people build software. More than 28 million people use GitHub to discover, fork, and contribute to over 80 million projects.
-
28
Migrating To Doom Emacs15 Mar 2020Yesterday, I spent some time migrating my vanilla Emacs configuration to Doom Emacs. The whole process took me...
-
7
Literal Programming Emacs Configure Literal Programming Emacs Configure Table of Contents Theme dracula dark theme (use-package dracula-t...
-
12
从Spacemacs迁移到Doom Emacs 发表于 2020-03-26 | 分类于 技术控 | 2 Com...
-
8
Setting Up Gmail in Doom Emacs using mbsync and mu4e I can think of far better ways to spend a quiet Sunday afternoon than trying to get Doom Emacs to serve as an email client, but...
-
8
doom-parents A set of Doom Emacs mappings for manipulating parentheses and sexps Installation ;; ~/.doom.d/packages.el (package! doom-parents :recipe (:host github :repo "tomekw/doom-parents")) ;; ~/.doom.d...
-
17
Clojure and Doom Emacs on a brand new M1 computerI've recently landed my first Clojure position and received an m1-powered MacBook. Two months before that, I had also bought myself an m1 MacBook air and had to set up Clojure to use i...
-
16
最近看了《子弹笔记法》,又想要折腾GTD工作法了。为什么起这个念头呢?那是因为2020都快结束了,而年初的计划根本就没有实现啊,感觉又白白浪费了一年,而我的青春已经所剩无几了(甚至到了连说“青春”两个字都要厚着脸皮的地步)。看了这本书之后,我决心要通...
-
33
在 2021-07-17 org-roam v2 已经正式合并到master分支,已经不用再像本文一样折腾了。 写在前面# org-...
-
4
Sachin Artani May 22, 2023 4 minute read ...
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK