Spring ContextLoaderListener And DispatcherServlet Concepts

In Spring Web Applications, there are two types of container, each of which is configured and initialized differently. One is the "Application Context" and the other is the "Web Application Context". Lets first talk about the "Application Context". 

Application Context is the container initialized by a  ContextLoaderListener  or  ContextLoaderServlet  defined in the  web.xml  and the configuration would look something like this: 

1
2
3
4
5
6
7
8
< listener >
< listener-class >org.springframework.web.context.ContextLoaderListener</ listener-class >
</ listener >
< context-param >
< param-name >contextConfigLocation</ param-name >
< param-value >classpath:*-context.xml</ param-value >
</ context-param >

In the above configuration, I am asking spring to load all files from the classpath that match *-context.xml and create an Application Context from it. This context might, for instance, contain components such as middle-tier transactional services, data access objects, or other objects that you might want to use (and re-use) across the application. There will be one application context per application. 
The other context is the  "WebApplicationContext"  which is the child context of the application context. Each  DispatcherServlet  defined in a Spring web application will have an associated  WebApplicationContext.  The initialization of the  WebApplicationContext  happens like this: 

1
2
3
4
5
6
7
8
9
< servlet >
< servlet-name >platform-services</ servlet-name >
< servlet-class >org.springframework.web.servlet.DispatcherServlet</ servlet-class >
< init-param >
< param-name >contextConfigLocation</ param-name >
< param-value >classpath:platform-services-servlet.xml</ param-value >
</ init-param >
< load-on-startup >1</ load-on-startup >
</ servlet >

You provide the name of the spring configuration file as a servlet initialization parameter. What is important to remember here is that the name of the XML must be of the form
1
< servlet name>-servlet. xml.

In our example, the name of the servlet is  platform-services  therefore the name of our XML must be  platform-services-servlet.xml

Whatever beans are available in the ApplicationContext can be referred to from each WebApplicationContext. It is a best practice to keep a clear separation between middle-tier services such as business logic components and data access classes (that are typically defined in the ApplicationContext) and web- related components such as controllers and view resolvers (that are defined in the WebApplicationContext per Dispatcher Servlet). 

There is a list to understand ApplicationContexts and WebApplicationContexts

a.  Application-Contexts  are hierarchial and so are  WebApplicationContexts.  Refer documentation  here  

b.  ContextLoaderListener  creates a root web-application-context for the web-application and puts it in the  ServletContext.  This context can be used to load and unload the spring-managed beans ir-respective of what technology is being used in the controller layer(Struts or Spring  MVC).  

c.  DispatcherServlet  creates its own  WebApplicationContext  and the handlers/controllers/view-resolvers are managed by this context. 

d. When  ContextLoaderListener  is used in tandem with  DispatcherServlet,  a root web-application-context is created first as said earlier and a child-context is also created by  DispatcherSerlvet  and is attached to the root application-context. Refer documentation  here

Refer to the diagram below from the Spring  documentation

 

QUESTION

In official doc of  ContextLoaderListener  says it is to start  WebApplicationContext  . Regarding  WebApplicationContext  , api says  Interface to provide configuration for a web application .  But i am not able to understand what i am achieving with  ContextLoaderListener  which internally init the  WebApplicationContext  ? 

As per my understanding , ContextLoaderListener reads the spring configuration file (with value given against contextConfigLocation in web.xml), parse it and loads the singleton bean defined in that config file. Similarly when we want to load prototype bean, we will use same webapplication context to load it. So we initialize the webapplication with ContextLoaderListener so that we read/parse/validate the config file in advance and whenever we wan to inject dependency we can straightaway do it without any delay. Is this understanding correct? 

ANSWER

Your understanding is correct. The  ApplicationContext  is where your Spring beans live. The purpose of the  ContextLoaderListener  is two-fold: 

1) to tie the lifecycle of the  ApplicationContext  to the lifecycle of the  ServletContext  
2) to automate the creation of the  ApplicationContext , so you don't have to write  explicit  code to do create it - it's a convenience  function  

Another convenient thing about the  ServletContextListener  is that it creates a  WebApplicationContext  and  WebApplicationContext  provides access to the  ServletContext   ServletContextAware  beans and the  getServletContext  method. 


QUESTION

Difference between applicationContext.xml and spring-servlet.xml in Spring


Are  applicationContext.xml  and  spring-servlet.xml  related anyhow in spring framework? Will the properties files declared in  applicationContext.xml  be available to  DispatcherServlet ? On a related note, why do I need a  *-servlet.xml  at all ? Why is  applicationContext.xml  alone insufficient? 

ANSWER

Spring lets you define multiple contexts in a parent-child hierarchy. 

The  applicationContext.xml  defines the beans for the "root webapp context", i.e. the context associated with the webapp. 

The  spring-servlet.xml  (or whatever  else  you call it) defines the beans for one servlet's app context. There can be many of these in a webapp, one per Spring servlet (e.g.  spring1-servlet.xml  for servlet  spring1 spring2-servlet.xml  for servlet  spring2 ). 
Beans in  spring-servlet.xml  can reference beans in  applicationContext.xml , but not vice versa. 

All Spring  MVC  controllers must go in the  spring-servlet.xml  context. 

In most simple cases, the  applicationContext.xml  context is unnecessary. It is generally used to contain beans that are shared between all servlets in a webapp. If you only have one servlet, then there's not really much point, unless you have a specific use for it. 


QUESTION

What is the difference between ApplicationContext and WebApplicationContext in Spring MVC?


What is the difference between Application Context and Web Application Context? 

I am aware that  WebApplicationContext  is used for Spring MVC architecture oriented applications? 

I want to know what is the use of  ApplicationContext  in MVC applications? And what kind of beans are defined in  ApplicationContext


ANSWER

1
2
3
public interface WebApplicationContext extends ApplicationContext {
ServletContext getServletContext();
}

Beans, instantiated in  WebApplicationContext  will also be able to use  ServletContext  if they implement  ServletContextAware   interface  
1
2
3
4
package org.springframework.web.context;
public interface ServletContextAware extends Aware {
void setServletContext(ServletContext servletContext);
}
There many things possible to do with the  ServletContext  instance, for example accessing  WEB-INF  resources(xml configs and etc.) by calling the getResourceAsStream()  method.Typically all application contexts defined in  web.xml  in a servlet Spring application are Web Application contexts, this goes both to the root webapp context and the servlet's app context. 

Also, depending on web application context capabilities may make your application a little harder to test, and you may need to use  MockServletContext  class for testing. 

Difference between servlet and root context Spring allows you to build multilevel application context hierarchies, so the required bean will be fetched from the parent context if it's not present in the current aplication context. In web apps as default there are two hierarchy levels, root and servlet contexts: 

enter image description here  

such thing allows you to run some services as the singletons for the entire application(Spring Security beans and basic database access services typically reside here) and another as separated services in the corresponding servlets to avoid name clashes between beans. For example one servlet context will be serving the web pages and another will be implementing a stateless web service. 
This two level separation comes out of the box when you use the spring servlet classes: to configure the root application context you should use  context-param  tag in your web.xml 

1
2
3
4
5
6
7
< context-param >
< param-name >contextConfigLocation</ param-name >
< param-value >
/WEB-INF/root-context.xml
/WEB-INF/applicationContext-security.xml
</ param-value >
</ context-param >

(the root application context is created by  ContextLoaderListener  which is declared in web.xml)

1
2
3
< listener >
< listener-class >org.springframework.web.context.ContextLoaderListener</ listener-class >
</ listener >
and servlet tag for the sevlet application contexts 

1
2
3
4
5
6
7
8
< servlet >
< servlet-name >myservlet</ servlet-name >
< servlet-class >org.springframework.web.servlet.DispatcherServlet</ servlet-class >
< init-param >
< param-name >contextConfigLocation</ param-name >
< param-value >app-servlet.xml</ param-value >
</ init-param >
</ servlet >

please note that if init-param will be omitted, then spring will use myservlet-servlet.xml in this example. 
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值