http-client-branch: review comment - provide a logger that can be protected with assert
--- a/src/java.net.http/share/classes/jdk/internal/net/http/common/DebugLogger.java Fri Apr 13 15:43:16 2018 +0100
+++ b/src/java.net.http/share/classes/jdk/internal/net/http/common/DebugLogger.java Fri Apr 13 16:14:15 2018 +0100
@@ -29,7 +29,6 @@
import java.util.Objects;
import java.util.ResourceBundle;
import java.util.function.Supplier;
-import java.lang.System.Logger;
/**
* A {@code System.Logger} that forwards all messages to an underlying
@@ -50,15 +49,15 @@
final static String HTTP_NAME = "jdk.internal.httpclient.debug";
final static String WS_NAME = "jdk.internal.httpclient.websocket.debug";
final static String HPACK_NAME = "jdk.internal.httpclient.hpack.debug";
- final static Logger HTTP = System.getLogger(HTTP_NAME);
- final static Logger WS = System.getLogger(WS_NAME);
- final static Logger HPACK = System.getLogger(HPACK_NAME);
+ final static System.Logger HTTP = System.getLogger(HTTP_NAME);
+ final static System.Logger WS = System.getLogger(WS_NAME);
+ final static System.Logger HPACK = System.getLogger(HPACK_NAME);
final static long START_NANOS = System.nanoTime();
private final Supplier<String> dbgTag;
private final Level errLevel;
private final Level outLevel;
- private final Logger logger;
+ private final System.Logger logger;
private final boolean debugOn;
private final boolean traceOn;
@@ -94,7 +93,7 @@
*
* @return A logger for HTTP internal debug traces
*/
- private DebugLogger(Logger logger,
+ private DebugLogger(System.Logger logger,
Supplier<String> dbgTag,
Level outLevel,
Level errLevel) {
@@ -121,6 +120,11 @@
}
@Override
+ public boolean isOn() {
+ return debugOn;
+ }
+
+ @Override
public boolean isLoggable(Level level) {
// fast path, we assume these guys never change.
// support only static configuration.
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/src/java.net.http/share/classes/jdk/internal/net/http/common/Logger.java Fri Apr 13 16:14:15 2018 +0100
@@ -0,0 +1,179 @@
+/*
+ * Copyright (c) 2018, 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 jdk.internal.net.http.common;
+
+import java.util.Objects;
+import java.util.ResourceBundle;
+import java.util.function.Supplier;
+
+/**
+ * An internal {@code System.Logger} that is used for internal
+ * debugging purposes in the {@link java.net.http} module.
+ * <p>
+ * Though not enforced, this interface is designed for emitting
+ * debug messages with Level.DEBUG, when system assertions are
+ * turned on.
+ * <p>
+ * It defines {@code log} methods that default to {@code Level.DEBUG}
+ * and always return {@code true}, so that they can be called in
+ * assert statements like:
+ * <pre>{@code assert debug.log("some %s with %d %s", message(), one(), params());}</pre>
+ *
+ * @implSpec
+ * This interface is implemented by loggers returned by
+ * {@link Utils#getDebugLogger(Supplier, boolean)},
+ * {@link Utils#getWebSocketLogger(Supplier, boolean)}and
+ * {@link Utils#getHpackLogger(Supplier, boolean)}.
+ * It is not designed to be implemented by any other
+ * loggers. Do not use outside of this module.
+ */
+public interface Logger extends System.Logger {
+ /**
+ * Tells whether this logger is on.
+ * @implSpec The default implementation for this method calls
+ * {@code this.isLoggable(Level.DEBUG);}
+ */
+ public default boolean isOn() {
+ return isLoggable(Level.DEBUG);
+ }
+
+ /**
+ * Logs a message.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, msg);}
+ *
+ * @param msg the string message (or a key in the message catalog, if
+ * this logger is a {@link
+ * System.LoggerFinder#getLocalizedLogger(java.lang.String,
+ * java.util.ResourceBundle, java.lang.Module) localized logger});
+ * can be {@code null}.
+ *
+ * @return Always return true.
+ */
+ public default boolean log(String msg) {
+ log(Level.DEBUG, msg);
+ return true;
+ }
+
+ /**
+ * Logs a lazily supplied message.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, msgSupplier);}
+ *
+ * @param msgSupplier a supplier function that produces a message.
+ *
+ * @throws NullPointerException if {@code msgSupplier} is {@code null}.
+ *
+ * @return Always return true.
+ */
+ public default boolean log(Supplier<String> msgSupplier) {
+ log(Level.DEBUG, msgSupplier);
+ return true;
+ }
+
+ /**
+ * Logs a message produced from the given object.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, obj);}
+ *
+ * @param obj the object to log.
+ *
+ * @throws NullPointerException if {@code obj} is {@code null}.
+ *
+ * @return Always return true.
+ */
+ public default boolean log(Object obj) {
+ log(Level.DEBUG, obj);
+ return true;
+ }
+
+ /**
+ * Logs a message associated with a given throwable.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, msg, thrown);}
+ *
+ * @param msg the string message (or a key in the message catalog, if
+ * this logger is a {@link
+ * System.LoggerFinder#getLocalizedLogger(java.lang.String,
+ * java.util.ResourceBundle, java.lang.Module) localized logger});
+ * can be {@code null}.
+ * @param thrown a {@code Throwable} associated with the log message;
+ * can be {@code null}.
+ *
+ * @return Always return true.
+ */
+ public default boolean log(String msg, Throwable thrown) {
+ this.log(Level.DEBUG, msg, thrown);
+ return true;
+ }
+
+ /**
+ * Logs a lazily supplied message associated with a given throwable.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, msgSupplier, thrown);}
+ *
+ * @param msgSupplier a supplier function that produces a message.
+ * @param thrown a {@code Throwable} associated with log message;
+ * can be {@code null}.
+ *
+ * @throws NullPointerException if {@code msgSupplier} is {@code null}.
+ *
+ * @return Always return true.
+ */
+ public default boolean log(Supplier<String> msgSupplier, Throwable thrown) {
+ log(Level.DEBUG, msgSupplier, thrown);
+ return true;
+ }
+
+ /**
+ * Logs a message with an optional list of parameters.
+ *
+ * @implSpec The default implementation for this method calls
+ * {@code this.log(Level.DEBUG, format, params);}
+ *
+ * @param format the string message format in
+ * {@link String#format(String, Object...)} or {@link
+ * java.text.MessageFormat} format, (or a key in the message
+ * catalog, if this logger is a {@link
+ * System.LoggerFinder#getLocalizedLogger(java.lang.String,
+ * java.util.ResourceBundle, java.lang.Module) localized logger});
+ * can be {@code null}.
+ * @param params an optional list of parameters to the message (may be
+ * none).
+ *
+ * @return Always return true.
+ */
+ public default boolean log(String format, Object... params) {
+ log(Level.DEBUG, format, params);
+ return true;
+ }
+
+}
--- a/src/java.net.http/share/classes/jdk/internal/net/http/common/Utils.java Fri Apr 13 15:43:16 2018 +0100
+++ b/src/java.net.http/share/classes/jdk/internal/net/http/common/Utils.java Fri Apr 13 16:14:15 2018 +0100
@@ -38,7 +38,6 @@
import java.io.PrintStream;
import java.io.UncheckedIOException;
import java.io.UnsupportedEncodingException;
-import java.lang.System.Logger;
import java.lang.System.Logger.Level;
import java.net.InetSocketAddress;
import java.net.URI;
@@ -767,11 +766,11 @@
* By default, this logger will forward all messages logged to an internal
* logger named "jdk.internal.httpclient.hpack.debug".
* In addition, if the message severity level is >= to
- * the provided {@code outLevel} it will print the messages on stdout.
+ * the provided {@code errLevel} it will print the messages on stderr.
* The logger will add some decoration to the printed message, in the form of
* {@code <Level>:[<thread-name>] [<elapsed-time>] <dbgTag>: <formatted message>}
*
- * @apiNote To obtain a logger that will always print things on stdout in
+ * @apiNote To obtain a logger that will always print things on stderr in
* addition to forwarding to the internal logger, use
* {@code getHpackLogger(this::dbgTag, Level.ALL);}.
* This is also equivalent to calling
@@ -783,13 +782,13 @@
*
* @param dbgTag A lambda that returns a string that identifies the caller
* (e.g: "Http2Connection(SocketTube(3))/hpack.Decoder(3)")
- * @param outLevel The level above which messages will be also printed on
- * stdout (in addition to be forwarded to the internal logger).
+ * @param errLevel The level above which messages will be also printed on
+ * stderr (in addition to be forwarded to the internal logger).
*
* @return A logger for HPACK internal debug traces
*/
- public static Logger getHpackLogger(Supplier<String> dbgTag, Level outLevel) {
- Level errLevel = Level.OFF;
+ public static Logger getHpackLogger(Supplier<String> dbgTag, Level errLevel) {
+ Level outLevel = Level.OFF;
return DebugLogger.createHpackLogger(dbgTag, outLevel, errLevel);
}
@@ -800,11 +799,11 @@
* By default, this logger will forward all messages logged to an internal
* logger named "jdk.internal.httpclient.hpack.debug".
* In addition, the provided boolean {@code on==true}, it will print the
- * messages on stdout.
+ * messages on stderr.
* The logger will add some decoration to the printed message, in the form of
* {@code <Level>:[<thread-name>] [<elapsed-time>] <dbgTag>: <formatted message>}
*
- * @apiNote To obtain a logger that will always print things on stdout in
+ * @apiNote To obtain a logger that will always print things on stderr in
* addition to forwarding to the internal logger, use
* {@code getHpackLogger(this::dbgTag, true);}.
* This is also equivalent to calling
@@ -817,13 +816,13 @@
* @param dbgTag A lambda that returns a string that identifies the caller
* (e.g: "Http2Connection(SocketTube(3))/hpack.Decoder(3)")
* @param on Whether messages should also be printed on
- * stdout (in addition to be forwarded to the internal logger).
+ * stderr (in addition to be forwarded to the internal logger).
*
* @return A logger for HPACK internal debug traces
*/
public static Logger getHpackLogger(Supplier<String> dbgTag, boolean on) {
- Level outLevel = on ? Level.ALL : Level.OFF;
- return getHpackLogger(dbgTag, outLevel);
+ Level errLevel = on ? Level.ALL : Level.OFF;
+ return getHpackLogger(dbgTag, errLevel);
}
/**