/*
* Copyright (c) 2000, 2017, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.util.logging;
import java.io.*;
import java.time.ZoneId;
import java.time.ZonedDateTime;
import jdk.internal.logger.SurrogateLogger;
Print a brief summary of the LogRecord
in a human readable format. The summary will typically be 1 or 2 lines.
Configuration: The SimpleFormatter
is initialized with the format string specified in the java.util.logging.SimpleFormatter.format
property to format the log messages. This property can be defined in the logging properties configuration file or as a system property. If this property is set in both the logging properties and system properties, the format string specified in the system property will be used. If this property is not defined or the given format string is illegal, the default format is implementation-specific.
See Also: Since: 1.4
/**
* Print a brief summary of the {@code LogRecord} in a human readable
* format. The summary will typically be 1 or 2 lines.
*
* <p>
* <a id="formatting">
* <b>Configuration:</b></a>
* The {@code SimpleFormatter} is initialized with the
* <a href="../Formatter.html#syntax">format string</a>
* specified in the {@code java.util.logging.SimpleFormatter.format}
* property to {@linkplain #format(LogRecord) format} the log messages.
* This property can be defined
* in the {@linkplain LogManager#getProperty logging properties}
* configuration file
* or as a system property. If this property is set in both
* the logging properties and system properties,
* the format string specified in the system property will be used.
* If this property is not defined or the given format string
* is {@linkplain java.util.IllegalFormatException illegal},
* the default format is implementation-specific.
*
* @since 1.4
* @see java.util.Formatter
*/
public class SimpleFormatter extends Formatter {
// format string for printing the log record
static String getLoggingProperty(String name) {
return LogManager.getLogManager().getProperty(name);
}
private final String format =
SurrogateLogger.getSimpleFormat(SimpleFormatter::getLoggingProperty);
Format the given LogRecord.
The formatting can be customized by specifying the
format string
in the java.util.logging.SimpleFormatter.format
property. The given LogRecord
will be formatted as if by calling:
String.format
(format, date, source, logger, level, message, thrown);
where the arguments are:
format
- the
java.util.Formatter
format string specified in the java.util.logging.SimpleFormatter.format
property or the default format.
date
- a ZonedDateTime
object representing event time of the log record in the ZoneId.systemDefault()
system time zone.
source
- a string representing the caller, if available; otherwise, the logger's name.
logger
- the logger's name.
level
- the
log level.
message
- the formatted log message returned from the Formatter.formatMessage(LogRecord)
method. It uses java.text
formatting and does not use the java.util.Formatter
format
argument.
thrown
- a string representing the throwable associated with the log record and its backtrace beginning with a newline character, if any; otherwise, an empty string.
Some example formats:
-
java.util.logging.SimpleFormatter.format="%4$s: %5$s [%1$tc]%n"
This prints 1 line with the log level (4$
), the log message (5$
) and the timestamp (1$
) in a square bracket.
WARNING: warning message [Tue Mar 22 13:11:31 PDT 2011]
-
java.util.logging.SimpleFormatter.format="%1$tc %2$s%n%4$s: %5$s%6$s%n"
This prints 2 lines where the first line includes the timestamp (1$
) and the source (2$
); the second line includes the log level (4$
) and the log message (5$
) followed with the throwable and its backtrace (6$
), if any:
Tue Mar 22 13:11:31 PDT 2011 MyClass fatal
SEVERE: several message with an exception
java.lang.IllegalArgumentException: invalid argument
at MyClass.mash(MyClass.java:9)
at MyClass.crunch(MyClass.java:6)
at MyClass.main(MyClass.java:3)
-
java.util.logging.SimpleFormatter.format="%1$tb %1$td, %1$tY %1$tl:%1$tM:%1$tS %1$Tp %2$s%n%4$s: %5$s%n"
This prints 2 lines similar to the example above
with a different date/time formatting and does not print
the throwable and its backtrace:
Mar 22, 2011 1:11:31 PM MyClass fatal
SEVERE: several message with an exception
-
java.util.logging.SimpleFormatter.format="%1$tb %1$td, %1$tY %1$tl:%1$tM:%1$tS.%1$tN %1$Tp %2$s%n%4$s: %5$s%6$s%n"
Since JDK 9, java.util.logging
uses java.time
to create more precise time stamps. The format above can be used to add a .%1$tN
to the date/time formatting so that nanoseconds will also be printed:
Feb 06, 2015 5:33:10.279216000 PM example.Main main
INFO: This is a test
This method can also be overridden in a subclass. It is recommended to use the Formatter.formatMessage
convenience method to localize and format the message field.
Params: - record – the log record to be formatted.
Returns: a formatted log record
/**
* Format the given LogRecord.
* <p>
* The formatting can be customized by specifying the
* <a href="../Formatter.html#syntax">format string</a>
* in the <a href="#formatting">
* {@code java.util.logging.SimpleFormatter.format}</a> property.
* The given {@code LogRecord} will be formatted as if by calling:
* <pre>
* {@link String#format String.format}(format, date, source, logger, level, message, thrown);
* </pre>
* where the arguments are:<br>
* <ol>
* <li>{@code format} - the {@link java.util.Formatter
* java.util.Formatter} format string specified in the
* {@code java.util.logging.SimpleFormatter.format} property
* or the default format.</li>
* <li>{@code date} - a {@link ZonedDateTime} object representing
* {@linkplain LogRecord#getInstant() event time} of the log record
* in the {@link ZoneId#systemDefault()} system time zone.</li>
* <li>{@code source} - a string representing the caller, if available;
* otherwise, the logger's name.</li>
* <li>{@code logger} - the logger's name.</li>
* <li>{@code level} - the {@linkplain Level#getLocalizedName
* log level}.</li>
* <li>{@code message} - the formatted log message
* returned from the {@link Formatter#formatMessage(LogRecord)}
* method. It uses {@link java.text.MessageFormat java.text}
* formatting and does not use the {@code java.util.Formatter
* format} argument.</li>
* <li>{@code thrown} - a string representing
* the {@linkplain LogRecord#getThrown throwable}
* associated with the log record and its backtrace
* beginning with a newline character, if any;
* otherwise, an empty string.</li>
* </ol>
*
* <p>Some example formats:<br>
* <ul>
* <li> {@code java.util.logging.SimpleFormatter.format="%4$s: %5$s [%1$tc]%n"}
* <p>This prints 1 line with the log level ({@code 4$}),
* the log message ({@code 5$}) and the timestamp ({@code 1$}) in
* a square bracket.
* <pre>
* WARNING: warning message [Tue Mar 22 13:11:31 PDT 2011]
* </pre></li>
* <li> {@code java.util.logging.SimpleFormatter.format="%1$tc %2$s%n%4$s: %5$s%6$s%n"}
* <p>This prints 2 lines where the first line includes
* the timestamp ({@code 1$}) and the source ({@code 2$});
* the second line includes the log level ({@code 4$}) and
* the log message ({@code 5$}) followed with the throwable
* and its backtrace ({@code 6$}), if any:
* <pre>
* Tue Mar 22 13:11:31 PDT 2011 MyClass fatal
* SEVERE: several message with an exception
* java.lang.IllegalArgumentException: invalid argument
* at MyClass.mash(MyClass.java:9)
* at MyClass.crunch(MyClass.java:6)
* at MyClass.main(MyClass.java:3)
* </pre></li>
* <li> {@code java.util.logging.SimpleFormatter.format="%1$tb %1$td, %1$tY %1$tl:%1$tM:%1$tS %1$Tp %2$s%n%4$s: %5$s%n"}
* <p>This prints 2 lines similar to the example above
* with a different date/time formatting and does not print
* the throwable and its backtrace:
* <pre>
* Mar 22, 2011 1:11:31 PM MyClass fatal
* SEVERE: several message with an exception
* </pre></li>
* <li> {@code java.util.logging.SimpleFormatter.format="%1$tb %1$td, %1$tY %1$tl:%1$tM:%1$tS.%1$tN %1$Tp %2$s%n%4$s: %5$s%6$s%n"}
* <p>Since JDK 9, {@code java.util.logging} uses {@link
* java.time.Clock#systemUTC() java.time} to create more precise time
* stamps.
* The format above can be used to add a {@code .%1$tN} to the
* date/time formatting so that nanoseconds will also be printed:
* <pre>
* Feb 06, 2015 5:33:10.279216000 PM example.Main main
* INFO: This is a test
* </pre></li>
* </ul>
* <p>This method can also be overridden in a subclass.
* It is recommended to use the {@link Formatter#formatMessage}
* convenience method to localize and format the message field.
*
* @param record the log record to be formatted.
* @return a formatted log record
*/
@Override
public String format(LogRecord record) {
ZonedDateTime zdt = ZonedDateTime.ofInstant(
record.getInstant(), ZoneId.systemDefault());
String source;
if (record.getSourceClassName() != null) {
source = record.getSourceClassName();
if (record.getSourceMethodName() != null) {
source += " " + record.getSourceMethodName();
}
} else {
source = record.getLoggerName();
}
String message = formatMessage(record);
String throwable = "";
if (record.getThrown() != null) {
StringWriter sw = new StringWriter();
PrintWriter pw = new PrintWriter(sw);
pw.println();
record.getThrown().printStackTrace(pw);
pw.close();
throwable = sw.toString();
}
return String.format(format,
zdt,
source,
record.getLoggerName(),
record.getLevel().getLocalizedLevelName(),
message,
throwable);
}
}