Append text to stderr redirects in bash Append text to stderr redirects in bash bash bash

Append text to stderr redirects in bash


This is very interesting. I've asked a guy who knows bash quite well, and he told me this way:

 foo() { while IFS='' read -r line; do echo "$(date) $line" >> file.txt; done; };

First, that creates a function reading one line of raw input from stdin, while the assignment to IFS makes it doesn't ignore blanks. Having read one line, it outputs it with the appropriate data prepended. Then you have to tell bash to redirect stderr into that function:

exec 2> >(foo)

Everything you write into stderr will now go through the foo function. Note when you do it in an interactive shell, you won't see the prompt anymore, because it's printed to stderr, and the read in foo is line buffered :)


You could simple just use:

exec 1> >( sed "s/^/$(date '+[%F %T]'): /" | tee -a ${LOGFILE}) 2>&1

This will not completely solve your Problem regarding Prompt not shown (itt will show after a short time, but not realtime, since the pipe will cache some data...), but will display the output 1:1 on stdout as well as in the file.

The only problem is, that I could not solve, is, to do this from a function, since that opens a subshell, where the exec is useless for the main program...


This example redirects stdout and stderr without loosing the original stdout and stderr. Also errors in the stdout handler are logged to the stderr handler. The file descriptors are saved in variables and closed in the child processes. Bash takes care, that no collisions occur.

#! /bin/bashstamp (){  local LINE  while IFS='' read -r LINE; do    echo "$(date '+%Y-%m-%d %H:%M:%S,%N %z') $$ $LINE"  done}exec {STDOUT}>&1exec {STDERR}>&2exec 2> >(exec {STDOUT}>&-; exec {STDERR}>&-; exec &>> stderr.log; stamp)exec > >(exec {STDOUT}>&-; exec {STDERR}>&-; exec >> stdout.log; stamp)for n in $(seq 3); do  echo loop $n >&$STDOUT  echo o$n  echo e$n >&2done

This requires a current Bash version but thanks to Shellshock one can rely on this nowadays.