Contents
Shell and cron integration

Push notifications from shell scripts and cron

PushPiper turns any shell script or cron job into a push notification on your phone, free for 10,000 messages a month. All it takes is curl, which is already on almost every server and laptop.

Before you start

  1. Sign in at pushpiper.com/app (free, no credit card) and create an app. Its API token is your APP_TOKEN.
  2. Copy your user key from the dashboard. That's your USER_KEY.
  3. Export both in your shell profile so every script can pick them up.
~/.profile
export PUSHPIPER_TOKEN=APP_TOKEN
export PUSHPIPER_USER=USER_KEY

Send a notification

curl -sS https://api.pushpiper.com/1/messages.json \
  --form-string "token=$PUSHPIPER_TOKEN" \
  --form-string "user=$PUSHPIPER_USER" \
  --form-string "message=Backup finished"

Success returns {"status":1,"request":"..."}. --form-string sends values exactly as written, so a message that starts with @ or < isn't mistaken for a file.

Save the script as /usr/local/bin/push, run chmod +x on it, and any script on the box can call push "Disk almost full". The title defaults to the hostname. -fsS -o /dev/null keeps it silent on success, prints an error when the API says no and exits with curl's status. Prefer a function? Drop the second one into your ~/.bashrc.

Cron jobs

crontab -e
PUSHPIPER_TOKEN=APP_TOKEN
PUSHPIPER_USER=USER_KEY

# Only when the backup fails, with its exit code
30 2 * * * /usr/local/bin/backup.sh || /usr/local/bin/push "Backup failed (exit $?)" "Backup"

# Only when the sync succeeds
0 6 * * * /usr/local/bin/sync.sh && /usr/local/bin/push "Nightly sync done"

# Escape % in crontab lines
0 7 * * 1 /usr/local/bin/push "Weekly report for $(date +\%F)"

Cron runs jobs with /bin/sh and a bare environment, so use full paths and set the two variables at the top of the crontab. After ||, $? still holds the failed job's exit code, so the alert tells you how it failed.

A % in a crontab line turns into a newline, so escape it as \%, like in the date example.

Long commands, photos and emergencies

make release; push "make release finished with exit code $?"

Photos go up as multipart, up to 5 MB. Emergency alerts repeat every retry seconds (30 or more) until someone acknowledges them, for up to expire seconds (10800 at most), and the response includes a receipt. On Windows, Invoke-RestMethod sends the hashtable as a regular form post.

Useful fields

FieldExampleWhat it does
priority1From -2 (no alert) to 2 (emergency). 1 bypasses quiet hours.
soundsirenOne of the 23 built-in sounds, none included.
url, url_titlehttps://status.example.comA link under the message.
monospace1Fixed-width text for command output. Use html=1 for HTML instead, not both.
ttl3600Deletes the notification after that many seconds.
devicephoneSends to one of your devices only.

Everything else is in the API reference.

Limits and caveats

  • Sizes. Messages up to 1,024 characters, titles 250, attachments 5 MB.
  • Errors. HTTP 400 with an errors list for bad input, 429 once you're over your monthly quota. Every send response carries X-Limit-App-Limit, X-Limit-App-Remaining and X-Limit-App-Reset headers; add -i to the one-liner to see them.
  • Keys. Keep them in the environment or a file only you can read, not in scripts you commit.
  • Cron mail. The push script prints nothing on success, so it only adds to cron mail when sending fails.

Sources

Questions and answers

Do I need to install anything?

No, just curl, which ships with most Linux distributions, macOS and Windows 10 and 11. On Windows you can also use PowerShell's Invoke-RestMethod.

How do I get a push only when a cron job fails?

Chain the alert with ||, like backup.sh || push "Backup failed (exit $?)". The push only runs when the job exits with an error, and $? holds its exit code.

Can I send to several people?

Yes. Put up to 50 user keys, separated by commas, in user, or use a group key.

What happens after 10,000 messages?

The API answers HTTP 429 until your quota resets on the 1st of the month. Pro raises the limit to 50,000 messages for EUR 4 a month.