想象這麼一個場景,一個單例bean中依賴有原型bean我們怎麼去注入?
spring中我瞭解的大致有兩種方式,一種是@Lookup依賴查找,另一種就是實現ApplicationContextAware
使用方法
@Service
@Scope("prototype")
public class UserService {
}
@Component
public class UserService2 implements ApplicationContextAware {
private ApplicationContext context;
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
this.context = applicationContext;
}
public void test(){
UserService service = context.getBean(UserService.class);
System.out.println(service);
}
}
爲什麼我們實現這個接口就能拿到ApplicationContext?
首先在spring容器啓動的時候,有添加一個ApplicationContextAwareProcessor
protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
// Configure the bean factory with context callbacks.
// 在beanFactory中添加ApplicationContextAwareProcessor,如果自定義類中有實現ApplicationContextAware就能拿到ApplicationContext
beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
}
ApplicationContextAwareProcessor是BeanPostProcessor的實現在容器初始化過程中會執行所有的BeanPostProcessor
@Override
public void refresh() throws BeansException, IllegalStateException {
// 前後代碼就刪掉了
// Invoke factory processors registered as beans in the context.
invokeBeanFactoryPostProcessors(beanFactory);
}
在ApplicationContextAwareProcessor有這麼一段,如果一個bean是ApplicationContextAware的實現,就調用它的set方法傳入spring context
private void invokeAwareInterfaces(Object bean) {
if (bean instanceof ApplicationContextAware) {
((ApplicationContextAware) bean).setApplicationContext(this.applicationContext);
}
}