views:

1072

answers:

7

I'm using the Enerjy (http://www.enerjy.com/) static code analyzer tool on my Java code. It tells me that the following line:

System.err.println("Ignored that database");

is bad because it uses System.err. The exact error is: "JAVA0267 Use of System.err"

What is wrong with using System.err?

+13  A: 

Short answer: It is considered a bad practice to use it for logging purposes.

It is an observation that in the old times when there where no widely available/accepted logging frameworks, everyone used System.err to print error messages and stack traces to the console. This approach might be appropriate during the development and local testing phase but is not appropriate for a production environment, because you might loose important error messages. Because of this, in almost all static analysis tools today this kind of code is detected and flagged as bad practice (or a similarly named problem).

Logging frameworks in turn provide the structured and logical way to log your events and error messages as they can store the message in various persistent locations (log file, log db, etc.).

The most obvious (and free of external dependencies) hack resolution is to use the built in Java Logging framework through the java.util.logging.Logger class as it forwards the logging events to the console by default. For example:

final Logger log = Logger.getLogger(getClass().getName());
...
log.log(Level.ERROR, "Something went wrong", theException);

(or you could just turn off that analysis option)

kd304
+1 for logging example
dfa
Additionally System.err does not include information where the message came from. You therefore depend on human readers to determine what should be done, if anything at all.
Thorbjørn Ravn Andersen
+2  A: 

System.err is really more for debugging purposes than anything else. Proper exception handling and dealing with errors in a manner that is more user-friendly is preferred. If the user is meant to see the error, use a System.out.println instead.

If you want to keep track of those errors from a developer's standpoint, you should use a logger.

AlbertoPL
+7  A: 

the descriptor of your error is:

The use of System.err may indicate residual debug or boilerplate code. Consider using a full-featured logging package such as Apache Commons to handle error logging.

It seems that you are using System.err for logging purposes, that is suboptimal for several reasons:

  • it is impossible to enable logging at runtime without modifying the application binary
  • logging behavior cannot be controlled by editing a configuration file
  • problably many others
dfa
+1  A: 

Things written to System.err are typically lost at runtime, so it is considered a better practice to use a logging framework that is more flexible about where to output the message, so it can be stored as a file and analyzed.

System.err and System.out for non-console applications is only ever seen by the developer running the code in his or her IDE, and useful information may get lost if the item is triggered in production.

Yishai
+5  A: 

Whilst I agree with the points above about using a logging framework, I still tend to use System.err output in one place: Within shut-down hooks. This is because I discovered that when using the java.util.logging framework log statements are not always displayed if they occur in shut-down hooks. This is because the logging library presumably contains its own shutdown hook to clean up log files and other resources, and as you can't rely on the order in which shutdown hooks run, you cannot rely on java.util.logging statements working as expected.

Check out this link (the "Comments" section) for more information on this.

http://weblogs.java.net/blog/dwalend/archive/2004/05/shutdown_hooks_2.html

(Obviously the other alternative is to use a different logging framework.)

Adamski
+1 its good to know, thank you. I'd rather avoid shutdown hooks in my app though.
kd304
+1  A: 

System.err.println and System.out.println should not be used as loggging-interface. STD-Output and STD-Error (these are written by System.out and .err) are for messages from command-line-tools.

Mnementh
A: 

System.err prints to the console. This may be suitable for a student testing their homework, but will be unsuitable for an application where these messages won't be seen (Console only store so many lines).

A better approach would be to throw an exception holding the message that would normally get sent to the console. An alternative to this would be use third party logging software which would store this messages in a file which can be stored forever.

ewh105