Why does java.util.logging.Logger print to stderr?

The java.util.logging API was developed under JSR 47: Logging API Specification. According to the change log in the "Proposed Final Draft" the ConsoleHandler always used System.err. The JCP page also lists the original authors of the API and I think only those names truly know the answer to your question.

That said, I think the origin comes from System.err API docs.

Typically this stream corresponds to display output or another output destination specified by the host environment or user. By convention, this output stream is used to display error messages or other information that should come to the immediate attention of a user even if the principal output stream, the value of the variable out, has been redirected to a file or other destination that is typically not continuously monitored.

Opposed to System.out:

The "standard" output stream. This stream is already open and ready to accept output data. Typically this stream corresponds to display output or another output destination specified by the host environment or user.

Logging maps to diagnostics and not raw data. It is important to separate data from diagnostic error information especially when piping processes together as the downstream consumers are only ready to accept data information and not error messages. See Confused about stdin, stdout and stderr? for more detailed information.


It is well documented. By default, loggers publish to their parent's handlers, recursively up to the tree, until the other handler has been specified. You can loop over the parent's handlers and see that the default handler of the parent's logger is ConsoleHandler which uses System.err to publish log records.

public class Main {
    public static void main(String[] args) {
        Handler[] handlers = Logger.getLogger(Main.class.getName()).getParent().getHandlers();
        for (Handler handler : handlers) {
            System.out.println(handler.getClass().getName());
        }
    }
}