calcurse: sync with Google Calendar via calcurse-caldav
Hourly timer started from xmonad, plus UI hooks that sync before load and after exit. calcurse-sync notifies once when the OAuth login expires and restarts the daemon after imports, since it never re-reads its files.
This commit is contained in:
7 files changed
+78
No files matched your search
Executable
+52
@@ -0,0 +1,52 @@
|
||||
#!/bin/bash
|
||||
# Sync calcurse with Google Calendar via calcurse-caldav; notify once when the weekly OAuth login expires.
|
||||
# --now: called from the UI's pre-load hook (skip the UI check, shorter timeout, no daemon restart).
|
||||
set -uo pipefail
|
||||
|
||||
data=${XDG_DATA_HOME:-$HOME/.local/share}/calcurse
|
||||
state=${XDG_STATE_HOME:-$HOME/.local/state}/calcurse-sync
|
||||
expired_flag=$state/login-expired
|
||||
now=false
|
||||
[[ ${1:-} == --now ]] && now=true
|
||||
|
||||
# The UI keeps the data in memory, so syncing under it would lose changes; its post-save hook syncs after it exits.
|
||||
ui_running() {
|
||||
# shellcheck disable=SC2009 # pgrep can't match "has any terminal"
|
||||
ps -C calcurse -o tty= | grep -qv '?'
|
||||
}
|
||||
|
||||
if ! $now && ui_running; then
|
||||
echo "calcurse UI is running, skipping"
|
||||
exit 0
|
||||
fi
|
||||
|
||||
mkdir -p "$state"
|
||||
# BROWSER=true: an expired login must not open browser tabs on its own.
|
||||
out=$(BROWSER=true timeout "$($now && echo 15 || echo 60)" calcurse-caldav 2>&1)
|
||||
rc=$?
|
||||
printf '%s\n' "$out"
|
||||
|
||||
if ((rc != 0)); then
|
||||
if grep -q 'Access token is missing or refresh token is expired' <<<"$out"; then
|
||||
if [[ ! -e $expired_flag ]]; then
|
||||
notify-send -a calcurse -u critical -i x-office-calendar "Google Calendar login expired" \
|
||||
"Run calcurse-caldav in a terminal, allow access in the browser, then calcurse-caldav --authcode '<code>'."
|
||||
touch "$expired_flag"
|
||||
fi
|
||||
elif grep -q 'Another synchronization instance' <<<"$out"; then
|
||||
exit 0
|
||||
fi
|
||||
exit "$rc"
|
||||
fi
|
||||
rm -f "$expired_flag"
|
||||
|
||||
# A running daemon never re-reads the data files: restart it so imported appointments get alerts.
|
||||
if ! $now && ! grep -q '^0 items imported, 0 items removed locally' <<<"$out"; then
|
||||
pidfile=$data/.daemon.pid
|
||||
if [[ -s $pidfile ]] && pid=$(<"$pidfile") && kill "$pid" 2>/dev/null; then
|
||||
timeout 5 tail --pid="$pid" -f /dev/null
|
||||
# Own scope, so the daemon outlives this oneshot service.
|
||||
systemd-run --user --scope -q calcurse --daemon
|
||||
echo "restarted calcurse daemon"
|
||||
fi
|
||||
fi
|
||||
Reference in new issue
Block a user