Denote with a different root directory on Linux only
As some of you may be aware, I prefer to keep certain things private, which means I don’t use cloud services for those. So, I wanted to have a dedicated folder for private notes on my Linux desktop, which doesn’t sync to my Mac. This sounds simple enough, but my setup makes it a bit more complicated.
For my technical documentations and blog posts, I use Denote, an excellent org-mode note-taking package from Protesilaos Stavrou (AKA Prot). By design, Denote is set up to have one root folder to work from with an option for subfolders under that folder for organization, which is what I have: ~/Sync/Notes/
is the main folder, and under it I have ~/Sync/Notes/Info
and ~/Sync/Notes/Blog/
, which should make sense if you’re follwing along.
~/Sync/Notes/
is under my Sync
folder which is synced between my devices with Syncthing. Usually this is a good idea, since I want to have my technical notes and blog posts available to me both on Linux and on the Mac - and for that matter also on the iPhone and Android, but that’s a different story.
You’re probably starting to see the problem here. Denote is using a synced folder for its root folder, so I can’t have a “just for Linux” folder under normal circumstances. I wanted that private Linux-only folder to be at ~/Documents/private
on my Linux desktop, and here we have yet another problem: the Mac has a ~/Documents/
folder as well, which I’m syncing to iCloud. Again, usually this is good: some of my work files are there, and I have a few settings saved. But if this folder was synced between my Linux and the Mac, these files will quickly be uploaded to Apple’s servers. Not good.
While Denote’s documentation notes that the upcoming release will have the option to define several folders as a list for denote-directory
, this is not in production yet. So my first attempt took me through Syncthing documentation.
I knew I could ask Syncthing to ignore files using ignore patterns, and these are robust enough to work on folders as well. After a few attempts, I managed to have a ~/Sync/Notes/private
folder on my Linux desktop that did not sync to my other devices.
While this works, it’s a weird workaround to have an isolated folder inside a folder meant for syncing; it’s kind of counterintuitive. Another concern: if the .stignore
file with the ignore pattern was to be deleted by mistake, Sycnthing would sync that folder and its contents everywhere.
Digging deeper into my old Denote configurations, I found the solution in a Denote function that could solve it:
(defun jr-private-denote ()
(interactive)
(let ((denote-directory (expand-file-name "~/Documents/private/"))
(denote-excluded-directories-regexp "data")
(denote-prompts '(title keywords))
(denote-org-front-matter "
#+title: %s
#+creator: JTR
#+date: %s
#+filetags: %s
#+identifier: %s
#+STARTUP: inlineimages
#+OPTIONS: num:nil
\n"))
(call-interactively 'denote)))
This function bypasses the regular denoate creation process (M-x denote
) and changes the denote root folder to ~/Documents/private
just for the purpose of this function. As well, I’ve included a few more options in the Denote front-matter, like the creator and the option to load images when the file loads. This function also excludes the /data
subfolder under ~/Documents/private
, which contains attachments, so I don’t create a note there by mistake.
This worked well, but it still leaves me with the problem I mentioned earlier. My configurations are stored in an org file synced inside my sync folder (so Emacs on my Linux desktop will run the same way as Emacs on my Mac, as much as possible), which means I could still run this function on the Mac, creating a private note in my Documentation folder there, and I don’t want a chance of that to happen. Besides, tweaking stuff is fun.
To fix that, I included a condition to help out:
(defun jr-private-denote ()
(interactive)
(cond
((eq system-type 'gnu/linux)
(let ((denote-directory (expand-file-name "~/Documents/private/"))
(denote-excluded-directories-regexp "data")
(denote-prompts '(title keywords))
(denote-org-front-matter "
#+title: %s
#+creator: JTR
#+date: %s
#+filetags: %s
#+identifier: %s
#+STARTUP: inlineimages
#+OPTIONS: num:nil
\n"))
(call-interactively 'denote)))
((eq system-type 'darwin)
(message "You're using your Mac"))))
Now I have the Denote org file creation process dependent on a condition that I am running on Linux: (eq system-type 'gnu/linux)
. In case I’m running on Mac, (eq system-type 'darwin)
, I will only get a reminder that I’m using my Mac, and that’s it, nothing further will happen.