2015-04-13 3 views
8

Spring Boot автоматически инициализирует базовую систему ведения журнала, используя LoggingApplicationListener. Это хорошая вещь, если приложение, которое я разрабатываю, работает изолированным или автономным.Spring Boot: LoggingApplicationListener, препятствующий регистрации сервера приложений

Однако я разрабатываю веб-приложение, которое будет развернуто на сервере приложений WSO2, который предлагает унифицированное ведение журнала (с использованием log4j) с такими функциями, как управление центральным журналом (во время выполнения через веб-интерфейс), бизнес-отчетность и т. Д.

Если я использую Spring Boot «как есть», он регистрирует все полностью самостоятельно. Мой первый выстрел был, чтобы удалить spring-boot-starter-logging и вручную добавить slf4j-api как provided. Это работает в некоторой степени, так как LoggingApplicationListener теперь переопределяет настройки глобального лог-менеджера, предоставляемого WSO2 (и даже вызывает закрытие глобальных приложений).

Единственное «решение», которое я придумал, состоит в том, чтобы удалить слушателя через отражение. Затем Spring Загрузочный начинает вести себя именно так, как он должен (вход через глобальную регистраторе и не перекрывая заранее определенные уровни лога, форматы, appenders и т.д.)

Это «решение» выглядит следующим образом:

@SpringBootApplication 
public class MyApp extends SpringBootServletInitializer { 

    public static void main(String... args) { 
     SpringApplication.run(MyApp.class, args); 
    } 

    @Override 
    protected SpringApplicationBuilder configure(SpringApplicationBuilder builder) { 
     try { 
      Field appField = SpringApplicationBuilder.class.getDeclaredField("application"); 
      appField.setAccessible(true); 
      SpringApplication app = (SpringApplication)appField.get(builder); 

      Field listenersField = SpringApplication.class.getDeclaredField("listeners"); 
      listenersField.setAccessible(true); 
      List<ApplicationListener<?>> listeners = (List<ApplicationListener<?>>) listenersField.get(app); 
      for (int i = listeners.size() - 1; i >= 0; --i) { 
       if (listeners.get(i) instanceof LoggingApplicationListener) { 
        listeners.remove(i); 
       } 
      } 
     } catch (NoSuchFieldException e) { 
      e.printStackTrace(); 
     } catch (IllegalAccessException e) { 
      e.printStackTrace(); 
     } 
     return builder.sources(MyApp.class); 
    } 
} 

Есть ли лучшее решение моей проблемы, возможно, менее хаки, которое я, возможно, забыл во время моего исследования и анализа кода?

ответ

2

Благодарим вас за сообщение, это очень полезно. У меня была такая же проблема с Websphere Aplication Server: после инициализации начальной загрузки весны у меня больше не было журналов. Это решение эквивалентно, но менее грязно, переопределяя метод запуска SpringBootServletInitializer:

@Override 
    protected WebApplicationContext run(SpringApplication application) { 
     Collection<ApplicationListener<?>> listeners = 
       new ArrayList<>(); 
     for (ApplicationListener<?> listener: application.getListeners()) { 
      if (!(listener instanceof LoggingApplicationListener)) { 
       listeners.add(listener); 
      } 
     } 
     application.setListeners(listeners); 
     return super.run(application); 
    } 
+0

У меня была такая же проблема с Wildfly. Большое спасибо – michaldo

+0

У меня такая же проблема. спасибо – NeptuneZ

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