【spring】在servlet中注入spring的bean,servlet容器和spring容器


一、Servlet容器

Servlet的整個生命周期好象都是由Servlet容器來處理的。

如果把它硬放到Spring容器中去創建,Servlet對象是可被Spring容器建出來,但Servlet容器可能跟本就不知此Servlet存在,因不在它的容器中。

所以,servlet交給web server來管理,不要交給spring管理。

 

二、讓Servlet context 加載 spring context,servlet使用spring context中的對象/bean

在使用spring容器的web應用中,業務對象間的依賴關系都可以用spring-context.xml文件來配置,並且由spring容器來負責依賴對象的創建。

如果要在servlet中使用spring容器管理業務對象,通常需要使用 WebApplicationContextUtils.getRequiredWebApplicationContext(getServletContext()) 來獲得WebApplicationContext,然后調用WebApplicationContext.getBean("beanName")來獲得對象的引用,這實際上是使用了依賴查找來獲得對象,並且在servlet代碼中硬編碼了應用對象的bean名字

這種方式,相當於把spring容器中的bean加載到了servlet容器中,即把spring中的bean放到web.xml的bean中。

 

三、讓servlet感知spring中的bean

為了能在servlet中感知spring中bean,可采用如下步驟來實現:

1- 將servlet作為bean定義在spring-context.xml文件中,和要應用的bean定義放在一起;

2- 實現一個代理servlet,該servlet用WebApplicationContext來獲得在spring-context.xml中定義的servlet的對象,並將任務委托給spring-context.xml中定義的servlet

3- 在web.xml中用ContextLoaderListener來初始化spring 的context,同時在代理servlet的定義中用初始化參數來定義spring-context.xml中servlet的bean名字。

4- 在web.xml中定義代理servlet的mapping.

利用這種方式就將servlet和業務對象的依賴關系用spring 來進行管理,並且不用在servlet中硬編碼要引用的對象名字。

 

四、示例代碼

web.xml

<!-- The definition of the Root Spring Container shared by all Servlets and Filters -->
      <!-- 為了讓spring加載znserver-servlet之外的配置文件,需定義servlet監聽器ContextLoaderListener -->
    <context-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>
            /WEB-INF/server-servlet.xml
            /WEB-INF/server-bean.xml
        </param-value>
    </context-param>    
    <!-- Creates the Spring Container shared by all Servlets and Filters -->
    <!-- 與上面連起來用 ,加載spring容器
        把本地java程序不可用的bean和本地可用的分開放在不同配置文件,為了運行本地java程序-->
    <listener>
        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
    </listener>
    
    <!-- Processes application requests -->
    <!-- 處理應用的請求,/app/..下面 -->
    <servlet>
        <servlet-name>appServlet</servlet-name>
        <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
        <init-param>
            <param-name>contextConfigLocation</param-name>
            <param-value>/WEB-INF/server-bean.xml</param-value><!--server-bean.xml中要有URL處理的bean,比如Controller -->
        </init-param>
        <load-on-startup>1</load-on-startup>
    </servlet>        
    <servlet-mapping>
        <servlet-name>appServlet</servlet-name>
        <url-pattern>/</url-pattern>
    </servlet-mapping>
    
    <!-- 啟動InitialServlet,初始化應用和幾個重要對象 -->
    <servlet>
        <description></description>
        <display-name>ProxyServlet</display-name>
        <servlet-name>proxyServlet</servlet-name>
        <servlet-class>org.ccnt.med.common.DelegatingServletProxy</servlet-class>
        <load-on-startup>2</load-on-startup>
     </servlet>
     <servlet-mapping>
        <servlet-name>proxyServlet</servlet-name>
        <url-pattern>/ProxyServlet</url-pattern>
     </servlet-mapping>

server-servlet.xml

<bean id="proxyServlet" class="org.ccnt.med.common.ProxyServlet"/>

DelegatingServletProxy.java

public class DelegatingServletProxy extends GenericServlet {

    private String targetBean;
    private Servlet proxy;
    
    @Override
    public void service(ServletRequest arg0, ServletResponse arg1)
            throws ServletException, IOException {
        proxy.service(arg0, arg1);
    }

    @Override
    public void init() throws ServletException {
        this.targetBean = getServletName();
        getServletBean();
        proxy.init(getServletConfig());
    }
    
    private void getServletBean() {
        WebApplicationContext wac = WebApplicationContextUtils.getRequiredWebApplicationContext(getServletContext());
        this.proxy = (Servlet)wac.getBean(targetBean);//get proxyBean
    }
}

ProxyServlet.java

public class ProxyServlet extends HttpServlet{
    
    private Logger logger = LoggerFactory.getLogger(ProxyServlet.class);
    
    @Autowired
    private QueryService queryService;
    public void setQueryService(QueryService queryService)
    {
        this.queryService = queryService;
    }
    
    private static final long serialVersionUID = 1L;
    
    /**
     * @see HttpServlet#HttpServlet()
     */
    public ProxyServlet() {
        super();
    }
    
    /**
     * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        
    }

    /**
     * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
     */
    protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        // TODO Auto-generated method stub
    }

    @Override
    public void init(ServletConfig config) throws ServletException {
        logger.info("~~~START~~~");
    }
    
}

 

五、總結

到這都配置好了,可以放心得使用spring mvc了。回憶下流程:

1、web.xml中設置spring的listener,導入spring-context.xml。

    配置DelegatingServletProxy  servlet

2、spring-context.xml中配置bean proxyServlet

3、DelegatingServletProxy.java中,設置代理servlet--proxyServlet


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM