Reload functionality clean-up part 3 (#1034)
This commit is contained in:
@@ -47,6 +47,7 @@ import org.springframework.cloud.kubernetes.commons.config.reload.condition.Poll
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Import;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
|
||||
/**
|
||||
@@ -56,7 +57,8 @@ import org.springframework.core.env.AbstractEnvironment;
|
||||
@ConditionalOnKubernetesAndConfigEnabled
|
||||
@ConditionalOnClass(EndpointAutoConfiguration.class)
|
||||
@AutoConfigureAfter({ InfoEndpointAutoConfiguration.class, RefreshEndpointAutoConfiguration.class,
|
||||
RefreshAutoConfiguration.class, ConfigReloadAutoConfiguration.class })
|
||||
RefreshAutoConfiguration.class })
|
||||
@Import(ConfigReloadAutoConfiguration.class)
|
||||
@EnableConfigurationProperties(ConfigReloadProperties.class)
|
||||
public class KubernetesClientConfigReloadAutoConfiguration {
|
||||
|
||||
|
||||
@@ -179,7 +179,7 @@ class KubernetesClientEventBasedConfigMapChangeDetectorTests {
|
||||
}
|
||||
|
||||
@Override
|
||||
public OffsetDateTime read(JsonReader jsonReader) throws IOException {
|
||||
public OffsetDateTime read(JsonReader jsonReader) {
|
||||
return OffsetDateTime.now();
|
||||
}
|
||||
|
||||
|
||||
@@ -176,7 +176,7 @@ class KubernetesClientEventBasedSecretsChangeDetectorTests {
|
||||
}
|
||||
|
||||
@Override
|
||||
public OffsetDateTime read(JsonReader jsonReader) throws IOException {
|
||||
public OffsetDateTime read(JsonReader jsonReader) {
|
||||
return OffsetDateTime.now();
|
||||
}
|
||||
|
||||
|
||||
@@ -45,66 +45,51 @@ import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
|
||||
@ConditionalOnKubernetesAndConfigEnabled
|
||||
@ConditionalOnClass(EndpointAutoConfiguration.class)
|
||||
@AutoConfigureAfter({ InfoEndpointAutoConfiguration.class, RefreshEndpointAutoConfiguration.class,
|
||||
RefreshAutoConfiguration.class })
|
||||
RefreshAutoConfiguration.class, RestartEndpoint.class, ContextRefresher.class })
|
||||
@ConditionalOnProperty("spring.cloud.kubernetes.reload.enabled")
|
||||
public class ConfigReloadAutoConfiguration {
|
||||
|
||||
/**
|
||||
* Configuration reload must be enabled explicitly.
|
||||
*/
|
||||
@ConditionalOnProperty("spring.cloud.kubernetes.reload.enabled")
|
||||
@ConditionalOnClass({ RestartEndpoint.class, ContextRefresher.class })
|
||||
protected static class ConfigReloadAutoConfigurationBeans {
|
||||
@Bean("springCloudKubernetesTaskScheduler")
|
||||
@ConditionalOnMissingBean
|
||||
public TaskSchedulerWrapper<TaskScheduler> taskScheduler() {
|
||||
ThreadPoolTaskScheduler threadPoolTaskScheduler = new ThreadPoolTaskScheduler();
|
||||
|
||||
@Bean("springCloudKubernetesTaskScheduler")
|
||||
@ConditionalOnMissingBean
|
||||
public TaskSchedulerWrapper<TaskScheduler> taskScheduler() {
|
||||
ThreadPoolTaskScheduler threadPoolTaskScheduler = new ThreadPoolTaskScheduler();
|
||||
threadPoolTaskScheduler.setThreadNamePrefix("spring-cloud-kubernetes-ThreadPoolTaskScheduler-");
|
||||
threadPoolTaskScheduler.setDaemon(true);
|
||||
|
||||
threadPoolTaskScheduler.setThreadNamePrefix("spring-cloud-kubernetes-ThreadPoolTaskScheduler-");
|
||||
threadPoolTaskScheduler.setDaemon(true);
|
||||
return new TaskSchedulerWrapper<>(threadPoolTaskScheduler);
|
||||
}
|
||||
|
||||
return new TaskSchedulerWrapper<>(threadPoolTaskScheduler);
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public ConfigurationUpdateStrategy configurationUpdateStrategy(ConfigReloadProperties properties,
|
||||
ConfigurableApplicationContext ctx, @Autowired(required = false) RestartEndpoint restarter,
|
||||
ContextRefresher refresher) {
|
||||
switch (properties.getStrategy()) {
|
||||
case RESTART_CONTEXT:
|
||||
Objects.requireNonNull(restarter, "Restart endpoint is not enabled");
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
restarter.restart();
|
||||
});
|
||||
case REFRESH:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), refresher::refresh);
|
||||
case SHUTDOWN:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
ctx.close();
|
||||
});
|
||||
}
|
||||
throw new IllegalStateException("Unsupported configuration update strategy: " + properties.getStrategy());
|
||||
}
|
||||
|
||||
/**
|
||||
* @param properties config reload properties
|
||||
* @param ctx application context
|
||||
* @param restarter restart endpoint
|
||||
* @param refresher context refresher
|
||||
* @return provides the action to execute when the configuration changes.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public ConfigurationUpdateStrategy configurationUpdateStrategy(ConfigReloadProperties properties,
|
||||
ConfigurableApplicationContext ctx, @Autowired(required = false) RestartEndpoint restarter,
|
||||
ContextRefresher refresher) {
|
||||
switch (properties.getStrategy()) {
|
||||
case RESTART_CONTEXT:
|
||||
Objects.requireNonNull(restarter, "Restart endpoint is not enabled");
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
restarter.restart();
|
||||
});
|
||||
case REFRESH:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), refresher::refresh);
|
||||
case SHUTDOWN:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
ctx.close();
|
||||
});
|
||||
}
|
||||
throw new IllegalStateException("Unsupported configuration update strategy: " + properties.getStrategy());
|
||||
private static void wait(ConfigReloadProperties properties) {
|
||||
final long waitMillis = ThreadLocalRandom.current().nextLong(properties.getMaxWaitForRestart().toMillis());
|
||||
try {
|
||||
Thread.sleep(waitMillis);
|
||||
}
|
||||
|
||||
private static void wait(ConfigReloadProperties properties) {
|
||||
final long waitMillis = ThreadLocalRandom.current().nextLong(properties.getMaxWaitForRestart().toMillis());
|
||||
try {
|
||||
Thread.sleep(waitMillis);
|
||||
}
|
||||
catch (InterruptedException ignored) {
|
||||
}
|
||||
catch (InterruptedException ignored) {
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -29,7 +29,7 @@ import reactor.core.publisher.Mono;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySourceLocator;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.EventBasedConfigMapChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.Fabric8EventBasedConfigMapChangeDetector;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
|
||||
|
||||
@@ -37,7 +37,7 @@ import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
|
||||
* @author Ryan Baxter
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
public abstract class ConfigMapWatcherChangeDetector extends EventBasedConfigMapChangeDetector {
|
||||
public abstract class ConfigMapWatcherChangeDetector extends Fabric8EventBasedConfigMapChangeDetector {
|
||||
|
||||
protected Log log = LogFactory.getLog(getClass());
|
||||
|
||||
|
||||
@@ -29,7 +29,7 @@ import reactor.core.publisher.Mono;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySourceLocator;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.EventBasedSecretsChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.Fabric8EventBasedSecretsChangeDetector;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
|
||||
|
||||
@@ -37,7 +37,7 @@ import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
|
||||
* @author Ryan Baxter
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
public abstract class SecretsWatcherChangeDetector extends EventBasedSecretsChangeDetector {
|
||||
public abstract class SecretsWatcherChangeDetector extends Fabric8EventBasedSecretsChangeDetector {
|
||||
|
||||
protected Log log = LogFactory.getLog(getClass());
|
||||
|
||||
|
||||
@@ -1,200 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-2019 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
|
||||
*
|
||||
* https://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.kubernetes.fabric8.config.reload;
|
||||
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
|
||||
import io.fabric8.kubernetes.client.KubernetesClient;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.actuate.autoconfigure.endpoint.EndpointAutoConfiguration;
|
||||
import org.springframework.boot.actuate.autoconfigure.info.InfoEndpointAutoConfiguration;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.cloud.autoconfigure.RefreshAutoConfiguration;
|
||||
import org.springframework.cloud.autoconfigure.RefreshEndpointAutoConfiguration;
|
||||
import org.springframework.cloud.commons.util.TaskSchedulerWrapper;
|
||||
import org.springframework.cloud.context.refresh.ContextRefresher;
|
||||
import org.springframework.cloud.context.restart.RestartEndpoint;
|
||||
import org.springframework.cloud.kubernetes.commons.config.ConditionalOnKubernetesAndConfigEnabled;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingConfigMapChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingSecretsChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.EventReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.PollingReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySourceLocator;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySourceLocator;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* Definition of beans needed for the automatic reload of configuration.
|
||||
*
|
||||
* @author Nicolla Ferraro
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@ConditionalOnKubernetesAndConfigEnabled
|
||||
@ConditionalOnClass(EndpointAutoConfiguration.class)
|
||||
@AutoConfigureAfter({ InfoEndpointAutoConfiguration.class, RefreshEndpointAutoConfiguration.class,
|
||||
RefreshAutoConfiguration.class })
|
||||
@EnableConfigurationProperties(ConfigReloadProperties.class)
|
||||
public class ConfigReloadAutoConfiguration {
|
||||
|
||||
/**
|
||||
* Configuration reload must be enabled explicitly.
|
||||
*/
|
||||
@ConditionalOnProperty("spring.cloud.kubernetes.reload.enabled")
|
||||
@ConditionalOnClass({ RestartEndpoint.class, ContextRefresher.class })
|
||||
protected static class ConfigReloadAutoConfigurationBeans {
|
||||
|
||||
@Autowired
|
||||
private AbstractEnvironment environment;
|
||||
|
||||
@Autowired
|
||||
private KubernetesClient kubernetesClient;
|
||||
|
||||
/**
|
||||
* Polling configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator,
|
||||
TaskSchedulerWrapper taskSchedulerWrapper) {
|
||||
|
||||
return new PollingConfigMapChangeDetector(this.environment, properties, strategy,
|
||||
Fabric8ConfigMapPropertySource.class, fabric8ConfigMapPropertySourceLocator,
|
||||
taskSchedulerWrapper.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Polling secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator,
|
||||
TaskSchedulerWrapper taskScheduler) {
|
||||
|
||||
return new PollingSecretsChangeDetector(this.environment, properties, strategy,
|
||||
Fabric8SecretsPropertySource.class, fabric8SecretsPropertySourceLocator,
|
||||
taskScheduler.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configMap change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator) {
|
||||
|
||||
return new EventBasedConfigMapChangeDetector(this.environment, properties, this.kubernetesClient, strategy,
|
||||
fabric8ConfigMapPropertySourceLocator);
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to secrets change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator) {
|
||||
|
||||
return new EventBasedSecretsChangeDetector(this.environment, properties, this.kubernetesClient, strategy,
|
||||
fabric8SecretsPropertySourceLocator);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param properties config reload properties
|
||||
* @param ctx application context
|
||||
* @param restarter restart endpoint
|
||||
* @param refresher context refresher
|
||||
* @return provides the action to execute when the configuration changes.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public ConfigurationUpdateStrategy configurationUpdateStrategy(ConfigReloadProperties properties,
|
||||
ConfigurableApplicationContext ctx, @Autowired(required = false) RestartEndpoint restarter,
|
||||
ContextRefresher refresher) {
|
||||
switch (properties.getStrategy()) {
|
||||
case RESTART_CONTEXT:
|
||||
Assert.notNull(restarter, "Restart endpoint is not enabled");
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
restarter.restart();
|
||||
});
|
||||
case REFRESH:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), refresher::refresh);
|
||||
case SHUTDOWN:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
ctx.close();
|
||||
});
|
||||
}
|
||||
throw new IllegalStateException("Unsupported configuration update strategy: " + properties.getStrategy());
|
||||
}
|
||||
|
||||
private static void wait(ConfigReloadProperties properties) {
|
||||
final long waitMillis = ThreadLocalRandom.current().nextLong(properties.getMaxWaitForRestart().toMillis());
|
||||
try {
|
||||
Thread.sleep(waitMillis);
|
||||
}
|
||||
catch (InterruptedException ignored) {
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,182 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-2020 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
|
||||
*
|
||||
* https://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.kubernetes.fabric8.config.reload;
|
||||
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
|
||||
import io.fabric8.kubernetes.client.KubernetesClient;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnCloudPlatform;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.cloud.CloudPlatform;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.cloud.commons.util.TaskSchedulerWrapper;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingConfigMapChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingSecretsChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.EventReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.PollingReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySourceLocator;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySourceLocator;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
|
||||
/**
|
||||
* @author Ryan Baxter
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@ConditionalOnCloudPlatform(CloudPlatform.KUBERNETES)
|
||||
@ConditionalOnMissingBean(ConfigReloadAutoConfiguration.class)
|
||||
@EnableConfigurationProperties(ConfigReloadProperties.class)
|
||||
public class ConfigReloadDefaultAutoConfiguration {
|
||||
|
||||
/**
|
||||
* Configuration reload must be enabled explicitly.
|
||||
*/
|
||||
@ConditionalOnProperty("spring.cloud.kubernetes.reload.enabled")
|
||||
protected static class ConfigReloadAutoConfigurationBeans {
|
||||
|
||||
@Autowired
|
||||
private AbstractEnvironment environment;
|
||||
|
||||
@Autowired
|
||||
private KubernetesClient kubernetesClient;
|
||||
|
||||
@Autowired
|
||||
private Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator;
|
||||
|
||||
@Autowired
|
||||
private Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator;
|
||||
|
||||
private static void wait(ConfigReloadProperties properties) {
|
||||
final long waitMillis = ThreadLocalRandom.current().nextLong(properties.getMaxWaitForRestart().toMillis());
|
||||
try {
|
||||
Thread.sleep(waitMillis);
|
||||
}
|
||||
catch (InterruptedException ignored) {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Polling configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator,
|
||||
TaskSchedulerWrapper taskSchedulerWrapper) {
|
||||
|
||||
return new PollingConfigMapChangeDetector(this.environment, properties, strategy,
|
||||
Fabric8ConfigMapPropertySource.class, fabric8ConfigMapPropertySourceLocator,
|
||||
taskSchedulerWrapper.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Polling secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator,
|
||||
TaskSchedulerWrapper taskScheduler) {
|
||||
|
||||
return new PollingSecretsChangeDetector(this.environment, properties, strategy,
|
||||
Fabric8SecretsPropertySource.class, fabric8SecretsPropertySourceLocator,
|
||||
taskScheduler.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configMap change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator) {
|
||||
|
||||
return new EventBasedConfigMapChangeDetector(this.environment, properties, this.kubernetesClient, strategy,
|
||||
fabric8ConfigMapPropertySourceLocator);
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to secrets change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator) {
|
||||
|
||||
return new EventBasedSecretsChangeDetector(this.environment, properties, this.kubernetesClient, strategy,
|
||||
fabric8SecretsPropertySourceLocator);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param properties config reload properties
|
||||
* @param ctx application context
|
||||
* @return provides the action to execute when the configuration changes.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public ConfigurationUpdateStrategy configurationUpdateStrategy(ConfigReloadProperties properties,
|
||||
ConfigurableApplicationContext ctx) {
|
||||
switch (properties.getStrategy()) {
|
||||
case SHUTDOWN:
|
||||
return new ConfigurationUpdateStrategy(properties.getStrategy().name(), () -> {
|
||||
wait(properties);
|
||||
ctx.close();
|
||||
});
|
||||
}
|
||||
throw new IllegalStateException("Unsupported configuration update strategy: " + properties.getStrategy());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,146 @@
|
||||
/*
|
||||
* Copyright 2013-2019 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
|
||||
*
|
||||
* https://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.kubernetes.fabric8.config.reload;
|
||||
|
||||
import io.fabric8.kubernetes.client.KubernetesClient;
|
||||
|
||||
import org.springframework.boot.actuate.autoconfigure.endpoint.EndpointAutoConfiguration;
|
||||
import org.springframework.boot.actuate.autoconfigure.info.InfoEndpointAutoConfiguration;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.cloud.autoconfigure.RefreshAutoConfiguration;
|
||||
import org.springframework.cloud.autoconfigure.RefreshEndpointAutoConfiguration;
|
||||
import org.springframework.cloud.commons.util.TaskSchedulerWrapper;
|
||||
import org.springframework.cloud.context.refresh.ContextRefresher;
|
||||
import org.springframework.cloud.context.restart.RestartEndpoint;
|
||||
import org.springframework.cloud.kubernetes.commons.config.ConditionalOnKubernetesAndConfigEnabled;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadAutoConfiguration;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingConfigMapChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.PollingSecretsChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.EventReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.condition.PollingReloadDetectionMode;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8ConfigMapPropertySourceLocator;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySource;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.Fabric8SecretsPropertySourceLocator;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Import;
|
||||
import org.springframework.core.env.AbstractEnvironment;
|
||||
import org.springframework.scheduling.TaskScheduler;
|
||||
|
||||
/**
|
||||
* Definition of beans needed for the automatic reload of configuration.
|
||||
*
|
||||
* @author Nicolla Ferraro
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@ConditionalOnKubernetesAndConfigEnabled
|
||||
@ConditionalOnClass(EndpointAutoConfiguration.class)
|
||||
@AutoConfigureAfter({ InfoEndpointAutoConfiguration.class, RefreshEndpointAutoConfiguration.class,
|
||||
RefreshAutoConfiguration.class, RestartEndpoint.class, ContextRefresher.class })
|
||||
@EnableConfigurationProperties(ConfigReloadProperties.class)
|
||||
@ConditionalOnProperty("spring.cloud.kubernetes.reload.enabled")
|
||||
@Import(ConfigReloadAutoConfiguration.class)
|
||||
public class Fabric8ConfigReloadAutoConfiguration {
|
||||
|
||||
/**
|
||||
* Polling configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator,
|
||||
TaskSchedulerWrapper<TaskScheduler> taskSchedulerWrapper, AbstractEnvironment environment) {
|
||||
|
||||
return new PollingConfigMapChangeDetector(environment, properties, strategy,
|
||||
Fabric8ConfigMapPropertySource.class, fabric8ConfigMapPropertySourceLocator,
|
||||
taskSchedulerWrapper.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Polling secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to configuration changes and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(PollingReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangePollingWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator,
|
||||
TaskSchedulerWrapper<TaskScheduler> taskScheduler, AbstractEnvironment environment) {
|
||||
|
||||
return new PollingSecretsChangeDetector(environment, properties, strategy, Fabric8SecretsPropertySource.class,
|
||||
fabric8SecretsPropertySourceLocator, taskScheduler.getTaskScheduler());
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based configMap ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8ConfigMapPropertySourceLocator configMap property source locator
|
||||
* @return a bean that listen to configMap change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8ConfigMapPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector configMapPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator,
|
||||
AbstractEnvironment environment, KubernetesClient kubernetesClient) {
|
||||
|
||||
return new Fabric8EventBasedConfigMapChangeDetector(environment, properties, kubernetesClient, strategy,
|
||||
fabric8ConfigMapPropertySourceLocator);
|
||||
}
|
||||
|
||||
/**
|
||||
* Event Based secrets ConfigurationChangeDetector.
|
||||
* @param properties config reload properties
|
||||
* @param strategy configuration update strategy
|
||||
* @param fabric8SecretsPropertySourceLocator secrets property source locator
|
||||
* @return a bean that listen to secrets change events and fire a reload.
|
||||
*/
|
||||
@Bean
|
||||
@ConditionalOnBean(Fabric8SecretsPropertySourceLocator.class)
|
||||
@Conditional(EventReloadDetectionMode.class)
|
||||
public ConfigurationChangeDetector secretsPropertyChangeEventWatcher(ConfigReloadProperties properties,
|
||||
ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator, AbstractEnvironment environment,
|
||||
KubernetesClient kubernetesClient) {
|
||||
|
||||
return new Fabric8EventBasedSecretsChangeDetector(environment, properties, kubernetesClient, strategy,
|
||||
fabric8SecretsPropertySourceLocator);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -46,7 +46,7 @@ import org.springframework.core.env.AbstractEnvironment;
|
||||
* @author Haytham Mohamed
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
public class EventBasedConfigMapChangeDetector extends ConfigurationChangeDetector {
|
||||
public class Fabric8EventBasedConfigMapChangeDetector extends ConfigurationChangeDetector {
|
||||
|
||||
private final Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator;
|
||||
|
||||
@@ -54,7 +54,7 @@ public class EventBasedConfigMapChangeDetector extends ConfigurationChangeDetect
|
||||
|
||||
private KubernetesClient kubernetesClient;
|
||||
|
||||
public EventBasedConfigMapChangeDetector(AbstractEnvironment environment, ConfigReloadProperties properties,
|
||||
public Fabric8EventBasedConfigMapChangeDetector(AbstractEnvironment environment, ConfigReloadProperties properties,
|
||||
KubernetesClient kubernetesClient, ConfigurationUpdateStrategy strategy,
|
||||
Fabric8ConfigMapPropertySourceLocator fabric8ConfigMapPropertySourceLocator) {
|
||||
super(environment, properties, strategy);
|
||||
@@ -46,7 +46,7 @@ import org.springframework.core.env.AbstractEnvironment;
|
||||
* @author Haytham Mohamed
|
||||
* @author Kris Iyer
|
||||
*/
|
||||
public class EventBasedSecretsChangeDetector extends ConfigurationChangeDetector {
|
||||
public class Fabric8EventBasedSecretsChangeDetector extends ConfigurationChangeDetector {
|
||||
|
||||
private Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator;
|
||||
|
||||
@@ -54,7 +54,7 @@ public class EventBasedSecretsChangeDetector extends ConfigurationChangeDetector
|
||||
|
||||
private KubernetesClient kubernetesClient;
|
||||
|
||||
public EventBasedSecretsChangeDetector(AbstractEnvironment environment, ConfigReloadProperties properties,
|
||||
public Fabric8EventBasedSecretsChangeDetector(AbstractEnvironment environment, ConfigReloadProperties properties,
|
||||
KubernetesClient kubernetesClient, ConfigurationUpdateStrategy strategy,
|
||||
Fabric8SecretsPropertySourceLocator fabric8SecretsPropertySourceLocator) {
|
||||
super(environment, properties, strategy);
|
||||
@@ -1,5 +1,5 @@
|
||||
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
|
||||
org.springframework.cloud.kubernetes.fabric8.config.reload.ConfigReloadAutoConfiguration
|
||||
org.springframework.cloud.kubernetes.fabric8.config.reload.Fabric8ConfigReloadAutoConfiguration
|
||||
org.springframework.cloud.bootstrap.BootstrapConfiguration=\
|
||||
org.springframework.cloud.kubernetes.fabric8.config.Fabric8BootstrapConfiguration,\
|
||||
org.springframework.cloud.kubernetes.fabric8.config.Fabric8RetryBootstrapConfiguration
|
||||
|
||||
@@ -35,7 +35,7 @@ import org.springframework.cloud.kubernetes.commons.config.NamedConfigMapNormali
|
||||
import org.springframework.cloud.kubernetes.commons.config.NormalizedSource;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigReloadProperties;
|
||||
import org.springframework.cloud.kubernetes.commons.config.reload.ConfigurationUpdateStrategy;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.EventBasedConfigMapChangeDetector;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.Fabric8EventBasedConfigMapChangeDetector;
|
||||
import org.springframework.mock.env.MockEnvironment;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
@@ -78,8 +78,8 @@ class EventBasedConfigurationChangeDetectorTests {
|
||||
|
||||
});
|
||||
Fabric8ConfigMapPropertySourceLocator configMapLocator = mock(Fabric8ConfigMapPropertySourceLocator.class);
|
||||
EventBasedConfigMapChangeDetector detector = new EventBasedConfigMapChangeDetector(env, configReloadProperties,
|
||||
k8sClient, configurationUpdateStrategy, configMapLocator);
|
||||
Fabric8EventBasedConfigMapChangeDetector detector = new Fabric8EventBasedConfigMapChangeDetector(env,
|
||||
configReloadProperties, k8sClient, configurationUpdateStrategy, configMapLocator);
|
||||
List<Fabric8ConfigMapPropertySource> sources = detector
|
||||
.findPropertySources(Fabric8ConfigMapPropertySource.class);
|
||||
assertThat(sources.size()).isEqualTo(1);
|
||||
|
||||
@@ -25,7 +25,7 @@ import org.springframework.boot.autoconfigure.context.PropertyPlaceholderAutoCon
|
||||
import org.springframework.boot.builder.SpringApplicationBuilder;
|
||||
import org.springframework.cloud.autoconfigure.RefreshAutoConfiguration;
|
||||
import org.springframework.cloud.bootstrap.BootstrapConfiguration;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.ConfigReloadAutoConfiguration;
|
||||
import org.springframework.cloud.kubernetes.fabric8.config.reload.Fabric8ConfigReloadAutoConfiguration;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
|
||||
/**
|
||||
@@ -45,8 +45,9 @@ public class KubernetesConfigTestBase {
|
||||
String[] properties = Stream.concat(Arrays.stream(commonProperties), Arrays.stream(env))
|
||||
.toArray(size -> new String[size]);
|
||||
context = new SpringApplicationBuilder(PropertyPlaceholderAutoConfiguration.class, mockClientConfiguration,
|
||||
BootstrapConfiguration.class, ConfigReloadAutoConfiguration.class, RefreshAutoConfiguration.class)
|
||||
.web(org.springframework.boot.WebApplicationType.NONE).properties(properties).run();
|
||||
BootstrapConfiguration.class, Fabric8ConfigReloadAutoConfiguration.class,
|
||||
RefreshAutoConfiguration.class).web(org.springframework.boot.WebApplicationType.NONE)
|
||||
.properties(properties).run();
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
|
||||
Reference in New Issue
Block a user