diff options
| author | Craig Jennings <c@cjennings.net> | 2025-10-12 11:47:26 -0500 |
|---|---|---|
| committer | Craig Jennings <c@cjennings.net> | 2025-10-12 11:47:26 -0500 |
| commit | 092304d9e0ccc37cc0ddaa9b136457e56a1cac20 (patch) | |
| tree | ea81999b8442246c978b364dd90e8c752af50db5 /modules/org-gcal-config.el | |
changing repositories
Diffstat (limited to 'modules/org-gcal-config.el')
| -rw-r--r-- | modules/org-gcal-config.el | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/modules/org-gcal-config.el b/modules/org-gcal-config.el new file mode 100644 index 00000000..7f9b656d --- /dev/null +++ b/modules/org-gcal-config.el @@ -0,0 +1,92 @@ +;;; org-gcal-config.el --- Google Calendar synchronization for Org-mode -*- lexical-binding: t; coding: utf-8; -*- +;; +;; Author: Craig Jennings <c@cjennings.net> +;; +;;; Commentary: +;; +;; Bidirectional synchronization between Google Calendar and Org-mode using org-gcal. +;; - Credential management via authinfo.gpg +;; - Automatic archival of past events +;; - Automatic removal of cancelled events, but with TODOs added for visibility +;; - System timezone configuration via functions in host-environment +;; - No notifications on syncing +;; - Initial automatic sync post Emacs startup. No auto resync'ing. +;; (my calendar doesn't change hourly and I want fewer distractions and slowdowns). +;; if you need it: https://github.com/kidd/org-gcal.el?tab=readme-ov-file#sync-automatically-at-regular-times +;; - Validates existing oath2-auto.plist file or creates it to avoid the issue mentioned here: +;; https://github.com/kidd/org-gcal.el?tab=readme-ov-file#note +;; +;; Prerequisites: +;; 1. Create OAuth 2.0 credentials in Google Cloud Console +;; See: https://github.com/kidd/org-gcal.el?tab=readme-ov-file#installation +;; 2. Store credentials in ~/.authinfo.gpg with this format: +;; machine org-gcal login YOUR_CLIENT_ID password YOUR_CLIENT_SECRET +;; 3. Define `gcal-file' in user-constants (location of org file to hold sync'd events). +;; +;; Usage: +;; - Manual sync: C-; g (or M-x org-gcal-sync) +;; +;; Note: +;; This configuration creates oauth2-auto.plist on first run to prevent sync errors. +;; Passphrase caching is enabled. +;; +;;; Code: + +(require 'host-environment) +(require 'user-constants) + +(use-package org-gcal + :defer t ;; unless idle timer is set below (currently disabled in config) + :bind ("C-; g" . org-gcal-sync) + :preface + ;; org-gcal stumbles if this doesn't exist before initial sync + (let ((oauth-file (concat user-emacs-directory "oauth2-auto.plist"))) + (unless (file-exists-p oauth-file) + (with-temp-buffer + (write-file oauth-file)))) + + :init + ;; identify calendar to sync and it's destination + (setq org-gcal-fetch-file-alist `(("craigmartinjennings@gmail.com" . ,gcal-file))) + + (setq org-gcal-up-days 30) ;; Look 30 days back + (setq org-gcal-down-days 60) ;; Look 60 days forward + (setq org-gcal-auto-archive t) ;; auto-archive old events + (setq org-gcal-notify-p nil) ;; nil disables; t enables notifications + (setq org-gcal-remove-api-cancelled-events t) ;; auto-remove cancelled events + (setq org-gcal-update-cancelled-events-with-todo t) ;; todo cancelled events for visibility + + :config + ;; Retrieve credentials from authinfo.gpg + (require 'auth-source) + (let ((credentials (car (auth-source-search :host "org-gcal" :require '(:user :secret))))) + (when credentials + (setq org-gcal-client-id (plist-get credentials :user)) + ;; The secret might be a function, so we need to handle that + (let ((secret (plist-get credentials :secret))) + (setq org-gcal-client-secret + (if (functionp secret) + (funcall secret) + secret))))) + + + ;; Enable plstore passphrase caching after org-gcal loads + (require 'plstore) + (setq plstore-cache-passphrase-for-symmetric-encryption t) + + ;; set org-gcal timezone based on system timezone + (setq org-gcal-local-timezone (cj/detect-system-timezone)) + + ;; Reload client credentials + (org-gcal-reload-client-id-secret)) + +;; Set up automatic initial sync on boot with error handling +(run-with-idle-timer + 5 nil + (lambda () + (condition-case err + (org-gcal-sync) + (error (message "org-gcal: Initial sync failed: %s" err))))) + +(provide 'org-gcal-config) +;;; org-gcal-config.el ends here |
