我们之前开发项目时,需要用到非常多的配置文件,如数据库的配置信息、mapper.xml等。。。
但是这样会存在一个问题,如果我们的项目已经启动运行,那么数据库服务器的ip地址发生了改变,我们该怎么办?
这时我们需要重新修改我们的配置文件并且重启服务器,若数据库信息庞大,维护成本可想而知。
这时Spring Cloud Config可以为我们统一配置文件,以及实时同步更新,并不需要重新启动应用程序。
文章目录
提示:以下是本篇文章正文内容,下面案例可供参考
一、Spring Cloud Config 简介
SpringCloud Config为微服务架构中的微服务提供集中化的外部配置支持,配置服务器为各个不同微服务应用的所有环境提供了一个中心化的外部配置。
SpringCloud Config分为服务端和客户端两部分。
服务端也称为分布式配置中心,它是一个独立的微服务应用,用来连接配置服务器并为客户端提供获取配置信息,加密/解密信息等访问接口。
客户端则是通过指定的配置中心来管理应用资源,以及与业务相关的配置内容,并在启动的时候从配置中心获取和加载配置信息。
配置服务器默认采用git来存储配置信息,这样就有助于对环境配置进行版本管理,并且可以通过git客户端工具来方便的管理和访问配置内容
二、快速入门 – 搭建Config Server
1.准备3个配置文件,推送到Git服务器
准备3个文件(也可以使用yml文件):
microservice-dev.properties
microservice-prod.properties
microservice-test.properties
该文件的命名规则是:{application}-{profile}.properties
其内容是(另外2个文件内容稍有不同即可):
jdbc.driverClassName=com.mysql.jdbc.Driver
jdbc.url=jdbc:mysql://127.0.0.1:3306/test?useUnicode=true&characterEncoding=utf8&autoReconnect=true&allowMultiQueries=true
jdbc.username=root
jdbc.password=123456
2.创建工程microservice-config-server
导入pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.zpc.microservice</groupId>
<artifactId>microservice-config-server</artifactId>
<version>1.0-SNAPSHOT</version>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.6.RELEASE</version>
</parent>
<dependencyManagement>
<dependencies>
<!-- 导入Spring Cloud的依赖管理 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Finchley.SR1</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<!--整合配置中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-server</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
编写入口ConfigApplication
package com.zyc.config;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.config.server.EnableConfigServer;
@EnableConfigServer
@SpringBootApplication
public class ConfigServerApplication {
public static void main(String[] args) {
SpringApplication.run(ConfigServerApplication.class, args);
}
}
编写application.yml
server:
port: 7788 #服务端口
spring:
application:
name: config-server #指定服务名
cloud:
config:
server:
git: #配置git仓库地址
uri: https://gitee.com/strange_guest_in_silver/zyc.git
search-paths:
- zycfiles #配置文件目录地址
label: master #分支名称
启动测试
三、快速入门 – 搭建Config Client
导入pom依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-client</artifactId>
</dependency>
新建bootstrap.yml
spring:
cloud:
config:
uri: http://127.0.0.1:7788/ #配置中心的地址
profile: dev #对应配置服务中的{profile}
label: master #对应的分支
name: microservice
关于此配置中的name:
如果你仓库的propoties是以application开头的,则不用配置
编写JdbcConfigBean
编写对象通过@Value注解读取Config Server中的值。
package com.zyc.product.config;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.stereotype.Component;
@Component
public class JdbcConfigBean {
@Value("${jdbc.url}")
private String url;
@Value("${jdbc.username}")
private String username;
@Value("${jdbc.password}")
private String password;
@Value("${jdbc.driverClassName}")
private String driverClassName;
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getDriverClassName() {
return driverClassName;
}
public void setDriverClassName(String driverClassName) {
this.driverClassName = driverClassName;
}
@Override
public String toString() {
return "JdbcConfigBean [url=" + url + ", username=" + username
+ ", password=" + password + ", driverClassName="
+ driverClassName + "]";
}
}
编写测试方法进行测试
在Controller中增加testconfig方法:
package com.zyc.product.controller;
import com.zyc.product.config.JdbcConfigBean;
import com.zyc.product.entity.Product;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.List;
@RestController //http+restful+json
@RequestMapping("/product")
public class ProductController {
@Autowired
private JdbcConfigBean jdbcConfigBean;
@GetMapping(value = "testconfig")
public String testconfig(){
return this.jdbcConfigBean.toString();
}
}
启动测试:
测试结果显示,已经从Config Server中获取到配置文件的内容。
三、手动更新运行中的配置文件
如果git服务器中的配置文件更新了怎么办?正在运行的应用中的配置内容如何更新?
现在我们更改git服务器中的配置文件内容,端口改成8888:
然后刷新Config Server地址观察:
可以看到这里查询到的是新的数据,端口已经更新为8888。
但是在Config Client中测试:
看到依然是旧的数据。
如何才能在重启应用的情况下,获取到最新的配置文件内容呢? – 为Config Client添加refresh支持。
1.加入依赖,使用actuator 监控中心完成刷新功能:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
2.为JdbcConfigBean添加@RefreshScope注解
修改application.yml文件
#开启所有端点
management:
endpoints:
web:
exposure:
include: "*"
重启做测试:
刷新可以看到有配置文件内容更新了。
四、Config Client配置优化-注册到Eureka中
分析:
作为Config Client,在配置文件中了写死了Config Server的地址:
spring:
cloud:
config:
name: microservice #对应配置中心的应用名称,不写默认是本应用名,即spring.application.name
uri: http://127.0.0.1:7788/
profile: dev #对应配置服务中的{profile}
label: master #对应的分支
这样的硬编码是不好的,如果配置中心的ip地址发生了改变,那么久需要重新修改并且重启应用了。
想想,有什么好的办法解决呢? 如果将Config Server作为一个微服务,并且将其注册的Eureka中,是不是就可以不用硬编码了?
解决方案如下:
1.在 config-server中添加Eureka的依赖
<!--整合eureka客户端-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
2.修改application.yml文件
server:
port: 7788 #服务端口
spring:
application:
name: config-server #指定服务名
cloud:
config:
server:
git: #配置git仓库地址
uri: https://gitee.com/strange_guest_in_silver/zyc.git
search-paths:
- zycfiles #配置文件目录地址
label: master #分支名称
eureka:
client:
###因为该应用为服务提供者,是eureka的一个客户端,需要注册到注册中心
register-with-eureka: true
###是否需要从eureka上检索服务
fetch-registry: true
instance:
prefer-ip-address: true #将自己的ip地址注册到Eureka服务中
instance-id: ${
spring.application.name}###${server.port} #指定实例id
3.ConfigApplication添加@EnableEurekaClient注解
package com.zyc.config;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.config.server.EnableConfigServer;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
@EnableConfigServer
@SpringBootApplication
@EnableEurekaClient
public class ConfigServerApplication {
public static void main(String[] args) {
SpringApplication.run(ConfigServerApplication.class, args);
}
}
4.在service-product中修改bootstrap.yml配置
spring:
cloud:
config:
uri: http://127.0.0.1:7788/ #配置中心的地址
profile: dev #对应配置服务中的{profile}
label: master #对应的分支
# name: microservice
discovery:
enabled: true #启用发现服务功能
service-id: microservice-config-server #指定配置中心工程的名称
疑问:在application.yml中以及配置Eureka的信息,为什么在bootstrap.yml还需要配置?
因为在Spring Boot中bootstrap.yml在application.yml之前加载,所以即使在application.yml中以及配置Eureka的信息,是使用不了的,所以需要在bootstrap.yml中配置Eureka的信息。
5.测试
发post请求手动刷新:
查看最新配置:
测试结果,一切正常。这就完美解决了硬编码的问题。