2015-04-01 4 views
2

Я переношу некоторые веб-приложения из Log4j 1.12 в Log4j2. Из-за политики компании наши местоположения файлов log4j.xml настроены как URL-адреса на сервере приложений, и приложения должны получать их с помощью JNDI. Мы реализовали ServletContextListener, что позволило нам инициализировать log4j infraestructure таким образом:Как загрузить файл конфигурации log4j2 из JNDI

public void contextInitialized(ServletContextEvent servletContextEvent) { 
    ... 
    urlLogConfig = (URL) context.lookup("java:comp/env/"+logLocation); 
    ... 
    //urlLogConfig -> file:///somepath/log4j.xml 
    DOMConfigurator.configureAndWatch(urlLogConfig.getPath()); 
} 
public void contextDestroyed(ServletContextEvent servletContextEvent) { 
    ServletContext servletContext = servletContextEvent.getServletContext(); 
    servletContext.log("Log4jConfigurationListener - Shutting down log4j"); 
    LogManager.shutdown(); 
} 

Однако, изменяет log4j2 API это уже не может быть использована. Log4j2 предоставляет модуль lo4j2-web.jar, который использует Log4jServletContainerInitializer для инициализации библиотеки. Это заканчивается вызовом Log4jWebInitializerImpl.getConfigURI(), ответственным за получение URI файла конфигурации.

Есть ли способ настроить поведение Log4jWebInitializerImpl, чтобы он разрешил xml-файл из JNDI-имени?

ответ

0

Как о чем-то вроде:

... 
import org.apache.logging.log4j.core.config.Configurator; 
... 

    private LoggerContext loggerContext; 

    public void contextInitialized(ServletContextEvent servletContextEvent) { 
     ... 
     urlLogConfig = (URL) context.lookup("java:comp/env/"+logLocation); 
     ... 
     //urlLogConfig -> file:///somepath/log4j.xml 
     ServletContext servletContext = servletContextEvent.getServletContext(); 
     String contextName = servletContext.getServletContextName(); 
     Classloader classloader = this.getClass().getClassloader(); 
     loggerContext = Configurator.initialize(contextName, classloader, urlLogConfig.toURI()); 
    } 

    public void contextDestroyed(ServletContextEvent servletContextEvent) { 
     ServletContext servletContext = servletContextEvent.getServletContext(); 
     servletContext.log("Log4jConfigurationListener - Shutting down log4j"); 
     if (loggerContext != null) 
      Configurator.shutdown(loggerContext); 
    } 
+0

Hi Steve, ваше решение было ОК. Однако меня немного беспокоит то, что сказано здесь https://logging.apache.org/log4j/2.x/manual/webapp.html. Ресурсы Log4j не могут быть очищены обычными способами. Log4j должен быть «запущен», когда веб-приложение развертывается и «выключается», когда веб-приложение распаковывается. Знаете ли вы, что то, что вы предложили, будет правильно очищать в веб-среде? – codependent

+0

Решение, приведенное выше, не использует пакет log4j2 webapp. 'Configurator.shutdown (loggerContext) должен очистить собственные инициализированные ресурсы. –

Смежные вопросы