天天看點

Spring IOC-Servlet加載到bean工廠

在Spring配置Servlet标簽一文中介紹了Servlet的調用以及初始化過程,在一系列的初始化過程init中加載bean的模式都是先從bean工廠得到,如果沒有那麼就加載Spring屬性檔案DispatcherServlet.properties中預設的,那麼在bean工廠中的bean是什麼時候設定進工廠的,很簡單,往下看。

先貼上繼承關系圖,好說話。

Spring IOC-Servlet加載到bean工廠

在FrameworkServlet類中有方法代碼

protected final void initServletBean() throws ServletException {
    ………………
    protected final void initServletBean() throws ServletException {
    ………………
           
protected WebApplicationContext initWebApplicationContext() {
    // A context instance was injected at construction time -> use it
   //一個context在初始化的時候被注入                                            
   wac = this.webApplicationContext;  
   if (wac instanceof ConfigurableWebApplicationContext) {
   ………………
     configureAndRefreshWebApplicationContext(cwac);
   ………………
   ////等于空,加載配置檔案然後重新整理                                        
   if (wac == null) {                                        
    // No context instance is defined for this servlet -> 
    //就是說下面的代碼是一定會初始化一個的,并且加載配置檔案                         
    wac = createWebApplicationContext(rootContext); 
    ………………                                 
           

下面看createWebApplicationContext()中的代碼。

………………
//用反射執行個體化一個                                                                           
ConfigurableWebApplicationContext wac =                                              
        (ConfigurableWebApplicationContext) BeanUtils.instantiateClass(contextClass);

wac.setParent(parent);                                                               
//重新設定配置檔案路徑,然後會重新整理。在listener中其實已經設定一次了,那時候已經重新整理路徑了加載bean了                             
//相當于每次該配置都要重新啟動工程                                                                   
wac.setConfigLocation(getContextConfigLocation());//參數配置的xml路徑                       

configureAndRefreshWebApplicationContext(wac);                                       
………………
           

注意上面的代碼

wac.setConfigLocation(getContextConfigLocation());

這回加載你的配置檔案,一般都是類似xxx-servlet.xml的檔案,在檔案中你既可以用傳統過的标簽定義bean,也可以簡單的聲明幾行代碼告訴Spring用的是注解的方式。

通過上面的代碼,很自然的我們轉到configureAndRefreshWebApplicationContext方法。關鍵代碼如下:

wac.setServletContext(getServletContext());                                                
wac.setServletConfig(getServletConfig());                                                  
wac.setNamespace(getNamespace());                                                          
//添加監聽器,org.springframework.context.event.SourceFilteringListener                          
wac.addApplicationListener(new SourceFilteringListener(wac, new ContextRefreshListener()));                                                                                          
postProcessWebApplicationContext(wac);                                                                                                                                                
applyInitializers(wac);                                                                                                                                                               
wac.refresh();                                                                             
           

好了,終于見到這行代碼了

wac.refresh();

,為什麼這麼說那,因為這行代碼就是WebApplicationContext的更新過程,這個更新過程的背景有一系列的複雜的但是很有調理的bean的裝配、加載以及部分bean的初始化過程。

詳細的介紹在《Spring IOC-WebApplicationContext重新整理》

繼續閱讀