Cuando se usa log4j, el Logger.log(Priority p, Object message)
método está disponible y se puede usar para registrar un mensaje en un nivel de registro determinado en tiempo de ejecución. Estamos usando este hecho y este consejo para redirigir stderr a un registrador en un nivel de registro específico.
slf4j no tiene un log()
método genérico que pueda encontrar. ¿Eso significa que no hay forma de implementar lo anterior?
slf4j 2.0
. jira.qos.ch/browse/SLF4J-124 Consulte mi respuesta para obtener detalles y una posibleslf4j 1.x
solución alternativa.Respuestas:
No hay forma de hacer esto con
slf4j
.Me imagino que la razón por la que falta esta funcionalidad es que es casi imposible construir un
Level
tiposlf4j
que se pueda asignar de manera eficiente al tipoLevel
(o equivalente) utilizado en todas las posibles implementaciones de registro detrás de la fachada. Alternativamente, los diseñadores decidieron que su caso de uso es demasiado inusual para justificar los gastos generales de soportarlo.En cuanto a @ ripper234 's de casos de uso (prueba de la unidad), creo que la solución pragmática es modificar la unidad de prueba (s) para el conocimiento de alambre duro de lo que es el sistema de registro detrás de la fachada ... slf4j al ejecutar las pruebas unitarias.
fuente
org.slf4j.Logger
: debug, error, info, trace, warn.Richard Fearn tiene la idea correcta, así que escribí la clase completa basándome en su código esqueleto. Es de esperar que sea lo suficientemente corto para publicarlo aquí. Copie y pegue para disfrutar. Probablemente también debería agregar algún encantamiento mágico: "Este código es de dominio público"
fuente
Intente cambiar a Logback y use
Creo que esta será la única llamada a Logback y el resto de su código permanecerá sin cambios. Logback usa SLF4J y la migración será sencilla, solo los archivos de configuración xml deberán cambiarse.
Recuerde volver a configurar el nivel de registro una vez que haya terminado.
fuente
Puede implementar esto usando Java 8 lambdas.
fuente
LevelLogger
), lo cual no es bueno porque generalmente es información muy útil.Esto se puede hacer con un
enum
método auxiliar y uno:Puede agregar otras variantes de
log
, digamos, si desea equivalentes genéricos de 1 parámetro o 2 parámetros de SLF4Jwarn
/error
/ etc. métodos.fuente
Cualquiera que desee una solución totalmente compatible con SLF4J para este problema puede querer consultar las extensiones Lidalia SLF4J : está en Maven Central.
fuente
Solo necesitaba algo así y se me ocurrió:
uso:
El registrador se pasa durante la invocación, por lo que la información de la clase debería estar bien y funciona bien con la anotación @ Slf4j lombok.
fuente
DEBUG
falta como constante.LogLevel
como clase ylog
como método, lo que hace que los registros sean menos significativos.Es no es posible especificar un nivel de registro en sjf4j
1.x
fuera de la caja. Pero hay esperanzas de que slf4j2.0
solucione el problema . En 2.0, podría verse así:Mientras tanto, para slf4j 1.x, puede utilizar esta solución alternativa:
Copia esta clase en tu classpath:
Entonces puedes usarlo así:
Esto generará un registro como este:
¿Vale la pena?
LogLevel
El código fuente como ejemplo mínimo está alojado en GitHub .
fuente
LogMethod
interfaz debe ser pública para que funcione con clases fuera de su paquete. Aparte de eso, funciona según lo previsto. ¡Gracias!No es posible con la API slf4j cambiar dinámicamente el nivel de registro, pero puede configurar el logback (si lo usa) por su cuenta. En ese caso, cree una clase de fábrica para su registrador e implemente el registrador raíz con la configuración que necesita.
Después de configurar el registrador raíz (solo una vez es suficiente), puede delegar la obtención de un nuevo registrador por
Recuerda usar el mismo
loggerContext
.Cambiar el nivel de registro es fácil de hacer con el registrador raíz proporcionado por
loggerContext
.fuente
Confirmar respuesta Ondrej Skopek
Obtendrás resultado:
fuente
Acabo de encontrar una necesidad similar. En mi caso, slf4j está configurado con el adaptador de registro de Java (el jdk14). Usando el siguiente fragmento de código, logré cambiar el nivel de depuración en tiempo de ejecución:
fuente
Basado en la respuesta de massimo virgilio, también logré hacerlo con slf4j-log4j usando introspección. HTH.
fuente
Aquí hay una solución lambda no tan fácil de usar como la de @Paul Croarkin en un sentido (el nivel se pasa efectivamente dos veces). Pero creo que (a) el usuario debería pasar el Logger; y (b) AFAIU, la pregunta original no pedía una forma conveniente para todas las partes de la aplicación, solo una situación con pocos usos dentro de una biblioteca.
Dado que slf4j permite un Throwable (cuyo seguimiento de pila debe registrarse) dentro del parámetro varargs , creo que no hay necesidad de sobrecargar el
log
método auxiliar para otros consumidores que no sean(String, Object[])
.fuente
Pude hacer esto para el enlace JDK14 solicitando primero la instancia de SLF4J Logger y luego estableciendo el nivel en el enlace; puede probar esto para el enlace Log4J.
fuente
El método que utilizo es importar los módulos ch.qos.logback y luego convertir la instancia de slf4j Logger en un ch.qos.logback.classic.Logger. Esta instancia incluye un método setLevel ().
Para averiguar los posibles niveles de registro, puede explotar la clase ch.qos.logback para ver todos los valores posibles para el nivel :
Los resultados son los siguientes:
fuente
usando la introspección de java puede hacerlo, por ejemplo:
fuente
no, tiene varios métodos, info (), debug (), warn (), etc. (esto reemplaza el campo de prioridad)
eche un vistazo a http://www.slf4j.org/api/org/slf4j/Logger.html para obtener la API completa de Logger.
fuente