Getting Notified When Long-Running Zsh Processes Complete

| Comments

I’m always on the lookout for neat, new ideas. Back in November, I saw a neat idea over at Reddit: using Zsh hooks to trigger a notification when a command takes a long time to complete. In the comments there, I found a link to Jean-Philippe Ouellet’s excellent little script.

His script is a great fit for anyone who only uses once machine. It wasn’t very useful to me on my Linux machine. A bell going off in the terminal didn’t wake up any of the terminals that I tested. This must be the default behavior on Mac OS X.

At first, I wasn’t sure how prolific these notifications might be. I ended up adding some logging to, and I promptly forgot about it for two months. The contents of the log file looked promising, so I decided to put some more work into this.

A test zbell.zsh notification

The goal

I wanted to be notified at the completion of very long-running processes, even if I am away from my desk. I also wanted to keep the notification process very simple because I wanted it to be easy to install on servers. This was a more difficult proposition than I had expected.

Sending an email seemed like a simple idea. I quickly remembered that most residential ISPs block outgoing SMTP. This slowed me down quite a bit. My next thought was Twitter, but their new authentication process looks a bit too complicated for a simple tool like curl.

That set me looking for a simple tool that could authenticate with an SMTP server over an encrypted connection, and it would be a bonus if the tool was available in the default Centos, Ubuntu, and Debian repositories. That last bit ended up being the difficult part.

I learned something new

It turns out that curl is able to send emails! I can’t even guess how many years I’ve been using curl, and I never noticed this capability before. Not only is it readily available in every Linux distribution’s repositories, but it can also connect to my mail server using SSL/TLS.

Sending an email on port 465 using curl
curl --ssl-reqd \
  --url "smtps://" \
  --mail-from "" \
  --mail-rcpt "" \
  --user '' \
  --insecure --upload-file - &> /dev/null <<EOF &|
From: "ZSH Notification" <>
To: "Pat Regan" <>
Subject: $HOST - $zbell_lastcmd

Completed with exit status $?




Where are we now?

My changes to are still pretty quick and dirty, and they are very specific to my own machine.

I decided to set up two different timers. My fork of plays a sound and fires off a desktop notification using notify-send if a process takes longer than 60 seconds to complete. If it takes more than three minutes, it sends off an email instead.

I also used my two months of logging to pick out commands to add to the zbell_ignore list. This combination has been working out so far, but I still get notified of a command that I don’t care about every now and then.

The future

This little script is working pretty well so far, but it still needs a lot of cleanup. The notifications and noise-making parts might be pretty specific to Ubuntu. I’d like to make those more generic or detect which relevant utilities exist on the system. The email addresses and login information are hard-coded into the script. I’m going to have to move those out into variables.

Other than that, it is a usable little script already.