18

What's the best way to suppress output (stdout and stderr) unless the program exits with a non-zero code? I'm thinking:

quiet_success()
{
  file=$(mktemp)
  if ! "$@" > "$file" 2>&1; then
    cat "$file"
  fi
  rm -f "$file"
}

And run quiet_success my_long_noisy_script.sh but I'm not sure if there's a better way. I feel like this has to be something other people have needed to do.

For context, I'm looking to add this to my cron scripts so that I get emailed with everything if they fail, but not if they don't.

  • This should be the default behavior of most commands (no output on success). If not, the first thing to do is to look for an option / switch to enable such behavior. Failing that, your approach is the right idea. Side note: I'm assuming you posted pseudo-code because it is not actually valid sh syntax, and your redirection order is backwards (do > "$file" 2>&1 and use more quotes). – jw013 Jun 22 '12 at 14:50
  • Yep, I just typed it up in the question. Applied your suggestion, and I agree, the command should be responsible for that, but alas... – dimo414 Jun 22 '12 at 14:53
  • Just a syntax note: no need for parenthesis around the command. – manatwork Jun 22 '12 at 16:27
14

You're going to have to buffer the output somewhere no matter what, since you need to wait for the exit code to know what to do. Something like this is probably easiest:

$ output=`my_long_noisy_script.sh 2>&1` || echo $output
12

The moreutils package contains a program chronic for this purpose. You just call it like

chronic my_program args ...

Very handy in cron jobs.

  • 2
    Do not be like me and mistake chronic for cronic, which is a similar program that suppresses output unless a command exists with a non-zero code or produces standard error output. – Witiko May 6 '18 at 16:10

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.