bash shell-script background-process process-substitution – Wait for Bash Process Substitution Subshells

background-processbashprocess-substitutionshell-script

I pipe the same content to multiple commands with tee, redirects and process substitution subshells like this:

#!/usr/bin/env bash

echo 'hello' | tee \
  >( sleep 3; cat /dev/stdin ) \
  >( sleep 2; cat /dev/stdin ) \
  >( sleep 1; cat /dev/stdin )

wait # Doesn't work :(

However, what I see is that the process substitution subshell output is written to the terminal after the main script exits and wait doesn't work:

$ ./test.sh
hello
$ hello
hello
hello

How to properly wait for the process substitution subshells?

Best Answer

In bash, you can't wait for process substitution. In:

cmd1 > >(cmd2)

the whole command finish as soon as cmd1 finish, regardless the status of cmd2.

You have to implement a mechanism to signal the parent process that the cmd2 have finished. An easy way, using a fifo:

#!/usr/bin/env bash

trap 'rm wait.fifo' EXIT
mkfifo wait.fifo

echo 'hello' | tee \
  >( sleep 3; cat /dev/stdin; : >wait.fifo ) \
  >( sleep 2; cat /dev/stdin; : >wait.fifo ) \
  >( sleep 1; cat /dev/stdin; : >wait.fifo )

for (( i=0;i<3;i++ )); do read <wait.fifo; done
Related Question