讀spring源碼時發現一個有趣的現象,spring源碼的很多地方,都存在很多空方法,沒有起到任何作用。
仔細思考一下,這正是spring設計的精妙之處,這些空方法令使用者可以重寫它來實現各種各樣的玩法,所以本博客將有一個系列,專門總結這些玩法的具體實踐。文中若有錯誤,煩請指正。
1、源碼預習
在讀到ClassPathXmlApplicationContext這個類的源碼時,進入refresh方法。
public ClassPathXmlApplicationContext(String[] configLocations, boolean refresh, ApplicationContext parent)
throws BeansException {
super(parent);
setConfigLocations(configLocations);
if (refresh) {
refresh();
}
}
看到一個prepareRefresh方法,我們進入這個方法。
public void refresh() throws BeansException, IllegalStateException {
synchronized (this.startupShutdownMonitor) {
// Prepare this context for refreshing.
prepareRefresh();
......
發現initPropertySources()是個空方法,裏面沒有任何具體實現。
protected void prepareRefresh() {
this.startupDate = System.currentTimeMillis();
this.active.set(true);
if (logger.isInfoEnabled()) {
logger.info("Refreshing " + this);
}
initPropertySources();
getEnvironment().validateRequiredProperties();
}
再看看getEnviroment().validateRequiredProperties(),它的作用如下:
從集合requiredProperties中獲取環境變量的key,調用getProperty(key)通過key獲取環境變量的值,只要有一個key對應的值爲空,則拋出異常。
public void validateRequiredProperties() {
MissingRequiredPropertiesException ex = new MissingRequiredPropertiesException();
for (String key : this.requiredProperties) {
if (this.getProperty(key) == null) {
ex.addMissingRequiredProperty(key);
}
}
if (!ex.getMissingRequiredProperties().isEmpty()) {
throw ex;
}
}
我們知道prepareRefresh方法是ClassPathXmlApplicationContext加載配置文件的步驟之一。
根據上面的閱讀,我們可以來實踐了。
2、自定義系統環境變量實踐
1、新建一個繼承ClassPathXmlApplicationContext的類並重寫initPropertySource
public class MyClassPathXmlApplicationContext extends ClassPathXmlApplicationContext {
public MyClassPathXmlApplicationContext(String... configLocations) throws BeansException {
super(configLocations);
}
@Override
protected void initPropertySources() {
getEnvironment().setRequiredProperties("VAR");
}
public static void main(String[] args) {
ApplicationContext applicationContext=new MyClassPathXmlApplicationContext("applicationContext.xml");
User user= (User) applicationContext.getBean("user");
user.setName("zhangsan");
user.setAge("18");
user.speak();
}
}
先運行一下,發現拋出了異常,這是因爲我們設置了要驗證VAR變量,但我們卻沒有設置VAR系統變量。
去idea的運行配置中設置系統環境變量
重新運行,成功