2017-01-07 14 views
0
@SpringBootApplication 
public class DataProcessorApplication { 
    public static void main(String[] args) throws UnknownHostException { 
    SpringApplication app = new SpringApplication(DataProcessorApplication.class); 
    app.run(); 
} 

постпроцессор классSpring загрузки боб Исключение нулевого

@Component 
@Order(Ordered.HIGHEST_PRECEDENCE) 
public class BeanRegistryPostProcessor implements BeanDefinitionRegistryPostProcessor { 

    private static final Logger LOG = LoggerFactory.getLogger(BeanRegistryPostProcessor.class); 

    @Autowired 
    private DataConfigurationService dataConfigurationService; 

    @Override 
    public void postProcessBeanFactory(final ConfigurableListableBeanFactory factory) 
     throws BeansException { 
    // we don't want to touch existing beans 
    } 

    @Override 
    public void postProcessBeanDefinitionRegistry(final BeanDefinitionRegistry registry){ 
    dataConfigurationService.something(); // service bean is null here 
    } 
} 

Мой класс Сервис

@Service 
public class DataConfigurationService implements ApplicationListener<ApplicationReadyEvent> { 

    private static final Logger LOG = LoggerFactory.getLogger(DataConfigurationService.class); 

    @Override 
    public void onApplicationEvent(final ApplicationReadyEvent e) { 
    LOG.debug("Loading active DataConfiguration instance..."); 
    } 
} 

Исключение

java.lang.NullPointerException: null 
    at dataprocessor.configmodels.processor.BeanRegistryPostProcessor.postProcessBeanDefinitionRegistry(BeanRegistryPostProcessor.java:40) 
    at org.springframework.context.support.PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(PostProcessorRegistrationDelegate.java:118) 
    at org.springframework.context.support.AbstractApplicationContext.invokeBeanFactoryPostProcessors(AbstractApplicationContext.java:685) 
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:523) 
    at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:122) 
    at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:736) 
    at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:369) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:313) 
    at dataprocessor.DataProcessorApplication.main(DataProcessorApplication.java:47) 

2017-01-07 12:42:47.802 WARN 8880 --- [   main] ationConfigEmbeddedWebApplicationContext : Exception thrown from LifecycleProcessor on context close 

java.lang.IllegalStateException: LifecycleProcessor not initialized - call 'refresh' before invoking lifecycle methods via the context: org.springframework.boot[email protected]7a138fc5: startup date [Sat Jan 07 12:42:46 CET 2017]; root of context hierarchy 
    at org.springframework.context.support.AbstractApplicationContext.getLifecycleProcessor(AbstractApplicationContext.java:416) 
    at org.springframework.context.support.AbstractApplicationContext.doClose(AbstractApplicationContext.java:1004) 
    at org.springframework.context.support.AbstractApplicationContext.close(AbstractApplicationContext.java:963) 
    at org.springframework.boot.SpringApplication.handleRunFailure(SpringApplication.java:793) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:324) 
    at dataprocessor.DataProcessorApplication.main(DataProcessorApplication.java:47) 

2017-01-07 12:42:47.803 ERROR 8880 --- [   main] o.s.b.f.s.DefaultListableBeanFactory  : Destroy method on bean with name 'org.springframework.boot.autoconfigure.internalCachingMetadataReaderFactory' threw an exception 

java.lang.IllegalStateException: ApplicationEventMulticaster not initialized - call 'refresh' before multicasting events via the context: org.springframework.boot[email protected]7a138fc5: startup date [Sat Jan 07 12:42:46 CET 2017]; root of context hierarchy 
    at org.springframework.context.support.AbstractApplicationContext.getApplicationEventMulticaster(AbstractApplicationContext.java:403) 
    at org.springframework.context.support.ApplicationListenerDetector.postProcessBeforeDestruction(ApplicationListenerDetector.java:97) 
    at org.springframework.beans.factory.support.DisposableBeanAdapter.destroy(DisposableBeanAdapter.java:233) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.destroyBean(DefaultSingletonBeanRegistry.java:578) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.destroySingleton(DefaultSingletonBeanRegistry.java:554) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.destroySingleton(DefaultListableBeanFactory.java:951) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.destroySingletons(DefaultSingletonBeanRegistry.java:523) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.destroySingletons(DefaultListableBeanFactory.java:958) 
    at org.springframework.context.support.AbstractApplicationContext.destroyBeans(AbstractApplicationContext.java:1035) 
    at org.springframework.context.support.AbstractApplicationContext.doClose(AbstractApplicationContext.java:1011) 
    at org.springframework.context.support.AbstractApplicationContext.close(AbstractApplicationContext.java:963) 
    at org.springframework.boot.SpringApplication.handleRunFailure(SpringApplication.java:793) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:324) 
    at dataprocessor.DataProcessorApplication.main(DataProcessorApplication.java:47) 

POM

<parent> 
     <groupId>org.springframework.boot</groupId> 
     <artifactId>spring-boot-starter-parent</artifactId> 
     <version>2.0.0.BUILD-SNAPSHOT</version> 
     <relativePath /> <!-- lookup parent from repository --> 
    </parent> 

ответ

0

Пружины инициализирует контекст в следующей последовательности:

Первого, в зависимости от конфигурации приложений и автоматически обнаруженных классов (@Component, @Service и т.д.) определение фасоли будет создано и зарегистрировано в BeanDefinitionRegistry.

После этого Spring автоматически определит beans, которые реализуют BeanFactoryPostProcessor в своих определениях бобов и применяют их до того, как будут созданы другие бобы. Так как ваш BeanRegistryPostProcessor является реализацией BeanFactoryPostProcessor, он будет применяться на этом этапе.

После этого Spring автоматически определит все бобы, которые реализуют интерфейс BeanPostProcessor и применит их к любым последующим компонентам. Один из этих компонентов - AutowiredAnnotationBeanPostProcessor, который обрабатывает аннотацию @Autoware. Это означает, что на этом этапе будет введена ваша услуга.

Как вы видите, вы пытаетесь использовать бобин DataConfigurationService, прежде чем он будет введен в BeanRegistryPostProcessor. Для решения этой проблемы вы можете реализовать интерфейс ApplicationContextAware в BeanRegistryPostProcessor, а затем получить экземпляр службы непосредственно из контекста приложения:

@Component 
@Order(Ordered.HIGHEST_PRECEDENCE) 
public class BeanRegistryPostProcessor 
    implements BeanDefinitionRegistryPostProcessor, ApplicationContextAware{ 

    private ApplicationContext applicationContext; 

    ... 

    @Override 
    public void postProcessBeanDefinitionRegistry(final BeanDefinitionRegistry registry){ 
     DataConfigurationService service = applicationContext.getBean(DataConfigurationService.class); 
     service.something(); 
    } 

    @Override 
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException { 
     this.applicationContext = applicationContext;    
    } 
} 

Более подробную информацию о так называемой контейнерной Точки расширения вы можете найти в Spring documentation.

+0

Итак, если я заменил компонент на Confguration for Service, он решит проблему? –

+0

@SaurabhKumar Нет. Потому что в любом случае аннотация '@ Autowired' будет обработана ПОСЛЕ« BeanRegistryPostProcessor ». Я немного обновил ответ. –