Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it possible to make stdout and stderr output be of different colors in XTerm or Konsole?

Is it even achievable?

I would like the output from a command’s stderr to be rendered in a different color than stdout (for example, in red).

I need such a modification to work with the Bash shell in the Konsole, XTerm, or GNOME Terminal terminal emulators on Linux.

like image 976
DinGODzilla Avatar asked Nov 19 '09 15:11

DinGODzilla


1 Answers

Here's a solution that combines some of the good ideas already presented.

Create a function in a bash script:

color() ( set -o pipefail; "$@" 2>&1>&3 | sed $'s,.*,\e[31m&\e[m,' >&2 ) 3>&1 

Use it like this:

$ color command -program -args 

It will show the command's stderr in red.

Keep reading for an explanation of how it works. There are some interesting features demonstrated by this command.

  • color()... — Creates a bash function called color.
  • set -o pipefail — This is a shell option that preserves the error return code of a command whose output is piped into another command. This is done in a subshell, which is created by the parentheses, so as not to change the pipefail option in the outer shell.
  • "$@" — Executes the arguments to the function as a new command. "$@" is equivalent to "$1" "$2" ...
  • 2>&1 — Redirects the stderr of the command to stdout so that it becomes sed's stdin.
  • >&3 — Shorthand for 1>&3, this redirects stdout to a new temporary file descriptor 3. 3 gets routed back into stdout later.
  • sed ... — Because of the redirects above, sed's stdin is the stderr of the executed command. Its function is to surround each line with color codes.
  • $'...' A bash construct that causes it to understand backslash-escaped characters
  • .* — Matches the entire line.
  • \e[31m — The ANSI escape sequence that causes the following characters to be red
  • & — The sed replace character that expands to the entire matched string (the entire line in this case).
  • \e[m — The ANSI escape sequence that resets the color.
  • >&2 — Shorthand for 1>&2, this redirects sed's stdout to stderr.
  • 3>&1 — Redirects the temporary file descriptor 3 back into stdout.

Here's an extension of the same concept that also makes STDOUT green:

function stdred() (     set -o pipefail;     (         "$@" 2>&1>&3 |         sed $'s,.*,\e[31m&\e[m,' >&2     ) 3>&1 |     sed $'s,.*,\e[32m&\e[m,' ) 
like image 198
21 revs, 4 users 73% Avatar answered Sep 19 '22 06:09

21 revs, 4 users 73%