首先看一个重要的构造器,其中configLoaction代表着以xml形式的配置文件,用数组的形式是因为可以有多个配置文件的存在
public FileSystemXmlApplicationContext(String[] configLocations, boolean refresh, ApplicationContext parent) throws BeansException { super(parent); setConfigLocations(configLocations); if (refresh) { refresh(); } }
public void refresh() throws BeansException, IllegalStateException { synchronized (this.startupShutdownMonitor) { //获得configureableListableBeanFactory ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory(); try { //为了方便说明里面的方法给删掉了 } catch (BeansException ex) { // Destroy already created singletons to avoid dangling resources. destroyBeans(); // Reset 'active' flag. cancelRefresh(ex); // Propagate exception to caller. throw ex; } } }
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() { refreshBeanFactory();//模版方法,在子类AbstractRefreshableApplicationContext实现了beanFactory创建 ConfigurableListableBeanFactory beanFactory = getBeanFactory();//getBeanFactory是模版方法,获得了refreshBeanFacotry()里面创建的beanFacto//ry return beanFactory; }
@Override protected final void refreshBeanFactory() throws BeansException { if (hasBeanFactory()) { destroyBeans(); closeBeanFactory();//主要是讲beanFactory设置为null } try { DefaultListableBeanFactory beanFactory = createBeanFactory(); loadBeanDefinitions(beanFactory);//模版方法,在子类AbstractXmlApplicationContext,beanFactory由此传到了子类中 synchronized (this.beanFactoryMonitor) { this.beanFactory = beanFactory;//在此处创建了beanFactory } } catch (IOException ex) { throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex); } }
protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException { // Create a new XmlBeanDefinitionReader for the given BeanFactory. XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory);//最终beanFactory传到了XmlBeanDefitionReader中 loadBeanDefinitions(beanDefinitionReader); }
rotected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws BeansException, IOException { Resource[] configResources = getConfigResources();//获取resource定位 if (configResources != null) { reader.loadBeanDefinitions(configResources);//具体的载入过程,在这里实现。该方法位于 AbstractBeanDefinitionReader中 } String[] configLocations = getConfigLocations(); if (configLocations != null) { reader.loadBeanDefinitions(configLocations); } }
public int loadBeanDefinitions(Resource... resources) throws BeanDefinitionStoreException { int counter = 0; for (Resource resource : resources) { counter += loadBeanDefinitions(resource);//这是个模版方法,具体的实现在子类XmlBeanDefinitionReader 中 } return counter; }
//下面看看XmlBeanDefinitionReader中loadBeanDefitions的实现过程 public int loadBeanDefinitions(Resource resource) throws BeanDefinitionStoreException { return loadBeanDefinitions(new EncodedResource(resource));//用EncodeResouce对resource进行包装 } //其中把传来的resource传入EncodedResource类中,EncodeResource类封装了private final Resource resource; private final String encoding; public int loadBeanDefinitions(EncodedResource encodedResource) throws BeanDefinitionStoreException { Set<EncodedResource> currentResources = this.resourcesCurrentlyBeingLoaded.get(); if (currentResources == null) { currentResources = new HashSet<EncodedResource>(4); this.resourcesCurrentlyBeingLoaded.set(currentResources); } try { InputStream inputStream = encodedResource.getResource().getInputStream();//获取Resource的输入流InputStream,因为Resource继承了InputStreamSource try { InputSource inputSource = new InputSource(inputStream);//获取InputSource方法 if (encodedResource.getEncoding() != null) {//获取resource的encoding inputSource.setEncoding(encodedResource.getEncoding());//把该encoding封装到inputsource里面 } return doLoadBeanDefinitions(inputSource, encodedResource.getResource());//加载BeanDefinitions具体的实现的地方 } finally { inputStream.close(); } } catch (IOException ex) { throw new BeanDefinitionStoreException( "IOException parsing XML document from " + encodedResource.getResource(), ex); } finally { currentResources.remove(encodedResource); if (currentResources.isEmpty()) { this.resourcesCurrentlyBeingLoaded.remove(); } } } protected int doLoadBeanDefinitions(InputSource inputSource, Resource resource) throws BeanDefinitionStoreException { try { int validationMode = getValidationModeForResource(resource) Document doc = this.documentLoader.loadDocument(//把Xml封装成Document inputSource, getEntityResolver(), this.errorHandler, validationMode, isNamespaceAware()); return registerBeanDefinitions(doc, resource);//具体的注册过程 } } public int registerBeanDefinitions(Document doc, Resource resource) throws BeanDefinitionStoreException { BeanDefinitionDocumentReader documentReader = createBeanDefinitionDocumentReader(); documentReader.setEnvironment(this.getEnvironment()); int countBefore = getRegistry().getBeanDefinitionCount(); documentReader.registerBeanDefinitions(doc, createReaderContext(resource)); return getRegistry().getBeanDefinitionCount() - countBefore; }