#java #spring #spring-mvc #logging #spring-batch
#java #spring #spring-mvc #ведение журнала #spring-batch
Вопрос:
Мне нужно записывать сообщения в разные файлы журнала, которые должны быть созданы во время выполнения в зависимости от параметра задания, который я передаю при запуске задания. например, batch_id = 2014-07-01 и т.д.
Я наткнулся https://github.com/dsyer/log4j-utils и с помощью тестового примера https://github.com/dsyer/log4j-utils/blob/master/src/test/resources/file-dispatcher.xml пытался настроить в моем проекте spring batch admin. Ниже приведена конфигурация
<appender name="LOGGER" class="org.springframework.util.log4j.DispatcherAppender">
<param name="propertyName" value="file" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="/var/log/st/batch.log.%x" />
</layout>
<appender-ref ref="FILE" />
</appender>
<appender name="FILE" class="org.apache.log4j.FileAppender">
<param name="file" value="/var/log/st/default.log" />
<layout class="org.apache.log4j.PatternLayout">
<param name="ConversionPattern" value="%5p: %m%n" />
</layout>
</appender>
<root>
<priority value="info" />
<appender-ref ref="LOGGER" />
</root
и в моем классе я использую
import org.apache.commons.lang3.StringUtils;
import org.apache.log4j.Level;
import org.apache.log4j.Logger;
import org.apache.log4j.NDC;
public class MyClass implements MyInterface {
Logger logger = Logger.getLogger(MyClass.class);
public void run(final String command, final long timeout) throws Exception {
NDC.push("2014-07-01");
logger.info("Running " command);
}
}
Я использую этот класс для запуска команд через spring batch ItemWriter в пакетном задании spring.
Он не работает, файлы журналов не создаются, и если мы создаем вручную и предоставляем полные разрешения, в файлы журналов все равно ничего не записывается.
Ответ №1:
В настоящее время я нахожусь в процессе реализации того, что вы указали, но с другим подходом. Я определил класс JobLoggerGenerator, который создает приложение для каждого класса, который он называется следующим образом :
public static Appender getJobAppender(Class<?> class_) {
PatternLayout layout = new PatternLayout(
logProperties.getProperty("log4j.appender.LogFile.layout.ConversionPattern"));
FileAppender appender = null;
try {
// vérifier l'existance du paramétre
if (UtilBatch.chaineVide(cheminExecutionJob)) {
throw new IOException("Le chemin de depôt des fichiers est vide");
}
// vérifier et créer le dossier des traces
String cheminDepotFichTraces = UtilBatch.verifierEtCreerChemin(cheminExecutionJob, "log");
// ajouter le fichier des traces pour ce job
appender = new FileAppender(layout,
UtilBatch.creerLien(cheminDepotFichTraces, jobExecutionId "_log.log"), true);
appender.setEncoding(logProperties.getProperty("log4j.appender.LogFile.Encoding"));
} catch (Exception e) {
Logger mainLog = Logger.getLogger(class_);
mainLog.error(jobExecutionId, e);
}
return appender;
}
Затем, например, в моем классе обслуживания у меня будет объявлен объект Logger, который я изменю следующим образом :
log.addAppender(JobLoggerGenerator.getJobAppender(TestsServiceImpl.class));
Не самый тонкий подход заключается в инициализации JobExecutionId в нужное время.
В случае Spring-batchs @BeforeStep вызывается ПОСЛЕ инициализации классов @Service, поэтому метод инициализации с @PostConstruct здесь работать не будет.
Вместо этого мне нужно дополнительно изменить метод @BeforeStep, чтобы 1) инициализировать идентификатор JobExecutionId и 2) вызвать каждый сервис или класс dao, в котором мне нужно что-то зарегистрировать, чтобы добавить приложение к объекту Logger. (Мне нужно выполнить строку выше для каждой службы в основном)..
Помогает ли это вам?
Ответ №2:
Это работает для меня. В вашем коде NDC.clear(); отсутствует. Это может быть причиной того, что файл не генерируется.