util logger how example create java logging

how - logger java import



java.util.logging.Logger no respeta java.util.logging.Level? (6)

En entorno Java SE 6 simple:

Logger l = Logger.getLogger("nameless"); l.setLevel(Level.ALL); l.fine("somemessage");

No aparece nada en la consola de Eclipse. l.info ("") y superior funcionan bien, pero cualquier cosa por debajo de la multa simplemente no parece funcionar. ¿Qué podría estar mal? TIA.


Aunque el nivel del registrador está configurado en TODO, ConsoleHandler (el controlador predeterminado en el registrador) todavía tiene un nivel predeterminado de INFO. Esto proviene del logging.properties predeterminado en JAVA_HOME / jre / lib


Debe establecer el nivel de registro tanto en los controladores en el registrador como en el registrador. El registro solo se realiza en el "más grueso" de los dos niveles. Aquí hay una clase de registro que hace el trabajo.

import java.io.PrintWriter; import java.io.StringWriter; import java.time.Instant; import java.time.ZoneId; import java.time.ZonedDateTime; import java.time.format.DateTimeFormatter; import java.util.logging.ConsoleHandler; import java.util.logging.Formatter; import java.util.logging.Handler; import java.util.logging.Level; import java.util.logging.LogRecord; import java.util.logging.Logger; public class Log { private static final Logger logger = Logger.getGlobal(); private static Level logLevel = Level.INFO; static { // Remove all the default handlers (usually just one console handler) Logger rootLogger = Logger.getLogger(""); Handler[] rootHandlers = rootLogger.getHandlers(); for (Handler handler : rootHandlers) { rootLogger.removeHandler(handler); } // Add our own handler ConsoleHandler handler = new ConsoleHandler(); handler.setLevel(logLevel); handler.setFormatter(new LogFormatter()); logger.addHandler(handler); logger.setLevel(logLevel); } public static class LogFormatter extends Formatter { @Override public String format(LogRecord record) { String stackTrace = ""; Throwable thrown = record.getThrown(); if (thrown != null) { StringWriter stacktraceWriter = new StringWriter(); try (PrintWriter writer = new PrintWriter(stacktraceWriter)) { thrown.printStackTrace(writer); } stackTrace = stacktraceWriter.toString(); } return ZonedDateTime.ofInstant(Instant.ofEpochMilli(record.getMillis()), ZoneId.of("UTC")).format(DateTimeFormatter.ISO_ZONED_DATE_TIME) + "/t" + record.getLevel() + "/t" + record.getMessage() + "/n" + stackTrace; } } private static final String classname = Log.class.getName(); private static String callerRef() { StackTraceElement[] stackTraceElements = Thread.currentThread().getStackTrace(); if (stackTraceElements.length < 4) { return ""; } else { int i = 1; for (; i < stackTraceElements.length; i++) { if (stackTraceElements[i].getClassName().equals(classname)) { break; } } for (; i < stackTraceElements.length; i++) { if (!stackTraceElements[i].getClassName().equals(classname)) { break; } } if (i < stackTraceElements.length) { return stackTraceElements[i].toString(); } else { return "[in unknown method]"; } } } public static void setLogLevel(Level newLogLevel) { logLevel = newLogLevel; for (Handler handler : logger.getHandlers()) { handler.setLevel(newLogLevel); } Log.logger.setLevel(newLogLevel); } public static int getLevelNum() { return logLevel.intValue(); } public static int getLevelNum(Level level) { return level.intValue(); } public static void fine(String msg) { logger.log(Level.FINE, msg); } public static void info(String msg) { logger.log(Level.INFO, msg); } public static void warning(String msg) { logger.log(Level.WARNING, msg + "/t " + callerRef()); } public static void error(String msg) { logger.log(Level.SEVERE, msg + "/t " + callerRef()); } public static void exception(String msg, Throwable cause) { logger.log(Level.SEVERE, msg + "/t " + callerRef(), cause); } }


En lugar de recorrer todos los controladores y establecer el nivel de registro, prefiero establecer solo el nivel del controlador de la consola:

//get the top Logger Logger topLogger = java.util.logging.Logger.getLogger(""); // Handler for console (reuse it if it already exists) Handler consoleHandler = null; //see if there is already a console handler for (Handler handler : topLogger.getHandlers()) { if (handler instanceof ConsoleHandler) { //found the console handler consoleHandler = handler; break; } } if (consoleHandler == null) { //there was no console handler found, create a new one consoleHandler = new ConsoleHandler(); topLogger.addHandler(consoleHandler); } //set the console handler to fine: consoleHandler.setLevel(java.util.logging.Level.FINEST);


Otros usuarios ya han dado una buena respuesta por qué sucedió (ConsoleHandler tiene una variable de nivel separada). Reutilizo el nivel de mi registrador de aplicaciones y lo copié en la jerarquía principal. También proporciona una manera fácil de actualizar los niveles en tiempo de ejecución en cualquier momento que desee.

// Set same level all loggers and handlers up to the parent level // OFF,SEVERE,WARNING,INFO,CONFIG,FINE,FINER,FINEST,ALL Logger logger = Logger.getLogger(this.getClass().getPackage().getName()); //Level level = Level.parse("FINEST"); Level level = logger.getLevel(); Logger tempLogger = logger; while(tempLogger != null) { tempLogger.setLevel(level); for(Handler handler : tempLogger.getHandlers()) handler.setLevel(level); tempLogger = tempLogger.getParent(); }


Un individuo en mi lugar de trabajo encontró lo siguiente para trabajar:

public class Foo { private final static Logger logger = Logger.getLogger(Foo.class.getName()); public static final void main(String[] args) { ConsoleHandler ch = new ConsoleHandler(); ch.setLevel(Level.FINEST); Foo.logger.addHandler(ch); Foo.logger.setLevel(Level.FINEST); Foo.logger.finest("test"); } }

Si acaba de establecer la raíz o el controlador en el mejor (exclusivamente), entonces no funcionó. Cuando configuro ambos en FINEST , funciona. Su explicación fue:

Tanto el registrador como sus manejadores tienen Niveles de registro ... El orden de filtrado es Logger y luego Handlers. Eso significa que verifica si el mensaje de registro pasa primero al filtro de registradores y luego envía el mensaje a los manejadores individuales para que se filtren.

Él lo explicó con los siguientes ejemplos:

  • Logger myLogger tiene un nivel de FINEST y un solo ConsoleHandler myHandler que tiene un nivel de INFO

  • myLogger.fine("foo") hace que pase el filtro del registrador, pero se detiene por el filtro del controlador ... No sale nada.

  • myLogger.info("foo") à pasa ambos filtros y foo sale.

Ahora…

  • Logger myLogger tiene un nivel de INFO y un solo ConsoleHandler myHandler que tiene un nivel de FINEST

  • myLogger.fine("foo") à mensaje se detiene por el filtro del registrador y nunca lo hace al controlador ... No sale nada.

  • myLogger.info("foo") à pasa ambos filtros y foo sale.

Ahora…

  • Logger myLogger tiene un nivel de FINEST y un solo ConsoleHandler myHandler que tiene un nivel de FINEST

  • myLogger.fine("foo") à pasa ambos filtros y se emite " foo ".

  • myLogger.info("foo") à pasa ambos filtros y foo sale.


private final static Logger LOGGER = Logger.getLogger(WoTServer.class.getName()); for(Handler h : LOGGER.getParent().getHandlers()){ if(h instanceof ConsoleHandler){ h.setLevel(Level.ALL); } }