Merge remote-tracking branch 'Upstream/master' into http-client-factories

This commit is contained in:
Ryan Baxter
2017-08-01 15:26:15 -04:00
18 changed files with 434 additions and 85 deletions

View File

@@ -101,12 +101,6 @@
<artifactId>json-path</artifactId>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<scope>compile</scope>
<optional>true</optional>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2013-2015 the original author or authors.
* Copyright 2013-2017 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.
@@ -16,20 +16,17 @@
package org.springframework.cloud.client;
import java.net.URI;
import java.util.LinkedHashMap;
import java.util.Map;
import lombok.Data;
import lombok.RequiredArgsConstructor;
import java.util.Objects;
/**
* Default implementation of {@link ServiceInstance}.
*
* @author Spencer Gibb
*/
@Data
@RequiredArgsConstructor
public class DefaultServiceInstance implements ServiceInstance {
private final String serviceId;
@@ -42,6 +39,15 @@ public class DefaultServiceInstance implements ServiceInstance {
private final Map<String, String> metadata;
public DefaultServiceInstance(String serviceId, String host, int port, boolean secure,
Map<String, String> metadata) {
this.serviceId = serviceId;
this.host = host;
this.port = port;
this.secure = secure;
this.metadata = metadata;
}
public DefaultServiceInstance(String serviceId, String host, int port,
boolean secure) {
this(serviceId, host, port, secure, new LinkedHashMap<String, String>());
@@ -68,4 +74,52 @@ public class DefaultServiceInstance implements ServiceInstance {
instance.getPort());
return URI.create(uri);
}
@Override
public String getServiceId() {
return serviceId;
}
@Override
public String getHost() {
return host;
}
@Override
public int getPort() {
return port;
}
@Override
public boolean isSecure() {
return secure;
}
@Override
public String toString() {
return "DefaultServiceInstance{" +
"serviceId='" + serviceId + '\'' +
", host='" + host + '\'' +
", port=" + port +
", secure=" + secure +
", metadata=" + metadata +
'}';
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
DefaultServiceInstance that = (DefaultServiceInstance) o;
return port == that.port &&
secure == that.secure &&
Objects.equals(serviceId, that.serviceId) &&
Objects.equals(host, that.host) &&
Objects.equals(metadata, that.metadata);
}
@Override
public int hashCode() {
return Objects.hash(serviceId, host, port, secure, metadata);
}
}

View File

@@ -1,3 +1,19 @@
/*
* Copyright 2017 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.cloud.client.actuator;
import java.util.ArrayList;
@@ -10,7 +26,6 @@ import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import lombok.Value;
/**
* @author Spencer Gibb
@@ -75,17 +90,47 @@ public class FeaturesEndpoint extends AbstractEndpoint<FeaturesEndpoint.Features
type.getPackage().getImplementationVendor()));
}
@Value
class Features {
List<Feature> enabled = new ArrayList<>();
List<String> disabled = new ArrayList<>();
final List<Feature> enabled = new ArrayList<>();
final List<String> disabled = new ArrayList<>();
public List<Feature> getEnabled() {
return enabled;
}
public List<String> getDisabled() {
return disabled;
}
}
@Value
class Feature {
final String type;
final String name;
final String version;
final String vendor;
public Feature(String type, String name, String version, String vendor) {
this.type = type;
this.name = name;
this.version = version;
this.vendor = vendor;
}
public String getType() {
return type;
}
public String getName() {
return name;
}
public String getVersion() {
return version;
}
public String getVendor() {
return vendor;
}
}
}

View File

@@ -1,12 +1,38 @@
/*
* Copyright 2017 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.cloud.client.actuator;
import lombok.Value;
/**
* @author Spencer Gibb
*/
@Value
public class NamedFeature {
private final String name;
private final Class<?> type;
public NamedFeature(String name, Class<?> type) {
this.name = name;
this.type = type;
}
public String getName() {
return name;
}
public Class<?> getType() {
return type;
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2013-2015 the original author or authors.
* Copyright 2013-2017 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,6 +19,8 @@ package org.springframework.cloud.client.discovery.health;
import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.boot.actuate.health.Health;
import org.springframework.boot.actuate.health.Status;
import org.springframework.cloud.client.discovery.DiscoveryClient;
@@ -26,12 +28,10 @@ import org.springframework.cloud.client.discovery.event.InstanceRegisteredEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.core.Ordered;
import lombok.extern.apachecommons.CommonsLog;
/**
* @author Spencer Gibb
*/
@CommonsLog
public class DiscoveryClientHealthIndicator implements DiscoveryHealthIndicator, Ordered,
ApplicationListener<InstanceRegisteredEvent<?>> {
@@ -42,6 +42,8 @@ public class DiscoveryClientHealthIndicator implements DiscoveryHealthIndicator,
private final DiscoveryClient discoveryClient;
private final DiscoveryClientHealthIndicatorProperties properties;
private final Log log = LogFactory.getLog(DiscoveryClientHealthIndicator.class);
@Deprecated
public DiscoveryClientHealthIndicator(DiscoveryClient discoveryClient) {
this(discoveryClient, new DiscoveryClientHealthIndicatorProperties());

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2013-2014 the original author or authors.
* Copyright 2013-2017 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.
@@ -21,6 +21,8 @@ import java.net.UnknownHostException;
import javax.annotation.PostConstruct;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
@@ -38,8 +40,6 @@ import org.springframework.context.annotation.Configuration;
import org.springframework.context.event.ContextRefreshedEvent;
import org.springframework.core.env.Environment;
import lombok.extern.apachecommons.CommonsLog;
/**
*
* @deprecated Use
@@ -50,7 +50,6 @@ import lombok.extern.apachecommons.CommonsLog;
@Configuration
@EnableConfigurationProperties
@ConditionalOnMissingBean(DiscoveryClient.class)
@CommonsLog
@Deprecated
public class NoopDiscoveryClientAutoConfiguration
implements ApplicationListener<ContextRefreshedEvent> {
@@ -69,6 +68,8 @@ public class NoopDiscoveryClientAutoConfiguration
private DefaultServiceInstance serviceInstance;
private final Log log = LogFactory.getLog(NoopDiscoveryClientAutoConfiguration.class);
@PostConstruct
public void init() {
String host = "localhost";

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2015 the original author or authors.
* Copyright 2017 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.
@@ -15,7 +15,6 @@
*/
package org.springframework.cloud.client.hypermedia;
import lombok.Data;
import java.util.Collections;
import java.util.List;
@@ -50,17 +49,39 @@ public class CloudHypermediaAutoConfiguration {
properties.getRefresh().getInitialDelay());
}
@Data
@ConfigurationProperties(prefix = "spring.cloud.hypermedia")
public static class CloudHypermediaProperties {
private Refresh refresh = new Refresh();
@Data
public Refresh getRefresh() {
return refresh;
}
public void setRefresh(Refresh refresh) {
this.refresh = refresh;
}
public static class Refresh {
private int fixedDelay = 5000;
private int initialDelay = 10000;
public int getFixedDelay() {
return fixedDelay;
}
public void setFixedDelay(int fixedDelay) {
this.fixedDelay = fixedDelay;
}
public int getInitialDelay() {
return initialDelay;
}
public void setInitialDelay(int initialDelay) {
this.initialDelay = initialDelay;
}
}
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2015 the original author or authors.
* Copyright 2015-2017 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.
@@ -15,12 +15,10 @@
*/
package org.springframework.cloud.client.hypermedia;
import lombok.Getter;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import java.net.URI;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.cloud.client.ServiceInstance;
import org.springframework.hateoas.Link;
import org.springframework.hateoas.MediaTypes;
@@ -35,15 +33,22 @@ import org.springframework.web.client.RestTemplate;
*
* @author Oliver Gierke
*/
@Slf4j
@RequiredArgsConstructor
public class DiscoveredResource implements RemoteResource {
private final ServiceInstanceProvider provider;
private final TraversalDefinition traversal;
private RestOperations restOperations = new RestTemplate();
private @Getter Link link = null;
private Link link = null;
private final Logger log = LoggerFactory.getLogger(DiscoveredResource.class);
public DiscoveredResource(ServiceInstanceProvider provider, TraversalDefinition traversal) {
this.provider = provider;
this.traversal = traversal;
}
/**
* Configures the {@link RestOperations} to use to execute the traversal and verifying HEAD calls.
@@ -54,6 +59,27 @@ public class DiscoveredResource implements RemoteResource {
this.restOperations = restOperations == null ? new RestTemplate() : restOperations;
}
public ServiceInstanceProvider getProvider() {
return provider;
}
public TraversalDefinition getTraversal() {
return traversal;
}
public RestOperations getRestOperations() {
return restOperations;
}
@Override
public Link getLink() {
return link;
}
public void setLink(Link link) {
this.link = link;
}
/**
* Verifies the link to the current
*/

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2015 the original author or authors.
* Copyright 2015-2017 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.
@@ -15,8 +15,6 @@
*/
package org.springframework.cloud.client.hypermedia;
import lombok.RequiredArgsConstructor;
import java.util.List;
import org.springframework.cloud.client.ServiceInstance;
@@ -28,16 +26,20 @@ import org.springframework.cloud.client.discovery.DiscoveryClient;
*
* @author Oliver Gierke
*/
@RequiredArgsConstructor
public class DynamicServiceInstanceProvider implements ServiceInstanceProvider {
private final DiscoveryClient client;
private final String serviceName;
public DynamicServiceInstanceProvider(DiscoveryClient client, String serviceName) {
this.client = client;
this.serviceName = serviceName;
}
/*
* (non-Javadoc)
* @see example.customers.integration.ServiceInstanceProvider#getServiceInstance()
*/
* (non-Javadoc)
* @see example.customers.integration.ServiceInstanceProvider#getServiceInstance()
*/
@Override
public ServiceInstance getServiceInstance() {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2015 the original author or authors.
* Copyright 2017 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.
@@ -15,8 +15,6 @@
*/
package org.springframework.cloud.client.hypermedia;
import lombok.RequiredArgsConstructor;
import java.util.List;
import org.springframework.scheduling.config.ContextLifecycleScheduledTaskRegistrar;
@@ -29,16 +27,21 @@ import org.springframework.scheduling.config.ScheduledTaskRegistrar;
*
* @author Oliver Gierke
*/
@RequiredArgsConstructor
public class RemoteResourceRefresher extends ContextLifecycleScheduledTaskRegistrar {
private final List<RemoteResource> discoveredResources;
private final int fixedDelay, initialDelay;
public RemoteResourceRefresher(List<RemoteResource> discoveredResources, int fixedDelay, int initialDelay) {
this.discoveredResources = discoveredResources;
this.fixedDelay = fixedDelay;
this.initialDelay = initialDelay;
}
/*
* (non-Javadoc)
* @see org.springframework.scheduling.config.ContextLifecycleScheduledTaskRegistrar#afterPropertiesSet()
*/
* (non-Javadoc)
* @see org.springframework.scheduling.config.ContextLifecycleScheduledTaskRegistrar#afterPropertiesSet()
*/
@Override
public void afterPropertiesSet() {

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2015 the original author or authors.
* Copyright 2017 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.
@@ -15,8 +15,6 @@
*/
package org.springframework.cloud.client.hypermedia;
import lombok.RequiredArgsConstructor;
import org.springframework.cloud.client.ServiceInstance;
/**
@@ -24,15 +22,18 @@ import org.springframework.cloud.client.ServiceInstance;
*
* @author Oliver Gierke
*/
@RequiredArgsConstructor
public class StaticServiceInstanceProvider implements ServiceInstanceProvider {
private final ServiceInstance instance;
public StaticServiceInstanceProvider(ServiceInstance instance) {
this.instance = instance;
}
/*
* (non-Javadoc)
* @see example.customers.integration.ServiceInstanceProvider#getServiceInstance()
*/
* (non-Javadoc)
* @see example.customers.integration.ServiceInstanceProvider#getServiceInstance()
*/
@Override
public ServiceInstance getServiceInstance() {
return instance;

View File

@@ -31,20 +31,21 @@ import java.util.concurrent.Future;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.TimeUnit;
import lombok.Data;
import lombok.extern.apachecommons.CommonsLog;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
/**
* @author Spencer Gibb
*/
@CommonsLog
public class InetUtils implements Closeable {
// TODO: maybe shutdown the thread pool if it isn't being used?
private final ExecutorService executorService;
private final InetUtilsProperties properties;
private static final InetUtils instance = new InetUtils(new InetUtilsProperties());
private final Log log = LogFactory.getLog(InetUtils.class);
public InetUtils(final InetUtilsProperties properties) {
this.properties = properties;
this.executorService = Executors
@@ -200,7 +201,6 @@ public class InetUtils implements Closeable {
return new HostInfo(host).getIpAddressAsInt();
}
@Data
public static class HostInfo {
public boolean override;
private String ipAddress;
@@ -227,6 +227,30 @@ public class InetUtils implements Closeable {
}
return ByteBuffer.wrap(inetAddress.getAddress()).getInt();
}
public boolean isOverride() {
return override;
}
public void setOverride(boolean override) {
this.override = override;
}
public String getIpAddress() {
return ipAddress;
}
public void setIpAddress(String ipAddress) {
this.ipAddress = ipAddress;
}
public String getHostname() {
return hostname;
}
public void setHostname(String hostname) {
this.hostname = hostname;
}
}
}

View File

@@ -1,3 +1,19 @@
/*
* Copyright 2017 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.cloud.commons.util;
import java.net.InetAddress;
@@ -7,12 +23,9 @@ import java.util.List;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
import lombok.Data;
/**
* @author Spencer Gibb
*/
@Data
@ConfigurationProperties(InetUtilsProperties.PREFIX)
public class InetUtilsProperties {
public static final String PREFIX = "spring.cloud.inetutils";
@@ -47,4 +60,56 @@ public class InetUtilsProperties {
* List of Java regex expressions for network addresses that will be preferred.
*/
private List<String> preferredNetworks = new ArrayList<>();
public static String getPREFIX() {
return PREFIX;
}
public String getDefaultHostname() {
return defaultHostname;
}
public void setDefaultHostname(String defaultHostname) {
this.defaultHostname = defaultHostname;
}
public String getDefaultIpAddress() {
return defaultIpAddress;
}
public void setDefaultIpAddress(String defaultIpAddress) {
this.defaultIpAddress = defaultIpAddress;
}
public int getTimeoutSeconds() {
return timeoutSeconds;
}
public void setTimeoutSeconds(int timeoutSeconds) {
this.timeoutSeconds = timeoutSeconds;
}
public List<String> getIgnoredInterfaces() {
return ignoredInterfaces;
}
public void setIgnoredInterfaces(List<String> ignoredInterfaces) {
this.ignoredInterfaces = ignoredInterfaces;
}
public boolean isUseOnlySiteLocalInterfaces() {
return useOnlySiteLocalInterfaces;
}
public void setUseOnlySiteLocalInterfaces(boolean useOnlySiteLocalInterfaces) {
this.useOnlySiteLocalInterfaces = useOnlySiteLocalInterfaces;
}
public List<String> getPreferredNetworks() {
return preferredNetworks;
}
public void setPreferredNetworks(List<String> preferredNetworks) {
this.preferredNetworks = preferredNetworks;
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2013-2015 the original author or authors.
* Copyright 2013-2017 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.
@@ -20,6 +20,8 @@ import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.List;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.BeanClassLoaderAware;
import org.springframework.context.EnvironmentAware;
import org.springframework.context.annotation.DeferredImportSelector;
@@ -30,7 +32,6 @@ import org.springframework.core.io.support.SpringFactoriesLoader;
import org.springframework.core.type.AnnotationMetadata;
import org.springframework.util.Assert;
import lombok.extern.apachecommons.CommonsLog;
/**
* Selects configurations to load defined by the generic type T. Loads implementations
@@ -39,7 +40,6 @@ import lombok.extern.apachecommons.CommonsLog;
* @author Spencer Gibb
* @author Dave Syer
*/
@CommonsLog
public abstract class SpringFactoryImportSelector<T>
implements DeferredImportSelector, BeanClassLoaderAware, EnvironmentAware {
@@ -49,6 +49,8 @@ public abstract class SpringFactoryImportSelector<T>
private Environment environment;
private final Log log = LogFactory.getLog(SpringFactoryImportSelector.class);
@SuppressWarnings("unchecked")
protected SpringFactoryImportSelector() {
this.annotationClass = (Class<T>) GenericTypeResolver

View File

@@ -1,20 +1,33 @@
/*
* Copyright 2017 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.cloud.client.loadbalancer;
import static org.hamcrest.MatcherAssert.assertThat;
import static org.hamcrest.Matchers.empty;
import static org.hamcrest.Matchers.hasSize;
import static org.hamcrest.Matchers.instanceOf;
import static org.hamcrest.Matchers.is;
import static org.hamcrest.Matchers.notNullValue;
import java.io.IOException;
import java.net.URI;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.Random;
import lombok.SneakyThrows;
import org.junit.Test;
import org.springframework.beans.factory.annotation.Autowired;
@@ -25,7 +38,6 @@ import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Primary;
import org.springframework.http.client.ClientHttpRequestInterceptor;
import org.springframework.web.client.RestTemplate;
/**
@@ -138,15 +150,21 @@ public abstract class AbstractLoadBalancerAutoConfigurationTests {
}
@Override
@SneakyThrows
public <T> T execute(String serviceId, LoadBalancerRequest<T> request) {
return request.apply(choose(serviceId));
try {
return request.apply(choose(serviceId));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
@Override
@SneakyThrows
public <T> T execute(String serviceId, ServiceInstance serviceInstance, LoadBalancerRequest<T> request) throws IOException {
return request.apply(choose(serviceId));
try {
return request.apply(choose(serviceId));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
@Override

View File

@@ -1,6 +1,21 @@
/*
* Copyright 2017 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.cloud.client.loadbalancer;
import lombok.SneakyThrows;
import org.hamcrest.MatcherAssert;
import org.junit.Test;
import org.springframework.beans.factory.annotation.Autowired;
@@ -140,15 +155,21 @@ public class AsyncLoadBalancerAutoConfigurationTests {
}
@Override
@SneakyThrows
public <T> T execute(String serviceId, LoadBalancerRequest<T> request) {
return request.apply(choose(serviceId));
try {
return request.apply(choose(serviceId));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
@Override
@SneakyThrows
public <T> T execute(String serviceId, ServiceInstance serviceInstance, LoadBalancerRequest<T> request) throws IOException {
return request.apply(choose(serviceId));
try {
return request.apply(choose(serviceId));
} catch (Exception e) {
throw new RuntimeException(e);
}
}
@Override

View File

@@ -68,9 +68,8 @@ public class EnvironmentManager implements ApplicationEventPublisherAware {
public Map<String, Object> reset() {
Map<String, Object> result = new LinkedHashMap<String, Object>(map);
if (!map.isEmpty()) {
Set<String> keys = map.keySet();
map.clear();
publish(new EnvironmentChangeEvent(keys));
publish(new EnvironmentChangeEvent(result.keySet()));
}
return result;
}

View File

@@ -0,0 +1,45 @@
package org.springframework.cloud.context.environment;
import org.junit.Test;
import org.mockito.ArgumentCaptor;
import org.mockito.Mockito;
import org.springframework.context.ApplicationEvent;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.mock.env.MockEnvironment;
import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.*;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
public class EnvironmentManagerTest {
@Test
public void testCorrectEvents() {
MockEnvironment environment = new MockEnvironment();
ApplicationEventPublisher publisher = mock(ApplicationEventPublisher.class);
EnvironmentManager environmentManager = new EnvironmentManager(environment);
environmentManager.setApplicationEventPublisher(publisher);
environmentManager.setProperty("foo", "bar");
assertThat(environment.getProperty("foo")).isEqualTo("bar");
ArgumentCaptor<ApplicationEvent> eventCaptor = ArgumentCaptor.forClass(ApplicationEvent.class);
verify(publisher, times(1)).publishEvent(eventCaptor.capture());
assertThat(eventCaptor.getValue()).isInstanceOf(EnvironmentChangeEvent.class);
EnvironmentChangeEvent event = (EnvironmentChangeEvent) eventCaptor.getValue();
assertThat(event.getKeys()).containsExactly("foo");
reset(publisher);
environmentManager.reset();
assertThat(environment.getProperty("foo")).isNull();
verify(publisher, times(1)).publishEvent(eventCaptor.capture());
assertThat(eventCaptor.getValue()).isInstanceOf(EnvironmentChangeEvent.class);
event = (EnvironmentChangeEvent) eventCaptor.getValue();
assertThat(event.getKeys()).containsExactly("foo");
}
}