Joan Font
Joan Font

Reputation: 81

Redirect terminal stdout through command

All I want to do is just redirect the executed command's stdout to a pipe. An example will explain it better than I do.

$ echo "Hello world" | cowsay

outputs "Hello world" in cowsay, i want to preprocess terminal's / bash stdout to pass through cowsay

$ echo "Hello world"

this should output the same as the first command.

Thanks in advance.

Upvotes: 6

Views: 1014

Answers (2)

that other guy
that other guy

Reputation: 123400

You can use process substitution:

#!/bin/bash
exec >  >(cowsay)
echo "Hello world"

However, there are caveats. If you start anything in the background, the cow will wait for it to finish:

#!/bin/bash
exec >  >(cowsay)
echo "Hello world"
sleep 30 &           # Runs in the background
exit                 # Script exits immediately but no cow appears

In this case, the script will exit with no output. 30 seconds later, when sleep exits, the cow suddenly shows up.

You can fix this by telling the programs to write somewhere else, so that the cow doesn't have to wait for them:

#!/bin/bash
exec >  >(cowsay)
echo "Hello world"
sleep 30 > /dev/null & # Runs in the background and doesn't keep the cow waiting
exit                   # Script exits and the cow appears immediately.

If you don't start anything in the background, one of your tools or programs do. To find which ones, redirect or comment them out one by one until cows appear.

Upvotes: 4

Barmar
Barmar

Reputation: 780673

You can use a named pipe:

mkfifo /tmp/cowsay_pipe
cowsay < /tmp/cowsay_pipe &
exec > /tmp/cowsay_pipe # Redirect all future output to the pipe
echo "Hello world"

Upvotes: 3

Related Questions