Comment créer un Appender personnalisé dans log4j2?
comme décrit dans ce lien: comment créer un propre Appender dans log4j?
pour la création d'un appender personnalisé dans log4j 1.x nous devons étendre la classe AppenderSkeleton et implémente sa méthode d'ajout.
de même, comment nous pouvons créer un appender personnalisé dans log4j2 car nous n'avons pas la classe AppenderSkelton pour étendre et tous les autres appender étendre la classe AppenderBase .
2 réponses
cela fonctionne tout à fait différemment dans log4j2 que dans log4j-1.2.
dans log4j2, vous créeriez un plugin pour cela. Le manuel a une explication avec un exemple pour un appender personnalisé ici: http://logging.apache.org/log4j/2.x/manual/extending.html#Appenders
il peut être commode de prolonger org.apache.logging.log4j.core.appender.AbstractAppender
, mais ce n'est pas nécessaire.
lorsque vous annotez votre classe Appender personnalisé avec @Plugin(name="MyCustomAppender", ....
, le nom du plugin devient le nom de l'élément de configuration, donc une configuration avec votre appender personnalisé ressemblerait alors à ceci:
<Configuration packages="com.yourcompany.yourcustomappenderpackage">
<Appenders>
<MyCustomAppender name="ABC" otherAttribute="...">
...
</Appenders>
<Loggers><Root><AppenderRef ref="ABC" /></Root></Loggers>
</Configuration>
notez que l'attribut packages
sur la configuration est une liste séparée par des virgules de tous les paquets avec des plugins log4j2 personnalisés. Log4j2 recherchera ces paquets dans classpath pour les classes annotées avec @Plugin.
voici un exemple d'appender personnalisé qui imprime sur la console:
package com.yourcompany.yourcustomappenderpackage;
import java.io.Serializable;
import java.util.concurrent.locks.*;
import org.apache.logging.log4j.core.*;
import org.apache.logging.log4j.core.config.plugins.*;
import org.apache.logging.log4j.core.layout.PatternLayout;
// note: class name need not match the @Plugin name.
@Plugin(name="MyCustomAppender", category="Core", elementType="appender", printObject=true)
public final class MyCustomAppenderImpl extends AbstractAppender {
private final ReadWriteLock rwLock = new ReentrantReadWriteLock();
private final Lock readLock = rwLock.readLock();
protected MyCustomAppenderImpl(String name, Filter filter,
Layout<? extends Serializable> layout, final boolean ignoreExceptions) {
super(name, filter, layout, ignoreExceptions);
}
// The append method is where the appender does the work.
// Given a log event, you are free to do with it what you want.
// This example demonstrates:
// 1. Concurrency: this method may be called by multiple threads concurrently
// 2. How to use layouts
// 3. Error handling
@Override
public void append(LogEvent event) {
readLock.lock();
try {
final byte[] bytes = getLayout().toByteArray(event);
System.out.write(bytes);
} catch (Exception ex) {
if (!ignoreExceptions()) {
throw new AppenderLoggingException(ex);
}
} finally {
readLock.unlock();
}
}
// Your custom appender needs to declare a factory method
// annotated with `@PluginFactory`. Log4j will parse the configuration
// and call this factory method to construct an appender instance with
// the configured attributes.
@PluginFactory
public static MyCustomAppenderImpl createAppender(
@PluginAttribute("name") String name,
@PluginElement("Layout") Layout<? extends Serializable> layout,
@PluginElement("Filter") final Filter filter,
@PluginAttribute("otherAttribute") String otherAttribute) {
if (name == null) {
LOGGER.error("No name provided for MyCustomAppenderImpl");
return null;
}
if (layout == null) {
layout = PatternLayout.createDefaultLayout();
}
return new MyCustomAppenderImpl(name, filter, layout, true);
}
}
pour plus de détails sur les plugins: http://logging.apache.org/log4j/2.x/manual/plugins.html
si le manuel n'est pas suffisant, il peut être utile d'examiner le code source des annexes intégrées dans log4j-core.
on dirait que les Plugin appenders sont scannés au démarrage et ne peuvent pas être ajoutés pendant l'exécution. Est-ce vrai?
pour ajouter de nouveaux appender pendant l'exécution, vous pouvez utiliser la propriété monitorInterval pour mettre à jour la configuration du journal, c'est-à-dire toutes les 60 secondes:
<Configuration monitorInterval="60">