了解config
随着微服务项目的不断扩大,微服务的各种配置文件也不断增多,如果某一基础服务配置信息变更,势必会引起一系列的更新和重启,导致很麻烦。为了使微服务众多实例的配置文件能够统一化管理,SpringCloud Config提供了一套解决方案,建立一个配置服务中心,每个实例从config server中获取具体的配置文件,它不仅支持本地,而且支持远程git仓库。
项目搭建
仿照springcloud-eureka-application创建springcloud-eureka-server、springcloud-config-server、springcloud-config-client,并集成好Erueka。然后在这个基础上做改造。
首先配置config-server端
在git仓库根目录中添加配置信息的保存目录:repository,我们新建三个不同环境的文件进行测试,分别为:config-client-dev.properties、config-client-test.properties、config-client-prod.properties
内容分别为:
message.value=dev-开发环境
message.value=test-测试环境
message.value=prod-生产环境
添加依赖:
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-server</artifactId>
</dependency>
主类上添加使能注解:
@EnableConfigServer
主要配置信息如下:
spring:
application:
name: config-server
cloud:
config:
server:
git:
uri: https://gitee.com/superbutton/spring-cloud-study.git #对应你的git仓库地址
search-paths: repository #配置中心git仓库路径
username: #访问git仓库的用户名(如果Git仓库为公开仓库,可以不填写用户名和密码,如果是私有仓库需要填写)
password: #访问git仓库的密码(如果Git仓库为公开仓库,可以不填写用户名和密码,如果是私有仓库需要填写)
label: develop #配置git仓库的分支
启动config-server进行测试,看看是否能够访问到三个配置文件:
http请求地址和资源文件映射如下:
/{application}/{profile}[/{label}]
eg: http://localhost:8081/config-client/test/develop
/{application}-{profile}.yml
/{label}/{application}-{profile}.yml
/{application}-{profile}.properties
eg:http://localhost:8081/config-client-test.properties
/{label}/{application}-{profile}.properties
eg:http://localhost:8081/develop/config-client-test.properties
这个时候我们看到如果有中文会出现乱码,使用如下方式解决:
(1) 添加编码处理类
package com.zh.cloud.handle.encode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.boot.env.OriginTrackedMapPropertySource;
import org.springframework.boot.env.PropertySourceLoader;
import org.springframework.core.env.PropertySource;
import org.springframework.core.io.Resource;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Properties;
public class CustomPropertySourceLoader implements PropertySourceLoader {
private static final Logger logger = LoggerFactory.getLogger(CustomPropertySourceLoader.class);
@Override
public String[] getFileExtensions() {
return new String[]{"properties", "xml"};
}
@Override
public List<PropertySource<?>> load(String name, Resource resource) throws IOException {
Map<String, ?> properties = loadProperties(resource);
if (properties.isEmpty()) {
return Collections.emptyList();
}
return Collections
.singletonList(new OriginTrackedMapPropertySource(name, properties));
}
private Map<String, ?> loadProperties(Resource resource) {
Properties properties = new Properties();
InputStream inputStream = null;
try {
inputStream = resource.getInputStream();
properties.load(new InputStreamReader(inputStream, StandardCharsets.UTF_8));
inputStream.close();
} catch (IOException e) {
logger.error("load inputstream failure...", e);
} finally {
if (inputStream != null) {
try {
inputStream.close();
} catch (IOException e) {
logger.error("close IO failure ....", e);
}
}
}
return (Map) properties;
}
}
(2) 在resources文件夹下面创建META-INF文件夹,文件夹下新建一个spring.factories文件,文件内容如下:
org.springframework.boot.env.PropertySourceLoader=com.zh.cloud.handle.encode.CustomPropertySourceLoader
注:CustomPropertySourceLoader要写全类名
(3) 重启查看乱码是否解决
配置config-client端
添加依赖:
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
特别注意,client端的配置文件要用:bootstrap.properties,不再是application.yml了
server.port=8082
spring.application.name=config-client
# EurekaServer地址
eureka.client.service-url.defaultZone=http://127.0.0.1:8080/eureka
eureka.instance.instance-id=config-client
# 当调用getHostname获取实例的hostname时,返回ip而不是host名称
eureka.instance.prefer-ip-address=true
# 指定自己的ip信息,不指定的话会自己寻找
eureka.instance.ip-address= 127.0.0.1
#配置git远程仓库的分支
spring.cloud.config.label=develop
#配置服务中心地址(即config-server的地址) #http://localhost:8081/ 没有用注册中心的话可以用这种
#spring.cloud.config.uri= http://localhost:80081/
#配置环境 dev为开发环境配置文件,test为测试环境,pro为正式环境
spring.cloud.config.profile=prod
spring.cloud.config.discovery.enabled=true
spring.cloud.config.discovery.service-id=config-server
添加获取配置的代码:
package com.zh.cloud.controller;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
@RestController
public class GetPropertiesInfo {
@Value("${message.value}") //配置文件要取的值对应的key
String message;
@RequestMapping("/getPropertyInfo")
public String getPropertyFromConfigServer() {
System.out.println(message);
return message;
}
}
访问查看结果:http://localhost:8082/getPropertyInfo
完整代码如下:
https://gitee.com/superbutton/spring-cloud-study/tree/develop/springcloud-config-application
我们将git上配置文件内容修改一下,然后再次进行访问,看到访问到的内容没有修改过来,这是因为只有config-server在启动的时候才会去加载git上的配置文件,所以没有重启我们是没法得到最新的配置信息的。这时消息总线(Spring Cloud Bus )的作用体现出来了。