#!/bin/sh set -euf NL=' ' BN="${0##*/}" # note: use setsid when calling this with exec # e.g. if you make this a void user-service, do # exec setsid twitch-notify errecho() { echo "$*" >&2 ; } fail() { errecho "error: $BN: $*"; exit 1; } innerclean() { [ -f "${1:-}" ] && rm -f "$1" [ -f "${IMG:-}" ] && rm -f "$IMG" } clean() { trap 'exit' INT HUP TERM EXIT [ -f "${HTML:-}" ] && rm -f "$HTML" [ -f "${IMG:-}" ] && rm -f "$IMG" [ -d "${DIR:-}" ] && rm -rf "$DIR" kill 0 } # with the sleep 0.5, 2 tries gives like 99.9% accuracy check() { tmphtml="$2" max_tries=2 trap 'innerclean "$tmphtml"' INT HUP TERM EXIT curl --connect-timeout 10 -s -o "$2" -L "https://twitch.tv/$1" if [ -n "$(pup 'script[type="application/ld+json"]' < "$2")" ]; then if [ ! -f "$DIR/$1" ]; then touch "$DIR/$1" IMG="$(mktemp -t "twitch-notify-img.XXXX")" curl --connect-timeout 10 -s -o "$IMG" -L "$(pup 'meta[property="og:image"]' 'attr{content}' < "$2")" TITLE="$(pup 'script[type="application/ld+json"] text{}' < "$2" | jq -r '.[0].description')" CODE="$(notify-send -A "watch" -A "copy" -t 10000 -u normal -i "$IMG" "$1 is online!$NL$NL\"$TITLE\"")" case "${CODE:-999}" in 0) xdg-open "https://twitch.tv/$1" ;; 1) printf '%s' "https://twitch.tv/$1" | xclip -sel clipboard ;; *) : ;; esac rm -f "$IMG" fi elif [ "$i" -lt "$max_tries" ]; then i=$((i + 1)) sleep 0.5 check "$1" "$2" else [ -f "$DIR/$1" ] && rm "$DIR/$1" echo "$1 is most likely offline or doesn't exist." fi [ -f "$2" ] && rm -f "$2" } # janky way to do this but fuck it. easiest one that doesn't get race conditioned # if a file with their name exists in DIR, they're online DIR="${XDG_RUNTIME_DIR:-"${TMPDIR:-/tmp}"}/twitch-notify-dir-$USER" while getopts :t:l OPT; do case "$OPT" in t) SLEEP_INTERVAL="$OPTARG" ;; # in seconds, default 180 l) [ -d "$DIR" ] && printf 'ONLINE CHANNELS:\n' && ls -w 1 "$DIR"; exit 0 ;; *) fail "unknown option: -$OPTARG" ;; esac done shift "$((OPTIND - 1))" # this mkdir should prevent any "someone's trying to override this" type beats mkdir -m 700 -- "$DIR" || fail "$DIR already exists! remove it if no daemon is running" trap 'clean' INT HUP TERM EXIT while for name; do i=0 HTML="$(mktemp -t "twitch-notify-html.XXXX")" check "$name" "$HTML" & done do sleep "${SLEEP_INTERVAL:-60}" done & wait