diff --git a/spring-context/src/main/java/org/springframework/context/support/AbstractApplicationContext.java b/spring-context/src/main/java/org/springframework/context/support/AbstractApplicationContext.java index cc8b2f678a..40bf4e9ea1 100644 --- a/spring-context/src/main/java/org/springframework/context/support/AbstractApplicationContext.java +++ b/spring-context/src/main/java/org/springframework/context/support/AbstractApplicationContext.java @@ -1094,24 +1094,50 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader } } + /** + * Assert that this context's BeanFactory is currently active, + * throwing an {@link IllegalStateException} if it isn't. + *

Invoked by all {@link BeanFactory} delegation methods that depend + * on an active context, i.e. in particular all bean accessor methods. + *

The default implementation checks the {@link #isActive() 'active'} status + * of this context overall. May be overridden for more specific checks, or for a + * no-op if {@link #getBeanFactory()} itself throws an exception in such a case. + */ + protected void assertBeanFactoryActive() { + synchronized (this.activeMonitor) { + if (!this.active) { + if (this.closed) { + throw new IllegalStateException(getDisplayName() + " has been closed already"); + } + else { + throw new IllegalStateException(getDisplayName() + " has not been refreshed yet"); + } + } + } + } + //--------------------------------------------------------------------- // Implementation of BeanFactory interface //--------------------------------------------------------------------- public Object getBean(String name) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBean(name); } public T getBean(String name, Class requiredType) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBean(name, requiredType); } public T getBean(Class requiredType) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBean(requiredType); } public Object getBean(String name, Object... args) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBean(name, args); } @@ -1120,18 +1146,22 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader } public boolean isSingleton(String name) throws NoSuchBeanDefinitionException { + assertBeanFactoryActive(); return getBeanFactory().isSingleton(name); } public boolean isPrototype(String name) throws NoSuchBeanDefinitionException { + assertBeanFactoryActive(); return getBeanFactory().isPrototype(name); } public boolean isTypeMatch(String name, Class targetType) throws NoSuchBeanDefinitionException { + assertBeanFactoryActive(); return getBeanFactory().isTypeMatch(name, targetType); } public Class getType(String name) throws NoSuchBeanDefinitionException { + assertBeanFactoryActive(); return getBeanFactory().getType(name); } @@ -1157,30 +1187,36 @@ public abstract class AbstractApplicationContext extends DefaultResourceLoader } public String[] getBeanNamesForType(Class type) { + assertBeanFactoryActive(); return getBeanFactory().getBeanNamesForType(type); } public String[] getBeanNamesForType(Class type, boolean includeNonSingletons, boolean allowEagerInit) { + assertBeanFactoryActive(); return getBeanFactory().getBeanNamesForType(type, includeNonSingletons, allowEagerInit); } public Map getBeansOfType(Class type) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBeansOfType(type); } public Map getBeansOfType(Class type, boolean includeNonSingletons, boolean allowEagerInit) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBeansOfType(type, includeNonSingletons, allowEagerInit); } public Map getBeansWithAnnotation(Class annotationType) throws BeansException { + assertBeanFactoryActive(); return getBeanFactory().getBeansWithAnnotation(annotationType); } public A findAnnotationOnBean(String beanName, Class annotationType) { + assertBeanFactoryActive(); return getBeanFactory().findAnnotationOnBean(beanName, annotationType); } diff --git a/spring-context/src/main/java/org/springframework/context/support/AbstractRefreshableApplicationContext.java b/spring-context/src/main/java/org/springframework/context/support/AbstractRefreshableApplicationContext.java index 44ba2589d8..9fe74c206a 100644 --- a/spring-context/src/main/java/org/springframework/context/support/AbstractRefreshableApplicationContext.java +++ b/spring-context/src/main/java/org/springframework/context/support/AbstractRefreshableApplicationContext.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2012 the original author or authors. + * Copyright 2002-2013 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -175,6 +175,13 @@ public abstract class AbstractRefreshableApplicationContext extends AbstractAppl } } + /** + * Overridden to turn it into a no-op: With AbstractRefreshableApplicationContext, + * {@link #getBeanFactory()} serves a strong assertion for an active context anyway. + */ + @Override + protected void assertBeanFactoryActive() { + } /** * Create an internal bean factory for this context. diff --git a/spring-context/src/main/java/org/springframework/context/support/StaticApplicationContext.java b/spring-context/src/main/java/org/springframework/context/support/StaticApplicationContext.java index c03f3446dc..502beff5f7 100644 --- a/spring-context/src/main/java/org/springframework/context/support/StaticApplicationContext.java +++ b/spring-context/src/main/java/org/springframework/context/support/StaticApplicationContext.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2008 the original author or authors. + * Copyright 2002-2013 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -68,6 +68,13 @@ public class StaticApplicationContext extends GenericApplicationContext { } + /** + * Overridden to turn it into a no-op, to be more lenient towards test cases. + */ + @Override + protected void assertBeanFactoryActive() { + } + /** * Return the internal StaticMessageSource used by this context. * Can be used to register messages on it. @@ -77,7 +84,6 @@ public class StaticApplicationContext extends GenericApplicationContext { return this.staticMessageSource; } - /** * Register a singleton bean with the underlying bean factory. *

For more advanced needs, register with the underlying BeanFactory directly. diff --git a/spring-webmvc/src/test/java/org/springframework/web/servlet/support/RequestContextTests.java b/spring-webmvc/src/test/java/org/springframework/web/servlet/support/RequestContextTests.java index ecde8326f6..905eae7a7c 100644 --- a/spring-webmvc/src/test/java/org/springframework/web/servlet/support/RequestContextTests.java +++ b/spring-webmvc/src/test/java/org/springframework/web/servlet/support/RequestContextTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2012 the original author or authors. + * Copyright 2002-2013 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -48,6 +48,7 @@ public class RequestContextTests { @Before public void init() { GenericWebApplicationContext applicationContext = new GenericWebApplicationContext(); + applicationContext.refresh(); servletContext.setAttribute(WebApplicationContext.ROOT_WEB_APPLICATION_CONTEXT_ATTRIBUTE, applicationContext); }