M1 cut of environment, profiles and property work (SPR-7508)
Decomposed Environment interface into PropertySources, PropertyResolver
objects
Environment interface and implementations are still present, but
simpler.
PropertySources container aggregates PropertySource objects;
PropertyResolver provides search, conversion, placeholder
replacement. Single implementation for now is
PropertySourcesPlaceholderResolver
Renamed EnvironmentAwarePropertyPlaceholderConfigurer to
PropertySourcesPlaceholderConfigurer
<context:property-placeholder/> now registers PSPC by default, else
PPC if systemPropertiesMode* settings are involved
Refined configuration and behavior of default profiles
See Environment interface Javadoc for details
Added Portlet implementations of relevant interfaces:
* DefaultPortletEnvironment
* PortletConfigPropertySource, PortletContextPropertySource
* Integrated each appropriately throughout Portlet app contexts
Added protected 'createEnvironment()' method to AbstractApplicationContext
Subclasses can override at will to supply a custom Environment
implementation. In practice throughout the framework, this is how
Web- and Portlet-related ApplicationContexts override use of the
DefaultEnvironment and swap in DefaultWebEnvironment or
DefaultPortletEnvironment as appropriate.
Introduced "stub-and-replace" behavior for Servlet- and Portlet-based
PropertySource implementations
Allows for early registration and ordering of the stub, then
replacement with actual backing object at refresh() time.
Added AbstractApplicationContext.initPropertySources() method to
support stub-and-replace behavior. Called from within existing
prepareRefresh() method so as to avoid impact with
ApplicationContext implementations that copy and modify AAC's
refresh() method (e.g.: Spring DM).
Added methods to WebApplicationContextUtils and
PortletApplicationContextUtils to support stub-and-replace behavior
Added comprehensive Javadoc for all new or modified types and members
Added XSD documentation for all new or modified elements and attributes
Including nested <beans>, <beans profile="..."/>, and changes for
certain attributes type from xsd:IDREF to xsd:string
Improved fix for detecting non-file based Resources in
PropertiesLoaderSupport (SPR-7547, SPR-7552)
Technically unrelated to environment work, but grouped in with
this changeset for convenience.
Deprecated (removed) context:property-placeholder
'system-properties-mode' attribute from spring-context-3.1.xsd
Functionality is preserved for those using schemas up to and including
spring-context-3.0. For 3.1, system-properties-mode is no longer
supported as it conflicts with the idea of managing a set of property
sources within the context's Environment object. See Javadoc in
PropertyPlaceholderConfigurer, AbstractPropertyPlaceholderConfigurer
and PropertySourcesPlaceholderConfigurer for details.
Introduced CollectionUtils.toArray(Enumeration<E>, A[])
Work items remaining for 3.1 M2:
Consider repackaging PropertySource* types; eliminate internal use
of SystemPropertyUtils and deprecate
Further work on composition of Environment interface; consider
repurposing existing PlaceholderResolver interface to obviate need
for resolve[Required]Placeholder() methods currently in Environment.
Ensure configurability of placeholder prefix, suffix, and value
separator when working against an AbstractPropertyResolver
Add JNDI-based Environment / PropertySource implementatinos
Consider support for @Profile at the @Bean level
Provide consistent logging for the entire property resolution
lifecycle; consider issuing all such messages against a dedicated
logger with a single category.
Add reference documentation to cover the featureset.
This commit is contained in:
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Copyright 2002-2010 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package example.profilescan;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
import org.springframework.context.annotation.Profile;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.TYPE)
|
||||
@Profile(DevComponent.PROFILE_NAME)
|
||||
@Component
|
||||
public @interface DevComponent {
|
||||
|
||||
public static final String PROFILE_NAME = "dev";
|
||||
|
||||
String value() default "";
|
||||
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright 2002-2010 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package example.profilescan;
|
||||
|
||||
|
||||
@DevComponent(ProfileMetaAnnotatedComponent.BEAN_NAME)
|
||||
public class ProfileMetaAnnotatedComponent {
|
||||
|
||||
public static final String BEAN_NAME = "profileMetaAnnotatedComponent";
|
||||
|
||||
}
|
||||
@@ -39,7 +39,9 @@ import org.springframework.stereotype.Controller;
|
||||
import org.springframework.stereotype.Repository;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import example.profilescan.DevComponent;
|
||||
import example.profilescan.ProfileAnnotatedComponent;
|
||||
import example.profilescan.ProfileMetaAnnotatedComponent;
|
||||
import example.scannable.FooDao;
|
||||
import example.scannable.FooService;
|
||||
import example.scannable.FooServiceImpl;
|
||||
@@ -207,6 +209,15 @@ public class ClassPathScanningCandidateComponentProviderTests {
|
||||
assertThat(ctx.containsBean(ProfileAnnotatedComponent.BEAN_NAME), is(true));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIntegrationWithAnnotationConfigApplicationContext_validMetaAnnotatedProfile() {
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
|
||||
ctx.getEnvironment().setActiveProfiles(DevComponent.PROFILE_NAME);
|
||||
ctx.register(ProfileMetaAnnotatedComponent.class);
|
||||
ctx.refresh();
|
||||
assertThat(ctx.containsBean(ProfileMetaAnnotatedComponent.BEAN_NAME), is(true));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIntegrationWithAnnotationConfigApplicationContext_invalidProfile() {
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
|
||||
@@ -216,6 +227,15 @@ public class ClassPathScanningCandidateComponentProviderTests {
|
||||
assertThat(ctx.containsBean(ProfileAnnotatedComponent.BEAN_NAME), is(false));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIntegrationWithAnnotationConfigApplicationContext_invalidMetaAnnotatedProfile() {
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
|
||||
ctx.getEnvironment().setActiveProfiles("other");
|
||||
ctx.register(ProfileMetaAnnotatedComponent.class);
|
||||
ctx.refresh();
|
||||
assertThat(ctx.containsBean(ProfileMetaAnnotatedComponent.BEAN_NAME), is(false));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testIntegrationWithAnnotationConfigApplicationContext_defaultProfile() {
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext();
|
||||
|
||||
@@ -40,7 +40,7 @@ import test.beans.TestBean;
|
||||
* particularly convenient syntax requiring no extra artifact for the aspect.
|
||||
*
|
||||
* <p>Currently it is assumed that the user is bootstrapping Configuration class processing via XML (using
|
||||
* annotation-config or component-scan), and thus will also use {@literal <aop:aspectj-autoproxy/>} to enable
|
||||
* annotation-config or component-scan), and thus will also use {@code <aop:aspectj-autoproxy/>} to enable
|
||||
* processing of the Aspect annotation.
|
||||
*
|
||||
* @author Chris Beams
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2010 the original author or authors.
|
||||
* Copyright 2002-2011 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.
|
||||
@@ -72,7 +72,7 @@ public class ContextNamespaceHandlerTests {
|
||||
|
||||
@Test
|
||||
public void propertyPlaceholderEnvironmentProperties() throws Exception {
|
||||
MockEnvironment env = MockEnvironment.withProperty("foo", "spam");
|
||||
MockEnvironment env = new MockEnvironment().withProperty("foo", "spam");
|
||||
GenericXmlApplicationContext applicationContext = new GenericXmlApplicationContext();
|
||||
applicationContext.setEnvironment(env);
|
||||
applicationContext.load(new ClassPathResource("contextNamespaceHandlerTests-simple.xml", getClass()));
|
||||
|
||||
@@ -20,12 +20,11 @@ import static org.hamcrest.CoreMatchers.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.springframework.beans.factory.support.BeanDefinitionBuilder.genericBeanDefinition;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.context.support.AbstractApplicationContext;
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.mock.env.MockPropertySource;
|
||||
|
||||
import test.beans.TestBean;
|
||||
|
||||
@@ -49,7 +48,7 @@ public class EnvironmentAccessorIntegrationTests {
|
||||
.getBeanDefinition());
|
||||
|
||||
GenericApplicationContext ctx = new GenericApplicationContext(bf);
|
||||
ctx.getEnvironment().addPropertySource("testMap", new HashMap() {{ put("my.name", "myBean"); }});
|
||||
ctx.getEnvironment().getPropertySources().addFirst(new MockPropertySource().withProperty("my.name", "myBean"));
|
||||
ctx.refresh();
|
||||
|
||||
assertThat(ctx.getBean(TestBean.class).getName(), equalTo("myBean"));
|
||||
|
||||
@@ -1,91 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2010 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.context.support;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.springframework.beans.factory.support.BeanDefinitionBuilder.genericBeanDefinition;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.mock.env.MockEnvironment;
|
||||
|
||||
import test.beans.TestBean;
|
||||
|
||||
/**
|
||||
* Unit tests for {@link EnvironmentAwarePropertyPlaceholderConfigurer}.
|
||||
*
|
||||
* @author Chris Beams
|
||||
* @since 3.1
|
||||
* @see EnvironmentAwarePropertyPlaceholderConfigurerTests
|
||||
*/
|
||||
public class EnvironmentAwarePropertyPlaceholderConfigurerTests {
|
||||
|
||||
@Test(expected=IllegalArgumentException.class)
|
||||
public void environmentNotNull() {
|
||||
new EnvironmentAwarePropertyPlaceholderConfigurer().postProcessBeanFactory(new DefaultListableBeanFactory());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void localPropertiesOverrideFalse() {
|
||||
localPropertiesOverride(false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void localPropertiesOverrideTrue() {
|
||||
localPropertiesOverride(true);
|
||||
}
|
||||
|
||||
private void localPropertiesOverride(boolean override) {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${foo}")
|
||||
.getBeanDefinition());
|
||||
|
||||
EnvironmentAwarePropertyPlaceholderConfigurer ppc = new EnvironmentAwarePropertyPlaceholderConfigurer();
|
||||
|
||||
ppc.setLocalOverride(override);
|
||||
ppc.setProperties(MockEnvironment.withProperty("foo", "local").asProperties());
|
||||
ppc.setEnvironment(MockEnvironment.withProperty("foo", "enclosing"));
|
||||
ppc.postProcessBeanFactory(bf);
|
||||
if (override) {
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("local"));
|
||||
} else {
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("enclosing"));
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void simpleReplacement() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
MockEnvironment env = new MockEnvironment();
|
||||
env.setProperty("my.name", "myValue");
|
||||
|
||||
EnvironmentAwarePropertyPlaceholderConfigurer ppc =
|
||||
new EnvironmentAwarePropertyPlaceholderConfigurer();
|
||||
ppc.setEnvironment(env);
|
||||
ppc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("myValue"));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -9,7 +9,7 @@ import org.springframework.util.ClassUtils;
|
||||
|
||||
/**
|
||||
* Unit tests for {@link GenericXmlApplicationContext}.
|
||||
*
|
||||
*
|
||||
* See SPR-7530.
|
||||
*
|
||||
* @author Chris Beams
|
||||
|
||||
@@ -0,0 +1,163 @@
|
||||
/*
|
||||
* Copyright 2002-2010 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.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.context.support;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.springframework.beans.factory.support.BeanDefinitionBuilder.genericBeanDefinition;
|
||||
|
||||
import java.util.Properties;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
|
||||
import org.springframework.core.env.MutablePropertySources;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.core.io.Resource;
|
||||
import org.springframework.mock.env.MockEnvironment;
|
||||
import org.springframework.mock.env.MockPropertySource;
|
||||
|
||||
import test.beans.TestBean;
|
||||
|
||||
/**
|
||||
* Unit tests for {@link PropertySourcesPlaceholderConfigurer}.
|
||||
*
|
||||
* @author Chris Beams
|
||||
* @since 3.1
|
||||
*/
|
||||
public class PropertySourcesPlaceholderConfigurerTests {
|
||||
|
||||
@Test
|
||||
public void replacementFromEnvironmentProperties() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
MockEnvironment env = new MockEnvironment();
|
||||
env.setProperty("my.name", "myValue");
|
||||
|
||||
PropertySourcesPlaceholderConfigurer ppc =
|
||||
new PropertySourcesPlaceholderConfigurer();
|
||||
ppc.setEnvironment(env);
|
||||
ppc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("myValue"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void localPropertiesViaResource() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
PropertySourcesPlaceholderConfigurer pc = new PropertySourcesPlaceholderConfigurer();
|
||||
Resource resource = new ClassPathResource("PropertySourcesPlaceholderConfigurerTests.properties", this.getClass());
|
||||
pc.setLocation(resource);
|
||||
pc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("foo"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void localPropertiesOverrideFalse() {
|
||||
localPropertiesOverride(false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void localPropertiesOverrideTrue() {
|
||||
localPropertiesOverride(true);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void explicitPropertySources() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
MutablePropertySources propertySources = new MutablePropertySources();
|
||||
propertySources.addLast(new MockPropertySource().withProperty("my.name", "foo"));
|
||||
|
||||
PropertySourcesPlaceholderConfigurer pc = new PropertySourcesPlaceholderConfigurer();
|
||||
pc.setPropertySources(propertySources);
|
||||
pc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("foo"));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void explicitPropertySourcesExcludesEnvironment() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
MutablePropertySources propertySources = new MutablePropertySources();
|
||||
propertySources.addLast(new MockPropertySource());
|
||||
|
||||
PropertySourcesPlaceholderConfigurer pc = new PropertySourcesPlaceholderConfigurer();
|
||||
pc.setPropertySources(propertySources);
|
||||
pc.setEnvironment(new MockEnvironment().withProperty("my.name", "env"));
|
||||
pc.setIgnoreUnresolvablePlaceholders(true);
|
||||
pc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("${my.name}"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("serial")
|
||||
public void explicitPropertySourcesExcludesLocalProperties() {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${my.name}")
|
||||
.getBeanDefinition());
|
||||
|
||||
MutablePropertySources propertySources = new MutablePropertySources();
|
||||
propertySources.addLast(new MockPropertySource());
|
||||
|
||||
PropertySourcesPlaceholderConfigurer pc = new PropertySourcesPlaceholderConfigurer();
|
||||
pc.setPropertySources(propertySources);
|
||||
pc.setProperties(new Properties() {{ put("my.name", "local"); }});
|
||||
pc.setIgnoreUnresolvablePlaceholders(true);
|
||||
pc.postProcessBeanFactory(bf);
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("${my.name}"));
|
||||
}
|
||||
|
||||
@SuppressWarnings("serial")
|
||||
private void localPropertiesOverride(boolean override) {
|
||||
DefaultListableBeanFactory bf = new DefaultListableBeanFactory();
|
||||
bf.registerBeanDefinition("testBean",
|
||||
genericBeanDefinition(TestBean.class)
|
||||
.addPropertyValue("name", "${foo}")
|
||||
.getBeanDefinition());
|
||||
|
||||
PropertySourcesPlaceholderConfigurer ppc = new PropertySourcesPlaceholderConfigurer();
|
||||
|
||||
ppc.setLocalOverride(override);
|
||||
ppc.setProperties(new Properties() {{ setProperty("foo", "local"); }});
|
||||
ppc.setEnvironment(new MockEnvironment().withProperty("foo", "enclosing"));
|
||||
ppc.postProcessBeanFactory(bf);
|
||||
if (override) {
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("local"));
|
||||
} else {
|
||||
assertThat(bf.getBean(TestBean.class).getName(), equalTo("enclosing"));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1 @@
|
||||
my.name=foo
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2010 the original author or authors.
|
||||
* Copyright 2002-2011 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.
|
||||
@@ -19,30 +19,41 @@ package org.springframework.mock.env;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
import org.springframework.core.env.ConfigurableEnvironment;
|
||||
|
||||
|
||||
/**
|
||||
* Simple {@link ConfigurableEnvironment} implementation exposing a
|
||||
* {@link #setProperty(String, String)} and {@link #withProperty(String, String)}
|
||||
* methods for testing purposes.
|
||||
*
|
||||
* @author Chris Beams
|
||||
* @since 3.1
|
||||
* @see MockPropertySource
|
||||
*/
|
||||
public class MockEnvironment extends AbstractEnvironment {
|
||||
|
||||
private MockPropertySource propertySource = new MockPropertySource();
|
||||
|
||||
/**
|
||||
* Create a new {@code MockEnvironment} with a single {@link MockPropertySource}.
|
||||
*/
|
||||
public MockEnvironment() {
|
||||
getPropertySources().add(propertySource);
|
||||
getPropertySources().addLast(propertySource);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set a property on the underlying {@link MockPropertySource} for this environment.
|
||||
*/
|
||||
public void setProperty(String key, String value) {
|
||||
propertySource.setProperty(key, value);
|
||||
}
|
||||
|
||||
public static MockEnvironment withProperty(String key, String value) {
|
||||
MockEnvironment environment = new MockEnvironment();
|
||||
environment.setProperty(key, value);
|
||||
return environment;
|
||||
/**
|
||||
* Convenient synonym for {@link #setProperty} that returns the current instance.
|
||||
* Useful for method chaining and fluent-style use.
|
||||
* @return this {@link MockEnvironment} instance
|
||||
* @see MockPropertySource#withProperty(String, String)
|
||||
*/
|
||||
public MockEnvironment withProperty(String key, String value) {
|
||||
this.setProperty(key, value);
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2010 the original author or authors.
|
||||
* Copyright 2002-2011 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.
|
||||
@@ -19,24 +19,85 @@ package org.springframework.mock.env;
|
||||
import java.util.Properties;
|
||||
|
||||
import org.springframework.core.env.PropertiesPropertySource;
|
||||
import org.springframework.core.env.PropertySource;
|
||||
|
||||
/**
|
||||
* Simple {@link PropertySource} implementation for use in testing. Accepts
|
||||
* a user-provided {@link Properties} object, or if omitted during construction,
|
||||
* the implementation will initialize its own.
|
||||
*
|
||||
* The {@link #setProperty} and {@link #withProperty} methods are exposed for
|
||||
* convenience, for example:
|
||||
* <pre>
|
||||
* {@code
|
||||
* PropertySource<?> source = new MockPropertySource().withProperty("foo", "bar");
|
||||
* }
|
||||
* </pre>
|
||||
*
|
||||
* @author Chris Beams
|
||||
* @since 3.1
|
||||
* @see MockEnvironment
|
||||
*/
|
||||
public class MockPropertySource extends PropertiesPropertySource {
|
||||
|
||||
/**
|
||||
* {@value} is the default name for {@link MockPropertySource} instances not
|
||||
* otherwise given an explicit name.
|
||||
* @see #MockPropertySource()
|
||||
* @see #MockPropertySource(String)
|
||||
*/
|
||||
public static final String MOCK_PROPERTIES_PROPERTY_SOURCE_NAME = "mockProperties";
|
||||
|
||||
/**
|
||||
* Create a new {@code MockPropertySource} named {@value #MOCK_PROPERTIES_PROPERTY_SOURCE_NAME}
|
||||
* that will maintain its own internal {@link Properties} instance.
|
||||
*/
|
||||
public MockPropertySource() {
|
||||
this(new Properties());
|
||||
}
|
||||
|
||||
private MockPropertySource(Properties properties) {
|
||||
super("mockProperties", properties);
|
||||
/**
|
||||
* Create a new {@code MockPropertySource} with the given name that will
|
||||
* maintain its own internal {@link Properties} instance.
|
||||
* @param name the {@linkplain #getName() name} of the property source
|
||||
*/
|
||||
public MockPropertySource(String name) {
|
||||
this(name, new Properties());
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new {@code MockPropertySource} named {@value #MOCK_PROPERTIES_PROPERTY_SOURCE_NAME}
|
||||
* and backed by the given {@link Properties} object.
|
||||
* @param properties the properties to use
|
||||
*/
|
||||
public MockPropertySource(Properties properties) {
|
||||
this(MOCK_PROPERTIES_PROPERTY_SOURCE_NAME, properties);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new {@code MockPropertySource} with with the given name and backed by the given
|
||||
* {@link Properties} object
|
||||
* @param name the {@linkplain #getName() name} of the property source
|
||||
* @param properties the properties to use
|
||||
*/
|
||||
public MockPropertySource(String name, Properties properties) {
|
||||
super(name, properties);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the given property on the underlying {@link Properties} object.
|
||||
*/
|
||||
public void setProperty(String key, String value) {
|
||||
this.source.setProperty(key, value);
|
||||
this.source.put(key, value);
|
||||
}
|
||||
|
||||
public static MockPropertySource withProperty(String key, String value) {
|
||||
Properties properties = new Properties();
|
||||
properties.setProperty(key, value);
|
||||
return new MockPropertySource(properties);
|
||||
/**
|
||||
* Convenient synonym for {@link #setProperty} that returns the current instance.
|
||||
* Useful for method chaining and fluent-style use.
|
||||
* @return this {@link MockPropertySource} instance
|
||||
*/
|
||||
public MockPropertySource withProperty(String key, String value) {
|
||||
this.setProperty(key, value);
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user