001/* 002 * Copyright 2002-2012 the original author or authors. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * https://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016 017package org.springframework.context.support; 018 019import java.io.IOException; 020 021import org.springframework.beans.BeansException; 022import org.springframework.beans.factory.support.DefaultListableBeanFactory; 023import org.springframework.beans.factory.xml.ResourceEntityResolver; 024import org.springframework.beans.factory.xml.XmlBeanDefinitionReader; 025import org.springframework.context.ApplicationContext; 026import org.springframework.core.io.Resource; 027 028/** 029 * Convenient base class for {@link org.springframework.context.ApplicationContext} 030 * implementations, drawing configuration from XML documents containing bean definitions 031 * understood by an {@link org.springframework.beans.factory.xml.XmlBeanDefinitionReader}. 032 * 033 * <p>Subclasses just have to implement the {@link #getConfigResources} and/or 034 * the {@link #getConfigLocations} method. Furthermore, they might override 035 * the {@link #getResourceByPath} hook to interpret relative paths in an 036 * environment-specific fashion, and/or {@link #getResourcePatternResolver} 037 * for extended pattern resolution. 038 * 039 * @author Rod Johnson 040 * @author Juergen Hoeller 041 * @see #getConfigResources 042 * @see #getConfigLocations 043 * @see org.springframework.beans.factory.xml.XmlBeanDefinitionReader 044 */ 045public abstract class AbstractXmlApplicationContext extends AbstractRefreshableConfigApplicationContext { 046 047 private boolean validating = true; 048 049 050 /** 051 * Create a new AbstractXmlApplicationContext with no parent. 052 */ 053 public AbstractXmlApplicationContext() { 054 } 055 056 /** 057 * Create a new AbstractXmlApplicationContext with the given parent context. 058 * @param parent the parent context 059 */ 060 public AbstractXmlApplicationContext(ApplicationContext parent) { 061 super(parent); 062 } 063 064 065 /** 066 * Set whether to use XML validation. Default is {@code true}. 067 */ 068 public void setValidating(boolean validating) { 069 this.validating = validating; 070 } 071 072 073 /** 074 * Loads the bean definitions via an XmlBeanDefinitionReader. 075 * @see org.springframework.beans.factory.xml.XmlBeanDefinitionReader 076 * @see #initBeanDefinitionReader 077 * @see #loadBeanDefinitions 078 */ 079 @Override 080 protected void loadBeanDefinitions(DefaultListableBeanFactory beanFactory) throws BeansException, IOException { 081 // Create a new XmlBeanDefinitionReader for the given BeanFactory. 082 XmlBeanDefinitionReader beanDefinitionReader = new XmlBeanDefinitionReader(beanFactory); 083 084 // Configure the bean definition reader with this context's 085 // resource loading environment. 086 beanDefinitionReader.setEnvironment(this.getEnvironment()); 087 beanDefinitionReader.setResourceLoader(this); 088 beanDefinitionReader.setEntityResolver(new ResourceEntityResolver(this)); 089 090 // Allow a subclass to provide custom initialization of the reader, 091 // then proceed with actually loading the bean definitions. 092 initBeanDefinitionReader(beanDefinitionReader); 093 loadBeanDefinitions(beanDefinitionReader); 094 } 095 096 /** 097 * Initialize the bean definition reader used for loading the bean 098 * definitions of this context. Default implementation is empty. 099 * <p>Can be overridden in subclasses, e.g. for turning off XML validation 100 * or using a different XmlBeanDefinitionParser implementation. 101 * @param reader the bean definition reader used by this context 102 * @see org.springframework.beans.factory.xml.XmlBeanDefinitionReader#setDocumentReaderClass 103 */ 104 protected void initBeanDefinitionReader(XmlBeanDefinitionReader reader) { 105 reader.setValidating(this.validating); 106 } 107 108 /** 109 * Load the bean definitions with the given XmlBeanDefinitionReader. 110 * <p>The lifecycle of the bean factory is handled by the {@link #refreshBeanFactory} 111 * method; hence this method is just supposed to load and/or register bean definitions. 112 * @param reader the XmlBeanDefinitionReader to use 113 * @throws BeansException in case of bean registration errors 114 * @throws IOException if the required XML document isn't found 115 * @see #refreshBeanFactory 116 * @see #getConfigLocations 117 * @see #getResources 118 * @see #getResourcePatternResolver 119 */ 120 protected void loadBeanDefinitions(XmlBeanDefinitionReader reader) throws BeansException, IOException { 121 Resource[] configResources = getConfigResources(); 122 if (configResources != null) { 123 reader.loadBeanDefinitions(configResources); 124 } 125 String[] configLocations = getConfigLocations(); 126 if (configLocations != null) { 127 reader.loadBeanDefinitions(configLocations); 128 } 129 } 130 131 /** 132 * Return an array of Resource objects, referring to the XML bean definition 133 * files that this context should be built with. 134 * <p>The default implementation returns {@code null}. Subclasses can override 135 * this to provide pre-built Resource objects rather than location Strings. 136 * @return an array of Resource objects, or {@code null} if none 137 * @see #getConfigLocations() 138 */ 139 protected Resource[] getConfigResources() { 140 return null; 141 } 142 143}