之间的关联:SpringIocContainer | ApplicationContext | 的WebApplicationContext

The*_*ous 11 java spring spring-mvc ioc-container

背景

阅读1 2 3 4 5 6链接后我得出以下结论 -

由于Spring MVC设计了standered servlets,并促进相同的功能servlet contextapplication context.在春季存在两种类型的上下文ApplicationContextWebApplicationContext-

ApplicationContext初始化ContextLoaderListener,每个应用程序的单个实例. WebApplicationContext每个人加载DispatcherServlet.

我们可以理解上面这样ApplicationContext延伸,WebApplicationContext所以ApplicationContext最终与之相关的东西都是其中的一部分WebApplicationContext.

疑惑

  1. ApplicationContextAware提供哪个context对象.

    public class SomeThing implements ApplicationContextAware{
    @Override
    public void setApplicationContext(ApplicationContext ctx) throws BeanException{
    //this context object is `ApplicationContext` or `WebApplicationContext`?
     }
    }
    
    Run Code Online (Sandbox Code Playgroud)
  2. context并且container似乎是我们大多数人的同义词,我想举个例子.假设我们有两个调度程序servlet一个用于 rest和另一个用于mvc.

    第一个调度员 -

    public class RestInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
        @Override
        protected String[] getServletMappings() {
            return new String[] { "/rest/*" };
        }
    }
    
    Run Code Online (Sandbox Code Playgroud)

    第二个调度员 -

    public class WebAppInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {
            @Override
            protected String[] getServletMappings() {
                return new String[] { "/mvc/*" };
            }
        }
    
    Run Code Online (Sandbox Code Playgroud)

    比这里有两个实例WebApplicationContext,那些公共部分是由ContextLoaderListnerin define 加载的rootContext.

    我不确定,但一个SpringApplication中一定不能有2个IocContainer.

  3. BeanFactory即SpringIocContainer是所有bean对象存在的地方,我们关联的对象WebApplicationContext是Spring容器的一部分,这个容器是如何初始化的 WebApplicationContext?我想知道它们是如何相互关联的?

    每当我们这样做ctx.getBean()- 这会从spring容器返回对象,上下文和容器之间的这种通信是如何发生的?

它说,有一个类似的答案否认两者是相同的

Spring提供了几个容器实现,既可以加载bean定义,也可以连接bean,并根据请求分配bean,但ApplicationContext提供了更多功能.

所以我的观点是为什么加载bean定义,连接bean,这是一种返工?

还有一件事,即使web-app是弹簧驱动的,也必须有一个standard servlet在Http通信中提供和使用的上下文......

弹簧跟随这个或弹簧处理此在弹簧一些其他manner.And context指只是IOC container,其中一些部分被加载DispacherServlet并且一些部分被加载ContextLoaderListner并且可以促进更诸如I18N,access to static resource等.

mlg*_*mlg 0

基本上,在 Spring MVC 应用程序中,Spring 上下文注册在 Web 应用程序的 servlet 上下文中。您可以在web.xml设置弹簧的文件中执行此操作ContextLoaderListener中或使用 java 配置来完成此操作。在评论中,我指出了这个链接,它解释了如何通过 java 配置类完成此操作:

\n\n

spring:`@autowired`在哪里寻找bean?

\n\n

在那里您可以看到“连接”是如何完成的。然后,您在评论中询问这实现了什么:

\n\n
WebApplicationContextUtils.getWebApplicationContext(myServle\xe2\x80\x8c\xe2\x80\x8bt.getServletContext(\xe2\x80\x8c\xe2\x80\x8b))\n
Run Code Online (Sandbox Code Playgroud)\n\n

如果您检查该类的代码,您可以看到它WebApplicationContextServletContext. 这些属性是在 Web 应用程序初始化时设置的。如果您注意到,在ContextLoader班级( 的父级ContextLoaderListener)中,initWebApplicationContext方法中它将这些属性设置为 servlet 上下文:

\n\n
/**\n     * Initialize Spring\'s web application context for the given servlet context,\n     * using the application context provided at construction time, or creating a new one\n     * according to the "{@link #CONTEXT_CLASS_PARAM contextClass}" and\n     * "{@link #CONFIG_LOCATION_PARAM contextConfigLocation}" context-params.\n     * @param servletContext current servlet context\n     * @return the new WebApplicationContext\n     * @see #ContextLoader(WebApplicationContext)\n     * @see #CONTEXT_CLASS_PARAM\n     * @see #CONFIG_LOCATION_PARAM\n     */\n    public WebApplicationContext initWebApplicationContext(ServletContext servletContext) {\n        if (servletContext.getAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE) != null) {\n            throw new IllegalStateException(\n                    "Cannot initialize context because there is already a root application context present - " +\n                    "check whether you have multiple ContextLoader* definitions in your web.xml!");\n        }\n\n        Log logger = LogFactory.getLog(ContextLoader.class);\n        servletContext.log("Initializing Spring root WebApplicationContext");\n        if (logger.isInfoEnabled()) {\n            logger.info("Root WebApplicationContext: initialization started");\n        }\n        long startTime = System.currentTimeMillis();\n\n        try {\n            // Store context in local instance variable, to guarantee that\n            // it is available on ServletContext shutdown.\n            if (this.context == null) {\n                this.context = createWebApplicationContext(servletContext);\n            }\n            if (this.context instanceof ConfigurableWebApplicationContext) {\n                ConfigurableWebApplicationContext cwac = (ConfigurableWebApplicationContext) this.context;\n                if (!cwac.isActive()) {\n                    // The context has not yet been refreshed -> provide services such as\n                    // setting the parent context, setting the application context id, etc\n                    if (cwac.getParent() == null) {\n                        // The context instance was injected without an explicit parent ->\n                        // determine parent for root web application context, if any.\n                        ApplicationContext parent = loadParentContext(servletContext);\n                        cwac.setParent(parent);\n                    }\n                    configureAndRefreshWebApplicationContext(cwac, servletContext);\n                }\n            }\n            servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, this.context);\n\n            ClassLoader ccl = Thread.currentThread().getContextClassLoader();\n            if (ccl == ContextLoader.class.getClassLoader()) {\n                currentContext = this.context;\n            }\n            else if (ccl != null) {\n                currentContextPerThread.put(ccl, this.context);\n            }\n\n            if (logger.isDebugEnabled()) {\n                logger.debug("Published root WebApplicationContext as ServletContext attribute with name [" +\n                        WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE + "]");\n            }\n            if (logger.isInfoEnabled()) {\n                long elapsedTime = System.currentTimeMillis() - startTime;\n                logger.info("Root WebApplicationContext: initialization completed in " + elapsedTime + " ms");\n            }\n\n            return this.context;\n        }\n        catch (RuntimeException ex) {\n            logger.error("Context initialization failed", ex);\n            servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, ex);\n            throw ex;\n        }\n        catch (Error err) {\n            logger.error("Context initialization failed", err);\n            servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, err);\n            throw err;\n        }\n    }\n
Run Code Online (Sandbox Code Playgroud)\n\n

这是在这一行中完成的:

\n\n
servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, this.context);\n
Run Code Online (Sandbox Code Playgroud)\n\n

正如您所看到的,它存储在您尝试使用以下命令获取它的同一位置WebApplicationContextUtils.getWebApplicationContext(myServle\xe2\x80\x8c\xe2\x80\x8bt.getServletContext(\xe2\x80\x8c\xe2\x80\x8b))

\n\n
/**\n     * Find the root {@code WebApplicationContext} for this web app, typically\n     * loaded via {@link org.springframework.web.context.ContextLoaderListener}.\n     * <p>Will rethrow an exception that happened on root context startup,\n     * to differentiate between a failed context startup and no context at all.\n     * @param sc ServletContext to find the web application context for\n     * @return the root WebApplicationContext for this web app, or {@code null} if none\n     * @see org.springframework.web.context.WebApplicationContext#ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE\n     */\n    public static WebApplicationContext getWebApplicationContext(ServletContext sc) {\n        return getWebApplicationContext(sc, WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE);\n    }\n
Run Code Online (Sandbox Code Playgroud)\n\n

正如您所看到的,您的疑问的所有答案都在 spring 在 Web 应用程序启动期间执行的代码中。

\n\n

希望我回答了你的问题。

\n


归档时间:

查看次数:

936 次

最近记录:

8 年,6 月 前