On expiry calcurse-sync starts calcurse-relogin, a notification that opens the consent page when clicked and catches the OAuth code on 127.0.0.1:8749. dunst's left-click now runs a notification's action before closing it.
58 lines
2.1 KiB
Bash
Executable File
58 lines
2.1 KiB
Bash
Executable File
#!/bin/bash
|
|
# Sync calcurse with Google Calendar via calcurse-caldav; start the login prompt when the weekly OAuth login expires.
|
|
# --now: called from the UI's pre-load hook (skip the UI check, shorter timeout, no daemon restart).
|
|
# --authcode CODE: finish a login (from calcurse-relogin, which checks for the UI itself).
|
|
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
|
|
authcode=()
|
|
case ${1:-} in
|
|
--now) now=true ;;
|
|
--authcode) authcode=(--authcode "$2") ;;
|
|
esac
|
|
|
|
# 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 && ((${#authcode[@]} == 0)) && 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 "${authcode[@]}" 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
|
|
# Prompt via calcurse-relogin, again daily if the prompt was dismissed.
|
|
if [[ ! -e $expired_flag || -n $(find "$expired_flag" -mmin +1440) ]]; then
|
|
systemctl --user start --no-block calcurse-relogin.service
|
|
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
|