spring源碼閱讀(一) Bean加載解析準備

做爲一名java工程師,沒有閱讀過spring源碼,總有一種要被鄙視的感受,另外也想經過閱讀源碼提高本身的能力,沒有比spring更合適的了。java

那麼開始這個源碼閱讀的系列吧,參考書籍《Spring源碼深度解析》spring

2019-06-26 Spring加載的解析函數

首先咱們構建的spring例子工程this

咱們主要代碼:spa

public static void main(String args[]){
        BeanFactory context = new XmlBeanFactory(new ClassPathResource("ioc.xml"));
        Zaojiaoshu zaojiaoshu = (Zaojiaoshu) context.getBean("zaojiaoshu");
        System.out.println(zaojiaoshu.getAge() + "歲" + zaojiaoshu.getHigh() + "米");
    }

核心是這個XmlBeanFactory咱們來看下它的代碼,打開發現比較簡單:code

public class XmlBeanFactory extends DefaultListableBeanFactory {
    private final XmlBeanDefinitionReader reader;

    public XmlBeanFactory(Resource resource) throws BeansException {
        this(resource, (BeanFactory)null);
    }

    public XmlBeanFactory(Resource resource, BeanFactory parentBeanFactory) throws BeansException {
        super(parentBeanFactory);
        this.reader = new XmlBeanDefinitionReader(this);
        this.reader.loadBeanDefinitions(resource);
    }
}

那麼,構造函數裏又調用了另外一個構造函數。纔是真正的核心。那麼BeanFactory自己的結構是什麼樣的?經過代碼能夠看到主要是繼承了DefaultListableBeanFactory。來看:xml

牽扯的內容不少,有些如今不能一一說明用意,只能粗略的瞭解下先。對象

好比:blog

BeanDefinitionRegistry 提供對BeanDefinition的各類增刪改查操做。後續瞭解清楚各個組建的做用後,再來添加詳細。To do ...繼承

返回以前Main方法中繼續。建立完XmlBeanFactoryBean對象時,主要參數是Resource對象。分析下:

Resource接口是spring提供的統一的資源封裝接口,用來封裝各類底層資源。

public interface Resource extends InputStreamSource {
    boolean exists();

    boolean isReadable();

    boolean isOpen();

    URL getURL() throws IOException;

    URI getURI() throws IOException;

    File getFile() throws IOException;

    long contentLength() throws IOException;

    long lastModified() throws IOException;

    Resource createRelative(String var1) throws IOException;

    String getFilename();

    String getDescription();
}

InputStream就更簡單了。

public interface InputStreamSource {
    InputStream getInputStream() throws IOException;
}

獲取InputStream的返回對象。

能夠看到Resource接口裏,提供了文件是否存在/是否可讀/是否打開的方法,來判斷資源狀態。另外還提供了不一樣資源向URL/URI/File類型資源的轉換方法。

看下Resource的類圖結構:

爲了便於顯示,刪除了部分AbstractResource的實現類,主要用來看下類結構圖。

相關實現,就比較簡單了,查看源碼就能看到,好比ClassPathResource

public InputStream getInputStream() throws IOException {
        InputStream is;
        if (this.clazz != null) {
            is = this.clazz.getResourceAsStream(this.path);
        } else if (this.classLoader != null) {
            is = this.classLoader.getResourceAsStream(this.path);
        } else {
            is = ClassLoader.getSystemResourceAsStream(this.path);
        }

        if (is == null) {
            throw new FileNotFoundException(this.getDescription() + " cannot be opened because it does not exist");
        } else {
            return is;
        }
    }

藉助ClassLoader或者class提供了底層方法進行調用。其餘的具體查看下代碼便可。核心就是可以獲取資源的InputStream流。

講了Resource,那繼續以前方法中的代碼:加載Bean。

Todo 把當時寫在word上的內容,挪過來。

相關文章
相關標籤/搜索