feature:support spring cloud configData

pull/451/head
wulingxiao 3 years ago
parent 0007b4a95b
commit 690431363f

@ -2,4 +2,6 @@ org.springframework.cloud.bootstrap.BootstrapConfiguration=\
com.tencent.cloud.polaris.circuitbreaker.config.PolarisCircuitBreakerBootstrapConfiguration
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
com.tencent.cloud.polaris.circuitbreaker.config.PolarisFeignClientAutoConfiguration,\
com.tencent.cloud.polaris.circuitbreaker.config.PolarisRestTemplateAutoConfiguration
com.tencent.cloud.polaris.circuitbreaker.config.PolarisRestTemplateAutoConfiguration,\
com.tencent.cloud.polaris.circuitbreaker.config.PolarisCircuitBreakerBootstrapConfiguration

@ -27,6 +27,7 @@ import com.tencent.polaris.client.api.SDKContext;
import com.tencent.polaris.configuration.api.core.ConfigFileService;
import com.tencent.polaris.configuration.factory.ConfigFileServiceFactory;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
@ -50,6 +51,7 @@ public class PolarisConfigBootstrapAutoConfiguration {
}
@Bean
@ConditionalOnMissingBean
public PolarisPropertySourceManager polarisPropertySourceManager() {
return new PolarisPropertySourceManager();
}

@ -17,19 +17,12 @@
package com.tencent.cloud.polaris.config.adapter;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import com.tencent.cloud.polaris.config.config.ConfigFileGroup;
import com.tencent.cloud.polaris.config.config.PolarisConfigProperties;
import com.tencent.cloud.polaris.config.enums.ConfigFileFormat;
import com.tencent.cloud.polaris.context.config.PolarisContextProperties;
import com.tencent.polaris.configuration.api.core.ConfigFileMetadata;
import com.tencent.polaris.configuration.api.core.ConfigFileService;
import com.tencent.polaris.configuration.api.core.ConfigKVFile;
import com.tencent.polaris.configuration.client.internal.DefaultConfigFileMetadata;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@ -39,7 +32,6 @@ import org.springframework.core.env.CompositePropertySource;
import org.springframework.core.env.Environment;
import org.springframework.core.env.PropertySource;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
/**
* Spring cloud reserved core configuration loading SPI.
@ -51,28 +43,18 @@ import org.springframework.util.StringUtils;
@Order(0)
public class PolarisConfigFileLocator implements PropertySourceLocator {
private static final Logger LOGGER = LoggerFactory.getLogger(PolarisConfigFileLocator.class);
private static final String POLARIS_CONFIG_PROPERTY_SOURCE_NAME = "polaris-config";
private final PolarisConfigProperties polarisConfigProperties;
private final PolarisContextProperties polarisContextProperties;
private final ConfigFileService configFileService;
private final PolarisPropertySourceManager polarisPropertySourceManager;
private final Environment environment;
private final PolarisConfigFilePuller polarisConfigFilePuller;
public PolarisConfigFileLocator(PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties, ConfigFileService configFileService,
PolarisPropertySourceManager polarisPropertySourceManager, Environment environment) {
this.polarisConfigProperties = polarisConfigProperties;
this.polarisContextProperties = polarisContextProperties;
this.configFileService = configFileService;
this.polarisPropertySourceManager = polarisPropertySourceManager;
this.environment = environment;
this.polarisConfigFilePuller = new PolarisConfigFilePuller(polarisContextProperties, configFileService,
polarisPropertySourceManager, environment);
}
@Override
@ -81,128 +63,14 @@ public class PolarisConfigFileLocator implements PropertySourceLocator {
POLARIS_CONFIG_PROPERTY_SOURCE_NAME);
// load spring boot default config files
initInternalConfigFiles(compositePropertySource);
polarisConfigFilePuller.initInternalConfigFiles(compositePropertySource);
// load custom config files
List<ConfigFileGroup> configFileGroups = polarisConfigProperties.getGroups();
if (CollectionUtils.isEmpty(configFileGroups)) {
return compositePropertySource;
}
initCustomPolarisConfigFiles(compositePropertySource, configFileGroups);
polarisConfigFilePuller.initCustomPolarisConfigFiles(compositePropertySource, configFileGroups);
return compositePropertySource;
}
private void initInternalConfigFiles(CompositePropertySource compositePropertySource) {
List<ConfigFileMetadata> internalConfigFiles = getInternalConfigFiles();
for (ConfigFileMetadata configFile : internalConfigFiles) {
PolarisPropertySource polarisPropertySource = loadPolarisPropertySource(
configFile.getNamespace(), configFile.getFileGroup(), configFile.getFileName());
compositePropertySource.addPropertySource(polarisPropertySource);
polarisPropertySourceManager.addPropertySource(polarisPropertySource);
LOGGER.info("[SCT Config] Load and inject polaris config file. file = {}", configFile);
}
}
private List<ConfigFileMetadata> getInternalConfigFiles() {
String namespace = polarisContextProperties.getNamespace();
String serviceName = polarisContextProperties.getService();
if (!StringUtils.hasText(serviceName)) {
serviceName = environment.getProperty("spring.application.name");
}
List<ConfigFileMetadata> internalConfigFiles = new LinkedList<>();
// priority: application-${profile} > application > boostrap-${profile} > boostrap
String[] activeProfiles = environment.getActiveProfiles();
for (String activeProfile : activeProfiles) {
if (!StringUtils.hasText(activeProfile)) {
continue;
}
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "application-" + activeProfile + ".properties"));
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "application-" + activeProfile + ".yml"));
}
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "application.properties"));
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "application.yml"));
for (String activeProfile : activeProfiles) {
if (!StringUtils.hasText(activeProfile)) {
continue;
}
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "bootstrap-" + activeProfile + ".properties"));
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "bootstrap-" + activeProfile + ".yml"));
}
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "bootstrap.properties"));
internalConfigFiles.add(new DefaultConfigFileMetadata(namespace, serviceName, "bootstrap.yml"));
return internalConfigFiles;
}
private void initCustomPolarisConfigFiles(CompositePropertySource compositePropertySource,
List<ConfigFileGroup> configFileGroups) {
String namespace = polarisContextProperties.getNamespace();
for (ConfigFileGroup configFileGroup : configFileGroups) {
String group = configFileGroup.getName();
if (!StringUtils.hasText(group)) {
throw new IllegalArgumentException("polaris config group name cannot be empty.");
}
List<String> files = configFileGroup.getFiles();
if (CollectionUtils.isEmpty(files)) {
return;
}
for (String fileName : files) {
PolarisPropertySource polarisPropertySource = loadPolarisPropertySource(namespace, group, fileName);
compositePropertySource.addPropertySource(polarisPropertySource);
polarisPropertySourceManager.addPropertySource(polarisPropertySource);
LOGGER.info(
"[SCT Config] Load and inject polaris config file success. namespace = {}, group = {}, fileName = {}",
namespace, group, fileName);
}
}
}
private PolarisPropertySource loadPolarisPropertySource(String namespace, String group, String fileName) {
ConfigKVFile configKVFile;
// unknown extension is resolved as properties file
if (ConfigFileFormat.isPropertyFile(fileName)
|| ConfigFileFormat.isUnknownFile(fileName)) {
configKVFile = configFileService.getConfigPropertiesFile(namespace, group, fileName);
}
else if (ConfigFileFormat.isYamlFile(fileName)) {
configKVFile = configFileService.getConfigYamlFile(namespace, group, fileName);
}
else {
LOGGER.warn("[SCT Config] Unsupported config file. namespace = {}, group = {}, fileName = {}", namespace,
group, fileName);
throw new IllegalStateException("Only configuration files in the format of properties / yaml / yaml"
+ " can be injected into the spring context");
}
Map<String, Object> map = new ConcurrentHashMap<>();
for (String key : configKVFile.getPropertyNames()) {
map.put(key, configKVFile.getProperty(key, null));
}
return new PolarisPropertySource(namespace, group, fileName, configKVFile, map);
}
}

@ -50,6 +50,12 @@ public class PolarisConfigProperties {
*/
private boolean autoRefresh = true;
/**
* When the local configuration is consistent with the remote configuration, whether to
* preferentially load the remote configuration.
*/
private boolean preference = true;
/**
* List of injected configuration files.
*/
@ -95,4 +101,11 @@ public class PolarisConfigProperties {
this.groups = groups;
}
public boolean isPreference() {
return preference;
}
public void setPreference(boolean preference) {
this.preference = preference;
}
}

@ -1,43 +1,36 @@
package com.tencent.cloud.polaris.config.configdata;
import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicBoolean;
import com.tencent.cloud.polaris.config.adapter.PolarisConfigFilePuller;
import com.tencent.cloud.polaris.config.adapter.PolarisPropertySource;
import com.tencent.cloud.polaris.config.adapter.PolarisPropertySourceManager;
import com.tencent.cloud.polaris.config.config.ConfigFileGroup;
import com.tencent.cloud.polaris.config.config.PolarisConfigProperties;
import com.tencent.cloud.polaris.config.enums.ConfigFileFormat;
import com.tencent.cloud.polaris.context.config.PolarisContextProperties;
import com.tencent.polaris.client.api.SDKContext;
import com.tencent.polaris.configuration.api.core.ConfigFileMetadata;
import com.tencent.polaris.configuration.api.core.ConfigFileService;
import com.tencent.polaris.configuration.api.core.ConfigKVFile;
import com.tencent.polaris.configuration.client.internal.DefaultConfigFileMetadata;
import com.tencent.polaris.configuration.factory.ConfigFileServiceFactory;
import org.apache.commons.logging.Log;
import org.springframework.boot.ConfigurableBootstrapContext;
import org.springframework.boot.context.config.ConfigData;
import org.springframework.boot.context.config.ConfigDataLoader;
import org.springframework.boot.context.config.ConfigDataLoaderContext;
import org.springframework.boot.context.config.ConfigDataResourceNotFoundException;
import org.springframework.boot.context.config.Profiles;
import org.springframework.boot.logging.DeferredLogFactory;
import org.springframework.core.env.CompositePropertySource;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;
import java.io.IOException;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import static org.springframework.boot.context.config.ConfigData.Option.IGNORE_IMPORTS;
import static org.springframework.boot.context.config.ConfigData.Option.IGNORE_PROFILES;
import static org.springframework.boot.context.config.ConfigData.Option.PROFILE_SPECIFIC;
/**
* Implementation of {@link ConfigDataLoader}.can be used to load {@link ConfigData} for a given
* {@link PolarisConfigDataResource}
* {@link PolarisConfigDataResource} .
* <p>
* Load {@link ConfigData} via {@link PolarisConfigDataLoader}
*
@ -50,53 +43,91 @@ public class PolarisConfigDataLoader implements ConfigDataLoader<PolarisConfigDa
private final Log log;
private ConfigFileService configFileService;
private PolarisConfigFilePuller puller;
private static final AtomicBoolean INTERNAL_CONFIG_FILES_LOADED = new AtomicBoolean(false);
private static final AtomicBoolean CUSTOM_POLARIS_CONFIG_FILE_LOADED = new AtomicBoolean(false);
public PolarisConfigDataLoader(DeferredLogFactory logFactory) {
this.log = logFactory.getLog(getClass());
}
@Override
public ConfigData load(ConfigDataLoaderContext context, PolarisConfigDataResource resource)
throws IOException, ConfigDataResourceNotFoundException {
ConfigurableBootstrapContext bootstrapContext = context.getBootstrapContext();
throws ConfigDataResourceNotFoundException {
try {
return load(context.getBootstrapContext(), resource);
}
catch (Exception e) {
log.warn("Error getting properties from polaris: " + resource, e);
if (!resource.isOptional()) {
throw new ConfigDataResourceNotFoundException(resource, e);
}
return null;
}
}
public ConfigData load(ConfigurableBootstrapContext bootstrapContext, PolarisConfigDataResource resource) {
CompositePropertySource compositePropertySource = locate(bootstrapContext, resource);
return new ConfigData(compositePropertySource.getPropertySources(),
getOptions(context, resource));
return new ConfigData(compositePropertySource.getPropertySources(), getOptions(resource));
}
private CompositePropertySource locate(ConfigurableBootstrapContext bootstrapContext,
PolarisConfigDataResource resource) {
PolarisConfigDataResource resource) {
CompositePropertySource compositePropertySource = new CompositePropertySource(
POLARIS_CONFIG_PROPERTY_SOURCE_NAME);
SDKContext sdkContext = bootstrapContext.get(SDKContext.class);
ConfigFileService configFileService = ConfigFileServiceFactory.createConfigFileService(sdkContext);
PolarisConfigFilePuller puller = new PolarisConfigFilePuller(resource.getPolarisContextProperties()
,configFileService,
bootstrapContext.get(PolarisPropertySourceManager.class));
puller.initCustomPolarisConfigFile(compositePropertySource, configFileGroup(resource));
if (null == this.configFileService) {
this.configFileService = ConfigFileServiceFactory.createConfigFileService(sdkContext);
}
if (null == this.puller) {
this.puller = new PolarisConfigFilePuller(resource.getPolarisContextProperties(),
configFileService, bootstrapContext.get(PolarisPropertySourceManager.class));
}
Profiles profiles = resource.getProfiles();
if (INTERNAL_CONFIG_FILES_LOADED.compareAndSet(false, true)) {
log.info("loading internal config files");
this.puller.initInternalConfigFiles(compositePropertySource, profiles, resource.getServiceName());
}
PolarisConfigProperties polarisConfigProperties = resource.getPolarisConfigProperties();
if (!CollectionUtils.isEmpty(polarisConfigProperties.getGroups()) &&
CUSTOM_POLARIS_CONFIG_FILE_LOADED.compareAndSet(false, true)) {
log.info("loading custom config files");
this.puller.initCustomPolarisConfigFiles(compositePropertySource,
polarisConfigProperties.getGroups());
}
// load config data
if (StringUtils.hasText(resource.getFileName())) {
log.info("loading config data config file,group:" + resource.getGroupName() + "file:" + resource.getFileName());
this.puller.initCustomPolarisConfigFile(compositePropertySource, configFileGroup(resource));
}
return compositePropertySource;
}
private ConfigData.Option[] getOptions(ConfigDataLoaderContext context,
PolarisConfigDataResource resource) {
private ConfigData.Option[] getOptions(PolarisConfigDataResource resource) {
List<ConfigData.Option> options = new ArrayList<>();
options.add(IGNORE_IMPORTS);
options.add(IGNORE_PROFILES);
// mark it as 'PROFILE_SPECIFIC' config, it has higher priority,
// will override the none profile specific config.
options.add(PROFILE_SPECIFIC);
return options.toArray(new ConfigData.Option[0]);
PolarisConfigProperties polarisConfigProperties = resource.getPolarisConfigProperties();
if (polarisConfigProperties.isPreference()) {
// mark it as 'PROFILE_SPECIFIC' config, it has higher priority
options.add(PROFILE_SPECIFIC);
}
return options.toArray(new ConfigData.Option[]{});
}
private ConfigFileGroup configFileGroup(PolarisConfigDataResource polarisConfigDataResource) {
String fileName = polarisConfigDataResource.getFileName();
String serviceName = polarisConfigDataResource.getServiceName();
String groupName = polarisConfigDataResource.getGroupName();
ConfigFileGroup configFileGroup = new ConfigFileGroup();
configFileGroup.setName(serviceName);
configFileGroup.setName(groupName);
List<String> flies = new ArrayList<>();
flies.add(fileName);
configFileGroup.setFiles(flies);
return configFileGroup;
}
}

@ -1,5 +1,12 @@
package com.tencent.cloud.polaris.config.configdata;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.stream.Collectors;
import com.tencent.cloud.polaris.config.ConfigurationModifier;
import com.tencent.cloud.polaris.config.adapter.PolarisPropertySourceManager;
import com.tencent.cloud.polaris.config.config.PolarisConfigProperties;
@ -13,6 +20,7 @@ import com.tencent.polaris.client.api.SDKContext;
import com.tencent.polaris.factory.ConfigAPIFactory;
import com.tencent.polaris.factory.config.ConfigurationImpl;
import org.apache.commons.logging.Log;
import org.springframework.boot.BootstrapRegistry;
import org.springframework.boot.ConfigurableBootstrapContext;
import org.springframework.boot.context.config.ConfigDataLocation;
@ -27,19 +35,11 @@ import org.springframework.boot.context.properties.bind.Binder;
import org.springframework.boot.logging.DeferredLogFactory;
import org.springframework.core.Ordered;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.stream.Collectors;
/**
* Implementation of {@link ConfigDataLocationResolver}, used to resolve {@link ConfigDataLocation locations}
* into one or more {@link PolarisConfigDataResource polarisConfigDataResource}.
*
* @author wlx
* @date 2022/7/5 11:16
*/
public class PolarisConfigDataLocationResolver implements
ConfigDataLocationResolver<PolarisConfigDataResource>, Ordered {
@ -48,20 +48,29 @@ public class PolarisConfigDataLocationResolver implements
/**
* Prefix for Config Server imports.
*/
public static final String PREFIX = "polaris:";
public static final String PREFIX = "polaris";
/**
* Prefix for Polaris configurationProperties.
* Prefix for Polaris configurationProperties.
*/
public static final String POLARIS_PREFIX = "spring.cloud.polaris";
/**
* COLON.
*/
public static final String COLON = ":";
/**
* Empty String.
*/
public static final String EMPTY_STRING = "";
private final Log log;
public PolarisConfigDataLocationResolver(DeferredLogFactory logFactory) {
this.log = logFactory.getLog(getClass());
}
@Override
public boolean isResolvable(ConfigDataLocationResolverContext context, ConfigDataLocation location) {
if (!location.hasPrefix(PREFIX)) {
@ -101,7 +110,8 @@ public class PolarisConfigDataLocationResolver implements
POLARIS_PREFIX
);
prepareAndInitPolaris(resolverContext, polarisConfigProperties, polarisContextProperties);
// prepare and init earlier Polaris SDKContext to pull config files from remote.
prepareAndInitEarlierPolarisSdkContext(resolverContext, polarisConfigProperties, polarisContextProperties);
bootstrapContext.registerIfAbsent(PolarisConfigProperties.class,
BootstrapRegistry.InstanceSupplier.of(polarisConfigProperties));
@ -112,15 +122,14 @@ public class PolarisConfigDataLocationResolver implements
bootstrapContext.registerIfAbsent(PolarisPropertySourceManager.class,
BootstrapRegistry.InstanceSupplier.of(new PolarisPropertySourceManager()));
// stop sdkContext and register PolarisPropertySourceManager to context
bootstrapContext.addCloseListener(
event -> {
// destroy earlier Polaris sdkContext
event.getBootstrapContext().get(SDKContext.class).destroy();
// register PolarisPropertySourceManager to context
PolarisPropertySourceManager polarisPropertySourceManager = event.getBootstrapContext().get(PolarisPropertySourceManager.class);
event.getApplicationContext().getBeanFactory().registerSingleton(
"polarisPropertySourceManager",
event.getBootstrapContext().get(PolarisPropertySourceManager.class)
);
"polarisPropertySourceManager", polarisPropertySourceManager);
}
);
@ -133,8 +142,7 @@ public class PolarisConfigDataLocationResolver implements
return -1;
}
public <T> T loadPolarisConfigProperties(
protected <T> T loadPolarisConfigProperties(
ConfigDataLocationResolverContext context,
Class<T> typeClass,
String prefix) {
@ -143,27 +151,19 @@ public class PolarisConfigDataLocationResolver implements
T instance;
if (context.getBootstrapContext().isRegistered(typeClass)) {
instance = context.getBootstrapContext()
.get(typeClass);
instance = context.getBootstrapContext().get(typeClass);
}
else {
instance = binder
.bind(POLARIS_PREFIX, Bindable.of(typeClass),
bindHandler)
.map(properties -> binder
.bind(prefix,
Bindable.ofInstance(properties), bindHandler)
instance = binder.bind(prefix, Bindable.of(typeClass), bindHandler)
.map(properties -> binder.bind(prefix, Bindable.ofInstance(properties), bindHandler)
.orElse(properties))
.orElseGet(() -> binder
.bind(prefix,
Bindable.of(typeClass), bindHandler)
.orElseGet(() -> binder.bind(prefix, Bindable.of(typeClass), bindHandler)
.orElseGet(null));
}
return instance;
}
private BindHandler getBindHandler(ConfigDataLocationResolverContext context) {
private BindHandler getBindHandler(ConfigDataLocationResolverContext context) {
return context.getBootstrapContext().getOrElse(BindHandler.class, null);
}
@ -171,56 +171,70 @@ public class PolarisConfigDataLocationResolver implements
ConfigDataLocation location,
Profiles profiles,
PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties
) {
PolarisContextProperties polarisContextProperties) {
List<PolarisConfigDataResource> result = new ArrayList<>();
boolean optional = location.isOptional();
String fileName = location.getNonPrefixedValue(PREFIX);
String groupFileName = getRealGroupFileName(location);
String serviceName = loadPolarisConfigProperties(resolverContext,
String.class, "spring.application.name");
String groupName = StringUtils.isBlank(groupFileName) ? EMPTY_STRING : parseGroupName(groupFileName, serviceName);
log.info("group from configDataLocation is" + groupName);
String fileName = StringUtils.isBlank(groupFileName) ? EMPTY_STRING : parseFileName(groupFileName);
log.info("file from configDataLocation is" + fileName);
PolarisConfigDataResource polarisConfigDataResource = new PolarisConfigDataResource(
polarisConfigProperties,
polarisContextProperties,
profiles, optional,
fileName,serviceName
fileName, groupName, serviceName
);
result.add(polarisConfigDataResource);
return result;
}
private String getRealGroupFileName(ConfigDataLocation location) {
String prefixedValue = location.getNonPrefixedValue(PREFIX);
if (StringUtils.isBlank(prefixedValue) || !prefixedValue.startsWith(COLON)) {
return prefixedValue;
}
return prefixedValue.substring(1);
}
private String parseFileName(String groupFileName) {
String[] split = groupFileName.split(COLON);
if (split.length > 1) {
return split[1];
}
else {
return split[0];
}
}
private String parseGroupName(String groupFileName, String serviceName) {
String[] split = groupFileName.split(COLON);
if (split.length > 1) {
return split[0];
}
else {
return serviceName;
}
}
private void prepareAndInitPolaris(ConfigDataLocationResolverContext resolverContext,
PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
private void prepareAndInitEarlierPolarisSdkContext(ConfigDataLocationResolverContext resolverContext,
PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
ConfigurableBootstrapContext bootstrapContext = resolverContext.getBootstrapContext();
if (!bootstrapContext.isRegistered(SDKContext.class)) {
SDKContext sdkContext = sdkContext(resolverContext,
polarisConfigProperties, polarisContextProperties);
sdkContext.init();
bootstrapContext.register(SDKContext.class,
BootstrapRegistry.InstanceSupplier.of(sdkContext));
bootstrapContext.register(SDKContext.class, BootstrapRegistry.InstanceSupplier.of(sdkContext));
}
}
private List<PolarisConfigModifier> modifierList(PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
// add ModifyAddress and ConfigurationModifier to load SDKContext
List<PolarisConfigModifier> modifierList = new ArrayList<>();
ModifyAddress modifyAddress = new ModifyAddress();
modifyAddress.setProperties(polarisContextProperties);
ConfigurationModifier configurationModifier = new ConfigurationModifier(polarisConfigProperties,
polarisContextProperties);
modifierList.add(modifyAddress);
modifierList.add(configurationModifier);
return modifierList;
}
private SDKContext sdkContext(ConfigDataLocationResolverContext resolverContext,
PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
// 1. Read user-defined polaris.yml configuration
ConfigurationImpl configuration = (ConfigurationImpl) ConfigAPIFactory
@ -247,6 +261,18 @@ public class PolarisConfigDataLocationResolver implements
return SDKContext.initContextByConfig(configuration);
}
private List<PolarisConfigModifier> modifierList(PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties) {
// add ModifyAddress and ConfigurationModifier to load SDKContext
List<PolarisConfigModifier> modifierList = new ArrayList<>();
ModifyAddress modifyAddress = new ModifyAddress();
modifyAddress.setProperties(polarisContextProperties);
ConfigurationModifier configurationModifier = new ConfigurationModifier(polarisConfigProperties,
polarisContextProperties);
modifierList.add(modifyAddress);
modifierList.add(configurationModifier);
return modifierList;
}
}

@ -1,98 +1 @@
package com.tencent.cloud.polaris.config.configdata;
import com.tencent.cloud.polaris.config.config.PolarisConfigProperties;
import com.tencent.cloud.polaris.context.config.PolarisContextProperties;
import org.springframework.boot.context.config.ConfigData;
import org.springframework.boot.context.config.ConfigDataResource;
import org.springframework.boot.context.config.Profiles;
import java.util.Objects;
/**
* A polaris configData resource from which {@link ConfigData} can be loaded.
*
* @author wlx
* @date 2022/7/5 11:13
*/
public class PolarisConfigDataResource extends ConfigDataResource {
private final PolarisConfigProperties polarisConfigProperties;
private final PolarisContextProperties polarisContextProperties;
private final Profiles profiles;
private final boolean optional;
private final String fileName;
private final String serviceName;
public PolarisConfigDataResource(PolarisConfigProperties polarisConfigProperties,
PolarisContextProperties polarisContextProperties,
Profiles profiles,
boolean optional,
String fileName,
String serviceName) {
this.polarisConfigProperties = polarisConfigProperties;
this.polarisContextProperties = polarisContextProperties;
this.profiles = profiles;
this.optional = optional;
this.fileName = fileName;
this.serviceName = serviceName;
}
public PolarisConfigProperties getPolarisConfigProperties() {
return polarisConfigProperties;
}
public PolarisContextProperties getPolarisContextProperties() {
return polarisContextProperties;
}
public Profiles getProfiles() {
return profiles;
}
public boolean isOptional() {
return optional;
}
public String getFileName() {
return fileName;
}
public String getServiceName() {
return serviceName;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
PolarisConfigDataResource that = (PolarisConfigDataResource) o;
return optional == that.optional &&
polarisConfigProperties.equals(that.polarisConfigProperties) &&
polarisContextProperties.equals(that.polarisContextProperties) &&
profiles.equals(that.profiles) &&
fileName.equals(that.fileName) &&
serviceName.equals(that.serviceName);
}
@Override
public int hashCode() {
return Objects.hash(polarisConfigProperties, polarisContextProperties, profiles, optional, fileName, serviceName);
}
@Override
public String toString() {
return "PolarisConfigDataResource{" +
"polarisConfigProperties=" + polarisConfigProperties +
", polarisContextProperties=" + polarisContextProperties +
", profiles=" + profiles +
", optional=" + optional +
", fileName='" + fileName + '\'' +
", serviceName='" + serviceName + '\'' +
'}';
}
}
package com.tencent.cloud.polaris.config.configdata; import java.util.Objects; import com.tencent.cloud.polaris.config.config.PolarisConfigProperties; import com.tencent.cloud.polaris.context.config.PolarisContextProperties; import org.springframework.boot.context.config.ConfigData; import org.springframework.boot.context.config.ConfigDataResource; import org.springframework.boot.context.config.Profiles; /** * A polaris configData resource from which {@link ConfigData} can be loaded. * * @author wlx * @date 2022/7/5 11:13 下午 */ public class PolarisConfigDataResource extends ConfigDataResource { private final PolarisConfigProperties polarisConfigProperties; private final PolarisContextProperties polarisContextProperties; private final Profiles profiles; private final boolean optional; private final String fileName; private final String groupName; private final String serviceName; public PolarisConfigDataResource(PolarisConfigProperties polarisConfigProperties, PolarisContextProperties polarisContextProperties, Profiles profiles, boolean optional, String fileName, String groupName, String serviceName) { this.polarisConfigProperties = polarisConfigProperties; this.polarisContextProperties = polarisContextProperties; this.profiles = profiles; this.optional = optional; this.fileName = fileName; this.groupName = groupName; this.serviceName = serviceName; } public PolarisConfigProperties getPolarisConfigProperties() { return polarisConfigProperties; } public PolarisContextProperties getPolarisContextProperties() { return polarisContextProperties; } public Profiles getProfiles() { return profiles; } public boolean isOptional() { return optional; } public String getFileName() { return fileName; } public String getGroupName() { return groupName; } public String getServiceName() { return serviceName; } @Override public boolean equals(Object o) { if (this == o) { return true; } if (o == null || getClass() != o.getClass()) { return false; } PolarisConfigDataResource that = (PolarisConfigDataResource) o; return optional == that.optional && polarisConfigProperties.equals(that.polarisConfigProperties) && polarisContextProperties.equals(that.polarisContextProperties) && profiles.equals(that.profiles) && fileName.equals(that.fileName) && groupName.equals(that.groupName) && serviceName.equals(that.serviceName); } @Override public int hashCode() { return Objects.hash(polarisConfigProperties, polarisContextProperties, profiles, optional, fileName, groupName, serviceName); } }

@ -41,7 +41,7 @@ import org.springframework.core.env.PropertySource;
import static org.mockito.Mockito.when;
/**
* test for {@link PolarisConfigFileLocator}
* test for {@link PolarisConfigFileLocator}.
*@author lepdou 2022-06-11
*/
@RunWith(MockitoJUnitRunner.class)

@ -38,7 +38,7 @@ import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
/**
* test for {@link PolarisPropertySourceAutoRefresher}
* test for {@link PolarisPropertySourceAutoRefresher}.
*@author lepdou 2022-06-11
*/
@RunWith(MockitoJUnitRunner.class)

@ -5,7 +5,8 @@
<parent>
<artifactId>spring-cloud-tencent-examples</artifactId>
<groupId>com.tencent.cloud</groupId>
<version>1.6.0-2021.0.3-SNAPSHOT</version>
<version>${revision}</version>
<relativePath>../pom.xml</relativePath>
</parent>
<modelVersion>4.0.0</modelVersion>

@ -0,0 +1,56 @@
/*
* Tencent is pleased to support the open source community by making Spring Cloud Tencent available.
*
* Copyright (C) 2019 THL A29 Limited, a Tencent company. All rights reserved.
*
* Licensed under the BSD 3-Clause License (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://opensource.org/licenses/BSD-3-Clause
*
* 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 com.tencent.cloud.polaris.config.example;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.core.env.Environment;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* the endpoint for get config.
*
* @author lepdou 2022-03-10
*/
@RestController
@RefreshScope
public class ConfigController {
@Value("${timeout:1000}")
private int timeout;
@Autowired
private Person person;
@Autowired
private Environment environment;
@GetMapping("/timeout")
public int timeout() {
environment.getProperty("timeout", "1000");
return timeout;
}
@GetMapping("/person")
public String person() {
return person.toString();
}
}

@ -0,0 +1,58 @@
/*
* Tencent is pleased to support the open source community by making Spring Cloud Tencent available.
*
* Copyright (C) 2019 THL A29 Limited, a Tencent company. All rights reserved.
*
* Licensed under the BSD 3-Clause License (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://opensource.org/licenses/BSD-3-Clause
*
* 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 com.tencent.cloud.polaris.config.example;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
/**
* example property object.
*
* @author lepdou 2022-03-28
*/
@Component
@ConfigurationProperties(prefix = "teacher")
public class Person {
private String name;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public String toString() {
return "User{" + "name='" + name + '\'' + ", age=" + age + '}';
}
}

@ -0,0 +1,48 @@
/*
* Tencent is pleased to support the open source community by making Spring Cloud Tencent available.
*
* Copyright (C) 2019 THL A29 Limited, a Tencent company. All rights reserved.
*
* Licensed under the BSD 3-Clause License (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://opensource.org/licenses/BSD-3-Clause
*
* 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 com.tencent.cloud.polaris.config.example;
import com.tencent.cloud.polaris.config.annotation.PolarisConfigKVFileChangeListener;
import com.tencent.cloud.polaris.config.listener.ConfigChangeEvent;
import org.springframework.stereotype.Component;
import java.util.Set;
/**
* Custom Config Listener Example .
*
* @author Palmer Xu 2022-06-06
*/
@Component
public final class PersonConfigChangeListener {
/**
* PolarisConfigKVFileChangeListener Example .
* @param event instance of {@link ConfigChangeEvent}
*/
@PolarisConfigKVFileChangeListener(interestedKeyPrefixes = "teacher")
public void onChange(ConfigChangeEvent event) {
Set<String> changedKeys = event.changedKeys();
for (String changedKey : changedKeys) {
System.out.printf("%s = %s \n", changedKey, event.getChange(changedKey));
}
}
}

@ -1,8 +1,8 @@
server:
port: 48084
port: 48085
spring:
application:
name: polaris-config-example
name: polaris-config-data-example
cloud:
polaris:
address: grpc://183.47.111.80:8091
@ -14,7 +14,7 @@ spring:
files: [ "config/application.properties", "config/bootstrap.yml" ]
config:
import:
- optional:polaris:application.properties
- optional:polaris
management:
endpoints:
web:

Loading…
Cancel
Save