#!/bin/sh # cronpup: CronPup's command-line helper (POSIX sh + curl, no other dependencies). # # cronpup run [--] [args...] start signal, run, report exit code + output tail # cronpup ping [start|fail|] send one signal # cronpup version # # is the UUID from the monitor's page, a "/" pair (add ?create=1 to auto-create), or a full # ping URL. The base is https://cronpup.com unless CRONPUP_URL is set. # `run` passes the command's exit code and output through unchanged, and problems reaching CronPup never change the # job's result. # # Install: curl -fsSL https://cronpup.com/install.sh | sh # Crontab: 0 3 * * * cronpup run 0b6c4f5e-... -- /opt/jobs/backup.sh set -u VERSION=1.0.0 BASE_URL=${CRONPUP_URL:-https://cronpup.com} BASE_URL=${BASE_URL%/} usage() { sed -n '3,7p' "$0" 2>/dev/null | sed 's/^# \{0,1\}//' >&2 || echo "usage: cronpup run [--] " >&2 exit 64 } # monitor -> ping URL (query string kept separately so every signal carries it) resolve() { case "$1" in http://*|https://*) U=$1 ;; */*) U="$BASE_URL/p/$1" ;; *) U="$BASE_URL/p/$1" ;; esac PBASE=${U%%\?*} PQUERY=${U#"$PBASE"} PBASE=${PBASE%/} } send() { curl -fsS -m 10 --retry 3 -o /dev/null -A "cronpup-cli/$VERSION" "$@" 2>/dev/null || true; } [ $# -ge 1 ] || usage CMD=$1; shift case "$CMD" in version|--version|-v) echo "cronpup $VERSION"; exit 0 ;; help|--help|-h) usage ;; ping) [ $# -ge 1 ] || usage resolve "$1" case "${2:-}" in '') send "$PBASE$PQUERY" ;; start|fail) send "$PBASE/$2$PQUERY" ;; *[!0-9]*) echo "cronpup ping: signal must be start, fail or an exit code" >&2; exit 64 ;; *) send "$PBASE/$2$PQUERY" ;; esac exit 0 ;; run) [ $# -ge 2 ] || usage resolve "$1"; shift [ "${1:-}" = "--" ] && shift [ $# -ge 1 ] || usage send "$PBASE/start$PQUERY" LOG=$(mktemp "${TMPDIR:-/tmp}/cronpup.XXXXXX" 2>/dev/null) || LOG="" RCF="" [ -n "$LOG" ] && { RCF=$(mktemp "${TMPDIR:-/tmp}/cronpup-rc.XXXXXX" 2>/dev/null) || RCF=""; } if [ -n "$LOG" ] && [ -n "$RCF" ]; then { "$@" 2>&1; echo $? > "$RCF"; } | tee "$LOG" RC=$(cat "$RCF" 2>/dev/null) case "$RC" in ''|*[!0-9]*) RC=1 ;; esac tail -c 9000 "$LOG" | send --data-binary @- "$PBASE/$RC$PQUERY" else "$@" RC=$? send "$PBASE/$RC$PQUERY" fi [ -n "$LOG" ] && rm -f -- "$LOG" [ -n "$RCF" ] && rm -f -- "$RCF" exit "$RC" ;; *) usage ;; esac