2015-12-04 63 views
0

我试图想出一种在应用程序启动后动态添加spring bean的方法。在运行时添加bean的春天

我发现有类似的问题了几个地方,如在here

而且我所知道的ApplicationContext的扩展点,比如ApplicationContext中的事件和BeanFactoryPostProcessor的。

我手边的问题是我需要在创建一些bean之后添加bean,我想抛弃BeanFactoryPostProcessor选项,因为它在应用程序上下文开始注册bean之前发生。

我尝试添加singletonBean情况下进行了改版后:

@EventListener 
    public void postProcess(ContextRefreshedEvent refreshedEvent) throws BeansException { 
     ConfigurableListableBeanFactory beanFactory = ((ConfigurableApplicationContext)refreshedEvent.getApplicationContext()).getBeanFactory(); 
     List<Api> apis = repository.findAll(); 
     apis.forEach(api -> { 
      api.getEndpoints().forEach(endpoint -> { 
       HttpRequestHandlingMessagingGateway gateway = createGateway(endpoint); 
       customIntegrationHandlerMapping.register(gateway); 
       beanFactory.registerSingleton("httpflow-"+endpoint.getId(),createEndpointFlow(gateway)); 
      }); 
     }); 
    } 

的问题是,IntegrationFlow取决于后处理器登记单后豆不触发。我无法在这里强制刷新。

有没有办法解决这个鸡蛋问题?

回答

1

请参阅AutowireCapableBeanFactory.initializeBean(beanName)

您需要确保注册和初始化之间没有使用bean。

另外,请注意,在上下文初始化后注册单例直到最近才真正是线程安全的(4.2.2,我认为)。如果其他代码在工厂中遍历bean,则可能会导致ConcurrentModificationExceptions

但是,在这种情况下,注册HTTP路径可能为时已晚,您可能需要更多代码才能完成此操作。