RHCSA – Standard Outputs, Inputs, and Errors

Overview of standard Outputs/Inputs/Errors

By the end of this article you should be able to answer the following questions:

[expand title=”How many types of outputs can a command give out, and what are they called?” alt=” “]
Two types, They are called, “standard output” and “standard error”.
[/expand]


Standard Outputs and Standard Errors

In Linux, a command can return 2 types of outputs, they are called Standard Outputs and Standard Errors. Redirection gives you a further level of management control when redirecting Standard Outputs and Standard Errors.

The standard output is also known as Type 1) outputs. Similarly standard error outputs is known as Type 2. Standard errors, are more commonly recognized as error messages. By default all outputs, regardless of the type, are outputted to the screen. In most cases it is quite easy to identify the output type e.g.:

$ ls -l testfile.txt
ls: cannot access testfile.txt: No such file or directory

The above shows a “Standard Error” type message. A more definitive way to determine what type output a command outputted is by view a command’s “exit status”, which is stored in the special parameter, $?:

$ ls -l testfile.txt
ls: cannot access testfile.txt: No such file or directory
$ echo $?
2

If the return value is “0”, then the last command ran gave out type 1 messages. Otherwise it is a type 2 message.

$ touch testfile.txt
$ ls -l testfile.txt
-rw-r--r--. 1 root root 0 Oct 19 20:38 testfile.txt
$ echo $?
0

Note: All the available special parameters are documented in man bash, just search for “Special Parameters”

Redirection

In some cases, you might want to capture type 1 messages messages into a file. This is acheived by redirecting the standard output outputs to a file:

$ ls -l testfile.txt > info.log
$ cat info.log
-rw-r--r--. 1 root root 0 Oct 19 20:38 testfile.txt

However this doesn’t automatically redirect standard errors (type 2 outputs). That’s because the above command is an implicit version of the following command:

$ ls -l testfile 1>>info.log

The “1>>info.log” basically means only redirect type1 outputs to the file called info.log. The >> means append to this file, whereas a single > means set the content of this file. In both cases it will create the file if it doesn’t already exist.

Therefore type 2 outputs are outputed to the screen, e.g.:

$ ls -l i-dont-exits.txt > info.log
ls: cannot access i-dont-exits.txt: No such file or directory
$ echo $?
2
$ cat info.log
$

If you want to also redirect type2 outputs to the same place as type 1, then do:

$ ls -l testfile123 >info.log 2>&1

Here, “2>&1” means redirect type 2 outputs to where ever type1 outputs are being sent to

To summarise, There are actually several ways you can write the above command:

$ {command} >>info.log 2>&1
$ {command} 1>>info.log 2>>info.log
$ {command} 2>>info.log 1>&2
$ {command} 2>>info.log >&2

You can also display type1 on screen and just keep a log of type2, like this:

$ {command} 2>>info.log

Another popular option is to store type1 and type2 outputs in seperate files:

$ {command} 1>>info.log 2>>error.log

Discarding Outputs

Sometimes you might want to ignore outputs and don’t display/store them anywhere. To do this, you need to redirect the output to a special file, /dev/null. For example if you want to discard any type2 outputs, but display type1 on screen, then do:


$ {command} 2>>/dev/null

/dev/null is a special file that’s solely used for discarding outputs. It is a bit like Microsoft window’s recycle bin. Some people also refer to it as the “black hole”. Once you have sent an output to the /dev/null, thats it, you wont be able to recover it again.

Discarding type2 outputs is not a good idea, since they can be informative and can help you resolve issues. However sometimes it can be useful, such as when using the find command

Spacing doesnt matter

In the above examples we use a file called “info.log”. But it doesn’t really matter what you call the files whatever you like. e.g. you can call them log.txt, or just info
You can also specify the whole path of the file, to make sure the files are located where you want them. So instead of “info.log”, you can have them as “/tmp/info.log”
Anywhere that you see a redirection which is not preceded with a digit, e.g. ” >info.log”, then you should read this as the “1” is implied. Hence ” >info.log” can also be written as ” 1>info.log”. People often leave out the “1” because it saves them from extra typing.

Useful links

http://www.cyberciti.biz/faq/redirecting-stderr-to-stdout/
http://stackoverflow.com/questions/2342826/how-to-pipe-stderr-and-not-stdout

By default all output messages (which is 1 and 2) are sent to the standard output which is the command prompt screen. However this can be edited. Here is an example:

find / -type f -name “*.ora” 2=>/dev/null 1=>&2

This means:

2=>/dev/null : any error output messages is ignored

1=>&2 : any standard (success) output gets redirected to wherever standard error is sent to.

The following has the same effect (i.e. nothing is outputted):

find / -type f -name “*.ora” 2=>/dev/null 1=>/dev/null

You can also send error and standard info messages to different files. for example:

find / -type f -name “*.ora” 2=>error.log 1=>info.log

or

find / -type f -name “*.ora” 1=>info.log 2=>error.log

or you could leave out the “1”

find / -type f -name “*.ora” =>info.log 2=>error.log

This creates two files in the current directory and sends and saves error messages in one and info messages in the other.

Here is another example:

find / -type f -name “*.ora” =>log

This will save all success messages to the log whereas all error messages (e.g. permission denied messages) get displayed on the screen. so if you want to also save error messages to the log and not show them on screen, then you can do:

find / -type f -name “*.ora” =>log 2=>&1

or a shorthand way to write this is:

find / -type f -name “*.ora” &=>log

or

find / -type f -name “*.ora” =>log 2=>log

The above actually doesn’t work because error message overwrites success messages. The following also doesn’t work for other reasons:

find / -type f -name “*.ora” =>log 2=>=>log

The ordering of the redirection is also important, here is an example:

$ find / -type f -name “*.ora” =>/dev/null 2=>&1 | wc -l

0

Here, the first redirection is straight to null which is why all error messages are straight away ignored.

$ find / -type f -name “*.ora” 2=>&1 =>/dev/null | wc -l
160

The second command outputs error messages to screen before the redirection to null takes place.

Tip: In shell scripts, near to the top of the shell script, you can add:

exec 1>> /path/to/logfile.txt 2>&1

This means that from this point forward, all of the scripts output will get redirected to the log file.

See also:

http://www.cyberciti.biz/faq/redirecting-stderr-to-stdout/

You can also create a third file descriptor, which you can use to swap round how error and standard messages are treated, see:

http://stackoverflow.com/questions/2342826/how-to-pipe-stderr-and-not-stdout