Chris R

This is such an extremely specific complaint

Doom Emacs and direnv

Historical Post

Hi, reader. I wrote this in 2020. Technology and culture referenced may have changed and I nearly certainly have. I may disagree now with what I wrote then, or it may refer to obsolete terms and tech. I will usually only edit old posts to refresh links that have changed. If this post is particularly offensive please contact me and let me know.

I use both Doom Emacs and Direnv a lot, and I discovered -- and with the author of Doom's assistance, solved -- an peculiar issue arising from the interaction of the two.

Doom defines a doom sync command whose job it is to update the compiled elisp for packages, but also to update the environment used by emacs, including its PATH, by writing out the full current environment to a local cache. That allows Emacs to be independent of the shell invoking it.

Direnv customizes your shell environment based on your current working directory.

When both of these are in play, though, running doom sync can have interesting effects, since the direnv state will be retained when generating your synced environment file.

So, I took advantage of a hidden, but valuable, feature in Doom's cli: Env pre-hooks. I added a cli.el file to the ~/.doom.d configuration directory, and in that file I added a hook to check for direnv and prevent sync if running in a direnv:

(add-hook! 'doom-sync-pre-hook
  (or (not (getenv "DIRENV_DIR"))
      doom-auto-accept
      (y-or-n-p "doom env update: Direnv detected! Continue anyway?")
      (user-error "Aborted")))

This helps me avoid overwriting my neutral environment with project-specific content.

I haven't managed to identify a full set of available hooks, but I know that doom-sync-pre-hook and doom-env-pre-hook exist at a minimum.

Feedback

I don't embed any comments on this site, so if you want to give me feedback on the posts you find here, I encourage you tag me on wandering.shop