Sync Emacs Org Agenda Files via Dropbox Without Conflicts
I use beorg on iPad/iPhone to view my Emacs Org files. Until today, I did use it only for viewing files, not edit tasks, because I ran into sync conflicts.
This is how I solved the problem with a few simple1 settings.
Put org files into Dropbox
First, put your org files into the Dropbox. I have all .org
files in one directory and use the directory as org-agenda-files
:
(setq org-agenda-files (quote ("~/Pending/org/gtd")))
This will automatically expand directory contents using org-agenda-file-regexp
, which by default is set to:
"\\`[^.].*\\.org\\'"
So it matches all non-hidden org files, nice.
Prevent sync conflicts
When you sync files, you externally change the files that correspond to buffers that are probably open at all times if you use Emacs org agenda. Once you edit files on your computer, either saving will not work because of conflicts, or you will be asked if you want to read buffer contents from disk again.
One part of avoiding conflicts is to save relevant org files often, the other part is auto-reloading from disk when possible.
Auto-save org buffers to disk
You can enable auto-saving of org files while emacs is running with a hook:
(add-hook 'auto-save-hook 'org-save-all-org-buffers)
That will put auto-saving all open org files on a timer. Performing changes to buffers from the org agenda overview, for example, doesn’t mark the buffer as needing to auto-save, as far as I understand. So this setting helps to auto-save all org buffers regularly.
Auto-reload buffers when files on disk change
Then you can enable auto-reloading from disk when you change files in the Dropbox.
I am not comfortable having global-auto-revert-mode
turned on, I’d rather limit this to my task lists. But if this is cool with you, just put (global-auto-revert-mode t)
into your init.el
file.
If you’re like me and want to set only the task-related org buffers to auto-reload, you need to enable auto-revert-mode
minor mode for these buffers. That will reload the buffer when the file changes like the global variant, but limited to a particular buffer.
Do not set this manually. There’s a better way: auto-executing commands when files are loaded.
Emacs will execute whatever you put into a .dir-locals.el
as soon as you open (aka “find”) a file from that directory. This can be used to enable auto-revert-mode
for all org files in your Dropbox.
In my case, the path would be ~/Pending/org/gtd/.dir-locals.el
, and this is what I put inside:
; Enable auto-revert-mode for buffers from files from this directory:
((nil . ((eval . (auto-revert-mode 1)))))
Conclusion
Now when I open my org agenda, all org-agenda-files
will be loaded to populate the agenda – that is all contents from this directory. Each and every corresponding buffer will have auto-reload-mode
enabled, and thanks to the global settings, will save regularly to disk.
This isn’t bullet-proof. I can still produce file conflicts easily when I change files on disk before the auto-save is triggered.
But you know what? I didn’t even bother checking the auto-save interval settings. I want to save web links to my inbox.org
and tick off items from my mobile devices, that’s it. And when I’m on my mobile devices, minutes will have passed since I left my Mac and the files will already have synced. Same in the other direction. I don’t sit in front of my Mac and tick off stuff on my iPad. That’d be stupid. So I don’t produce sync errors under regular circumstances.
I’m happy with the result, and I hope your life will be better with this, too!
-
Simple, of course, only in hindsight. As always, figuring out what I am really looking for when tweaking my Emacs setup is the worst part. For example, I was trying to write a
ct/org-agenda-reload-all-buffers
that callsrevert-buffer
for each agenda-managed buffer, and I was prepared to manually sync by hitting the “R” key from the agenda view like a caveman. Now I found a totally different approach. ↩