欧美一区二区三区老妇人-欧美做爰猛烈大尺度电-99久久夜色精品国产亚洲a-亚洲福利视频一区二区

究Spring3.1之無web.xml式基于代碼配置的servlet3.0應(yīng)用

       (同樣寫于11年12月20日左右的,轉(zhuǎn)導(dǎo)入此)

       大家應(yīng)該都已經(jīng)知道Spring 3.1對(duì)無web.xml式基于代碼配置的servlet3.0應(yīng)用。通過spring的api或是網(wǎng)絡(luò)上高手們的博文,也一定很快就學(xué)會(huì)并且加到自己的應(yīng)用中去了。PS:如果還沒,也可以小小參考一下鄙人的上一篇文章<<探 Spring 3.1之無web.xml式 基于代碼配置的servlet3.0應(yīng)用>>。 

      經(jīng)過一天的深度research, 我了解,理解以及重現(xiàn)了springframework的那一小段代碼。 

        OK,第一步,入手點(diǎn),WebApplicationInitializer接口。因?yàn)槲覀冎恍鑼?shí)現(xiàn)這個(gè)接口覆寫它的一個(gè)方法,就可以做到配置web.xml同樣的功效??此脑创a,其實(shí)看和不看沒什么兩樣: 

10年積累的成都網(wǎng)站制作、做網(wǎng)站經(jīng)驗(yàn),可以快速應(yīng)對(duì)客戶對(duì)網(wǎng)站的新想法和需求。提供各種問題對(duì)應(yīng)的解決方案。讓選擇我們的客戶得到更好、更有力的網(wǎng)絡(luò)服務(wù)。我雖然不認(rèn)識(shí)你,你也不認(rèn)識(shí)我。但先做網(wǎng)站后付款的網(wǎng)站建設(shè)流程,更有民樂免費(fèi)網(wǎng)站建設(shè)讓你可以放心的選擇與我們合作。

Java代碼 
  1. package org.springframework.web;  
  2.   
  3. import javax.servlet.ServletContext;  
  4. import javax.servlet.ServletException;  
  5. public interface WebApplicationInitializer {  
  6.     void onStartup(ServletContext servletContext) throws ServletException;  
  7. }  


       就這么點(diǎn)兒,有效代碼5行,弄地我一頭霧水,就是一個(gè)普通接口,聲明了一個(gè)方法。連注解都沒有,server是怎么找到實(shí)現(xiàn)了它的類的?如果這樣,何不找我定義的其它接口(的實(shí)現(xiàn)類完成配置工作)呢??梢姮F(xiàn)在java的解耦技術(shù),真令人汗顏。 


   第二步,這個(gè)接口旁邊(同包)有個(gè)SpringServletContainerInitializer, 看下它是何方神圣吧: 

Java代碼 
  1. package org.springframework.web;  
  2.   
  3. import java.lang.reflect.Modifier;  
  4. import java.util.Collections;  
  5. import java.util.LinkedList;  
  6. import java.util.List;  
  7. import java.util.ServiceLoader;  
  8. import java.util.Set;  
  9. import javax.servlet.ServletContainerInitializer;  
  10. import javax.servlet.ServletContext;  
  11. import javax.servlet.ServletException;  
  12. import javax.servlet.annotation.HandlesTypes;  
  13.   
  14. import org.springframework.core.annotation.AnnotationAwareOrderComparator;  
  15.   
  16. @HandlesTypes(WebApplicationInitializer.class)  
  17. public class SpringServletContainerInitializer implements ServletContainerInitializer {  
  18. public void onStartup(Set<Class<?>> webAppInitializerClasses, ServletContext servletContext)  
  19.             throws ServletException {  
  20.   
  21.         List<WebApplicationInitializer> initializers = new LinkedList<WebApplicationInitializer>();  
  22.         if (webAppInitializerClasses != null) {  
  23.             for (Class<?> waiClass : webAppInitializerClasses) {  
  24.                 // Be defensive: Some servlet containers provide us with invalid classes,  
  25.                 // no matter what @HandlesTypes says...  
  26.                 if (!waiClass.isInterface() && !Modifier.isAbstract(waiClass.getModifiers()) &&             WebApplicationInitializer.class.isAssignableFrom(waiClass)) {  
  27.                     try {  
  28.                         initializers.add((WebApplicationInitializer) waiClass.newInstance());  
  29.                     }  
  30.                     catch (Throwable ex) {  
  31.                         throw new ServletException("Failed to instantiate WebApplicationInitializer class", ex);  
  32.                     }  
  33.                 }  
  34.             }  
  35.         }  
  36.   
  37.         if (initializers.isEmpty()) {  
  38.             servletContext.log("No Spring WebApplicationInitializer types detected on classpath");  
  39.             return;  
  40.         }  
  41.   
  42.         Collections.sort(initializers, new AnnotationAwareOrderComparator());  
  43.         servletContext.log("Spring WebApplicationInitializers detected on classpath: " + initializers);  
  44.   
  45.         for (WebApplicationInitializer initializer : initializers) {  
  46.             initializer.onStartup(servletContext);  
  47.         }  
  48.     }  
  49.   
  50. }  



     以上的有效代碼28行。剛看時(shí)也很迷茫,其實(shí)慢慢就理解了。擬個(gè)偽代碼吧,方便大家理解: 
      1,定義一個(gè)類SpringServletContainerInitializer,并標(biāo)明該類要操作的一個(gè)類WebApplicationInitializer 
      2, 該類會(huì)行使ServletContainerInitializer接口的一個(gè)行為onStartup,從而將一個(gè)集合中的初始化設(shè)置 全部配置到ServletContext的實(shí)例中。 
      3,具體的onStartup方法中,建立合格配置列表, 
      4,如果確定集合中有配置,逐一檢查配置是否是合格配置,具體判斷依據(jù):這個(gè)類不是接口,不是抽象類,而且是所要操作的那個(gè)接口的一個(gè)實(shí)現(xiàn)類。滿足此依據(jù),合格。將合格的配置類實(shí)例化放入合格配置列表。過程中有錯(cuò)要通知控制臺(tái)。 
     5,如若執(zhí)行完步驟4,發(fā)現(xiàn)沒有合格配置,在ServletContext記錄該結(jié)果,并結(jié)束onStartup行為。 
     6,將找到配置按一定排列方式(AnnotationAwareOrder)排序。 
     7,在ServletContext中記錄找到結(jié)果。 
     8,逐一執(zhí)行配置。 即驅(qū)動(dòng)每一個(gè)WebApplicationInitializer的實(shí)現(xiàn)類行使其onStartup行為。 

     第三步很明顯了,去research 接口ServletContainerInitializer和注解HandleType。在這里:http://docs.oracle.com/javaee/6/api/javax/servlet/ServletContainerInitializer.html 

    該接口允許一個(gè)庫(kù)或運(yùn)行時(shí),(運(yùn)行時(shí)應(yīng)該指server)聲明為一個(gè)web程序的啟動(dòng)狀態(tài),并執(zhí)行任何所需的程序中注冊(cè)的servlet,filter,listener來響應(yīng)它...... 
     其它也就不用看了,可以想象得到支持Servlet3機(jī)制的服務(wù)器,會(huì)找到這樣接口的實(shí)現(xiàn)類,執(zhí)行onStartup行為。至于如何找,無非也是這樣一系列的反射機(jī)制的應(yīng)用。自己做一個(gè)試試吧: 
     自定義的WebApplicationInitializer: 

Java代碼 
  1. package com.xxxxx.p_w_picpathcapture.cfg;  
  2.   
  3. import javax.servlet.ServletContext;  
  4. import javax.servlet.ServletException;  
  5.   
  6. public interface WebParameter {  
  7.     public void loadInfo(ServletContext servletContext) throws ServletException;  
  8. }  



     自定義的ServletContainerInitializer,我做得很簡(jiǎn)單,直接去執(zhí)行找到配置類中的loadInfo方法 

Java代碼 
  1. package com.xxxxx.p_w_picpathcapture.cfg;  
  2.   
  3. import java.lang.reflect.Modifier;  
  4. import java.util.Set;  
  5.   
  6. import javax.servlet.ServletContainerInitializer;  
  7. import javax.servlet.ServletContext;  
  8. import javax.servlet.ServletException;  
  9. import javax.servlet.annotation.HandlesTypes;  
  10.   
  11. @HandlesTypes(WebParameter.class)  
  12. public class WebConfiguration implements ServletContainerInitializer {  
  13.   
  14.     @Override  
  15.     public void onStartup(Set<Class<?>> webParams, ServletContext servletCtx)  
  16.             throws ServletException {  
  17.         if (webParams != null) {  
  18.             for (Class<?> paramClass : webParams) {  
  19.                 if (!paramClass.isInterface() && !Modifier.isAbstract(paramClass.getModifiers()) &&  
  20.                         WebParameter.class.isAssignableFrom(paramClass)) {  
  21.                     try {  
  22.                         ((WebParameter) paramClass.newInstance()).loadInfo(servletCtx);  
  23.                     }  
  24.                     catch (Throwable ex) {  
  25.                         throw new ServletException("Failed to instantiate WebParam class", ex);  
  26.                     }  
  27.                 }  
  28.             }//loop  
  29.         }//Web Params  
  30.     }//onStartup  
  31.   
  32. }  


      寫個(gè)測(cè)試Servlet: 

Java代碼 
  1. package com.xxxxx.p_w_picpathcapture.ctrl;  
  2.   
  3. import java.io.IOException;  
  4.   
  5. import javax.servlet.ServletException;  
  6. import javax.servlet.http.HttpServlet;  
  7. import javax.servlet.http.HttpServletRequest;  
  8. import javax.servlet.http.HttpServletResponse;  
  9.   
  10. import com.gxino.p_w_picpathcapture.cfg.WebParameter;  
  11.   
  12. public class TestServlet extends HttpServlet {  
  13.       
  14.     public void doGet(HttpServletRequest req, HttpServletResponse resp){  
  15.         System.out.println("Some client access once");  
  16.         try {  
  17.             req.getRequestDispatcher("/index.jsp").forward(req, resp);  
  18.         } catch (ServletException | IOException e) {  
  19.             // TODO Auto-generated catch block  
  20.             e.printStackTrace();  
  21.         }  
  22.     }  
  23.       
  24. }  



       實(shí)現(xiàn)WebParam配置接口來配置剛才的Servlet: 

Java代碼 
  1. package com.xxxxx.p_w_picpathcapture.cfg;  
  2.   
  3. import javax.servlet.ServletContext;  
  4. import javax.servlet.ServletException;  
  5. import javax.servlet.ServletRegistration;  
  6.   
  7.   
  8. public class ServletParameter implements WebParameter {  
  9.   
  10.     @Override  
  11.     public void loadInfo(ServletContext servletContext) throws ServletException {  
  12.         ServletRegistration.Dynamic testServlet=servletContext.addServlet("test","com.gxino.p_w_picpathcapture.ctrl.TestServlet");  
  13.         testServlet.setLoadOnStartup(1);  
  14.         testServlet.addMapping("/index.html");  
  15.     }  
  16.   
  17. }  


        啟動(dòng)服務(wù)器,訪問http://localhost:xxxx/xxxxx/index.html 
  
     失敗。Debug. 發(fā)現(xiàn)沒有走這些代碼。應(yīng)該還差關(guān)鍵環(huán)節(jié)??磥磉€得知道Servlet3中是怎么找ServletContainerInitializer的。再回剛才ServletContainerInitializer的api有這樣一句:該接口的實(shí)現(xiàn)必須聲明一個(gè)JAR資源放到程序中的META-INF/services下,并且記有該接口那個(gè)實(shí)現(xiàn)類的全路徑,才會(huì)被運(yùn)行時(shí)(server)的查找機(jī)制或是其它特定機(jī)制找到。那篇api需要仔細(xì)閱讀啊。 


     到org.springframework.web-3.0.1.RELEASE.jar中能找到META-INF/services下的javax.servlet.ServletContainerInitializer文件,內(nèi)容為org.springframework.web.SpringServletContainerInitializer同樣,我們專門作這樣一個(gè)包,在mkdir好的META-INF/services下vi 一個(gè)文件命名為javax.servlet.ServletContainerInitializer,內(nèi)容為自定的那個(gè)WebConfiguration的全路徑類名。 然后在META-INF的parent路徑下運(yùn)行jar cvf test.jar META-INF。一切完畢,將其放到WEB-INF/lib下。啟動(dòng)。 
     
     這回大功告成。 
     
     訪問http://localhost:xxxx/xxxxx/index.html。頁面跳到了index.jsp下。 
     并且控制臺(tái)打出: Some client access once 

     再使個(gè)勁,將Servlet和Servlet配置合二為一: 

Java代碼 
  1. package com.xxxxx.p_w_picpathcapture.ctrl;  
  2.   
  3. import java.io.IOException;  
  4.   
  5. import javax.servlet.ServletContext;  
  6. import javax.servlet.ServletException;  
  7. import javax.servlet.ServletRegistration;  
  8. import javax.servlet.http.HttpServlet;  
  9. import javax.servlet.http.HttpServletRequest;  
  10. import javax.servlet.http.HttpServletResponse;  
  11.   
  12. import com.xxxxx.p_w_picpathcapture.cfg.WebParameter;  
  13.   
  14. public class TestServlet extends HttpServlet implements WebParameter{  
  15.   
  16.     @Override  
  17.     public void loadInfo(ServletContext servletContext) throws ServletException {  
  18.         ServletRegistration.Dynamic testServlet=servletContext.addServlet("test", "com.gxino.p_w_picpathcapture.ctrl.TestServlet");  
  19.         testServlet.setLoadOnStartup(1);  
  20.         testServlet.addMapping("/index.html");  
  21.     }  
  22.     public void doGet(HttpServletRequest req, HttpServletResponse resp){  
  23.         System.out.println("Some client access once");  
  24.         try {  
  25.             req.getRequestDispatcher("/index.jsp").forward(req, resp);  
  26.         } catch (ServletException | IOException e) {  
  27.             // TODO Auto-generated catch block  
  28.             e.printStackTrace();  
  29.         }  
  30.     }  
  31.       
  32. }  



這回我們看到,配置文件與servlet放到了一起。這樣將回節(jié)省大量時(shí)間。 

    以后直接運(yùn)用Spring Framework的WebApplicationInitializer也知道是怎么一回事兒了。而且可以將Spring 的applicationContext.xml與web.xml融合在一個(gè)類中。即注解為@Configuration,并實(shí)現(xiàn)WebApplicationInitializer.回頭試試。

當(dāng)前名稱:究Spring3.1之無web.xml式基于代碼配置的servlet3.0應(yīng)用
網(wǎng)站網(wǎng)址:http://chinadenli.net/article46/ppgoeg.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供營(yíng)銷型網(wǎng)站建設(shè)、商城網(wǎng)站、微信小程序自適應(yīng)網(wǎng)站、外貿(mào)網(wǎng)站建設(shè)App設(shè)計(jì)

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)

搜索引擎優(yōu)化