SpringCloud使用Consul作为配置中心
目录
- 一、前言
- 二、初始化配置
- 三、代码练习
- 1. 创建cloud-consul-configdemo8007项目
- 2. 修改配置
- 3. 添加主启动类
- 4. 读取配置文件
- 5. 添加controller
- 6. 启动测试
- 7. 动态刷新配置
- 四、application.yml与bootstrap.yml的区别
- 1. 不使用bootstrap的后果
- 2. 两个的区别
- 3. 测试application和bootstrap
- 4. 使用注意
- 5. 区分环境
- 五、总结
一、前言
什么是配置中心?
微服务意味着要将单体应用中的业务拆分成一个个子服务,这些服务都需要必要配置信息才能运行,每个微服务都包含一个类似application.yml的配置文件,单个管理显得极其麻烦,于是集中式的管理思想诞生了,该思想旨在微服务模块之外提供一个集中化的外部配置支持平台,为每个微服务提供配置支持,这个平台称为配置中心。
Spring Cloud Config配置中心?
Spring Cloud Config
就是最早期cloud当中的配置中心,但是需要配合git,svn
或外部存储(例如各种数据库),且需要配合Spring Cloud Bus
实现配置刷新。
Consul注册中心
在https://blog.csdn.net/weixin_43888891/article/details/125511531这一篇文章我们学习了
Spring Cloud Consul
作为注册中心的使用方案,且作为Spring Cloud官方推荐替换Eureka 注册中心的方案。
Consul配置中心
Spring Cloud
官方还声明 Consul
可以作为 Spring Cloud Config
配置中心的替代方案。并且不需要额外的git、svn、数据库等配合,且无需配合Bus即可实现配置刷新
。
Consul
使用Go
语言编写,因此具有天然可移植性(支持Linux,Windows和Mac OS);安装包仅包含一个可执行文件,方便部署,与Docker
等轻量级容器可无缝配合。
什么是配置刷新?
所谓配置刷新就是consul配置文件一旦修改,我们应用能立马拿到最新的配置!就比如我们程序有时候经常遇到调用第三方程序接口,我们可以将接口地址配置到注册中心,假如哪天第三方域名修改了,我们不需要重启服务,只需要修改配置中心的配置即可,然后程序能立马拿到最新的访问地址。
Consul 官网:https://www.consul.io/
Consul 官网下载地址:https://www.consul.io/downloads
二、初始化配置
使用Consul作为配置中心,第一步我们先创建目录,把配置信息存储至Consul,点击菜单Key/Value 再点击Create 按钮。
1.创建 config/ 基本目录,可以理解为配置文件所在的最外层文件夹。
这个是官网提出的:
cloud官网:https://docs.spring.io/spring-cloud-consul/docs/current/reference/html/#spring-cloud-consul-config
为什么要用config作为根目录?
consul给我们提供的是key/value存储,也就意味着不仅仅可以存储配置文件,还可以进行存储别的东西,所以这里官网也是提出使用config作为根目录。
2.接下来在config下创建以下文件夹,这些文件夹代表的是应用文件夹,而并不是真正的配置文件!
orderService-dev就代表的是orderService服务的dev环境的应用文件夹。官网 提出的config/testApp, dev/
,服务与环境区分使用逗号分割
,读consul的配置的时候默认也是逗号,但是逗号比较丑,我们这里用的-分割,然后我们在读取consul的服务配置文件声明使用-分割即可。
3.创建配置文件,创建文件的时候不带/就是创建文件
在每个应用文件夹下创建配置文件,这里可以选择格式,我使用的YAML格式,注意这里是有语法校验的,假如有空格什么的都会报错的,建议在ider的yml文件写好配置后再进行复制到里面。
配置文件当中的name没有实质意义,就是为了测试 获取不同环境的配置。所以我们每个配置文件当中的name设置成不一样的。
假设以上内容为订单微服务的配置信息,下面我们通过案例来加载Consul配置中心中的配置信息。
三、代码练习
本篇文章采用了maven聚合工程,搭建父工程这些我就不记录了,完全是基于https://blog.csdn.net/weixin_43888891/article/details/125267683文章的项目进行开发的,具体参考这一篇文章!
git源码:https://gitee.com/gzl_com/spring-cloud.git
1. 创建cloud-consul-configdemo8007项目
2. 修改配置
修改pom:
<dependencies><!--spring cloud consul discovery 服务发现依赖 --><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-consul-discovery</artifactId></dependency><!--spring cloud consul config 配置中心依赖 --><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-consul-config</artifactId></dependency><!-- SpringBoot整合Web组件 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><!-- 健康检查 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-actuator</artifactId></dependency><!-- 使用@ConfigurationProperties注解警告的问题 --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-configuration-processor</artifactId><optional>true</optional></dependency><!--日常通用jar包配置--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-devtools</artifactId><scope>runtime</scope><optional>true</optional></dependency><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope></dependency>
</dependencies>
添加 bootstrap.yml
server:port: 8007 # 端口spring:application:name: config-demo # 应用名称profiles:active: dev # 指定环境,默认加载default环境cloud:consul:# Consul 服务器地址host: localhostport: 8500# 配置中心相关配置config:# 是否启用配置中心,默认值 true 开启enabled: true# 设置配置的基本文件夹,默认值config 可以理解为配置文件所在的最外层文件夹prefix: config# 设置应用的文件夹名称,默认值application 一般建议设置为微服务应用名称default-context: orderService# 配置环境分隔符,默认值","和default-context配置项搭配# 例如应用orderService 分别有环境 default, dev, test, prod# 只需 config 文件下创建 orderService, orderService-dev, orderService-test, orderService-prod文件夹profile-separator: '-'# 指定配置格式为yamLformat: yaml# Consul Key/Values 中的Key, Value 对应整个配置文件data-key: orderServiceConfig# 以上配置可以理解为:加载 config/orderService/ 文件夹下Key 为orderServiceConfig 的Value 对应的配置watch:# 是否开启自动刷新,默认值true 开启enabled: true# 刷新频率,单位:毫秒,默认值1000delay: 1000discovery:register: true # 是否需要注册instance-id: ${spring.application.name}-01 # 注册实例id(必须唯一)service-name: ${spring.application.name} # 服务名称port: ${server.port} # 服务端口(默认就是当前服务端口)prefer-ip-address: true # 是否使用ip地址注册(开启后可以在web界面看到实例ip)ip-address: ${spring.cloud.client.ip-address} # 服务请求ip(默认就是当前服务ip)
3. 添加主启动类
@EnableDiscoveryClient
这个注解是服务发现使用的,但是经过试验,当不使用这个注解注册中心照样能注册进去,并且使用RestTemplate
通过服务名称调用服务的时候也没有发现什么问题。所以我怀疑只要是加入了consul服务发现的依赖和配置了consul,就自动开启了,有没有这个注解都可以,针对于这个问题,我专门看了一下我们实际开发当中的项目,他启动类也带了这个注解,所以建议还是加上。
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;@SpringBootApplication
@EnableDiscoveryClient
public class ConfigDemoMain8007 {public static void main(String[] args) {SpringApplication.run(ConfigDemoMain8007.class, args);}
}
4. 读取配置文件
一般读取yml当中的配置文件的方式有两种,一种是使用@ConfigurationProperties
注解以前缀的形式注入到bean当中,一种是以@Value("${name}")
注解的形式注入到属性当中。本篇案例这两种都会练习。
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;@Component
@ConfigurationProperties(prefix = "mysql")
@Data
public class MysqlProperties {private String host;private Integer port;private String username;private String password;
}
5. 添加controller
import com.gzl.cn.config.MysqlProperties;
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.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;@RefreshScope
@RestController
public class ConfigController {@Autowiredprivate MysqlProperties mysqlProperties;@Value("${name}")private String name;@GetMapping("/name")public String getName() {return name;}@GetMapping("/mysql")public MysqlProperties getMysqlProperties() {return mysqlProperties;}
}
最终结构:
6. 启动测试
观察注册中心的服务,已经成功注册上了!
访问:http://localhost:8007/mysql
在项目的配置文件当中我们并没有配置mysql相关属性,访问接口的时候读出来的配置就是从consul上读取的配置。
访问:http://localhost:8007/name
访问出来的name是:order-service-dev,原因就是我们bootstrap的profiles是设置的dev环境。假如设置test就是读取的test的配置
假如我们不设置profiles,读取的就是不带环境的应用名称配置:
7. 动态刷新配置
现在配置文件读取的是dev的,假如修改dev配置环境的配置,过个几秒就会动态刷新配置。所谓动态刷新就是consul配置文件一旦修改,我们应用能立马拿到最新的配置!
动态刷新的时候控制台会有打印日志的,当日志出来之后我们再去访问获取配置的接口,会发现配置已经是最新的了。
Consul 使用 Spring 定时任务 Spring TaskScheduler
来监听配置文件的更新。
默认情况下,它是一个定时任务线程池ThreadPoolTaskScheduler ,其poolSize值为1,要更改TaskScheduler
,请创建-TaskScheduler
用 ConsulConfigAutoConfiguration. CONFIG_WATCH_TASK_SCHEDULER_NAME
常量命名的bean类型,下图是官网说明:
如果 consul 不可用于配置,在某些情况下(如本地开发或某些测试场景)可能会很方便。设置spring.cloud.consul.config.fail-fast=false
将导致配置模块记录警告而不是抛出异常。这将允许应用程序继续正常启动。
四、application.yml与bootstrap.yml的区别
Spring Boot 默认支持 properties(.properties)
和 YAML(.yml .yaml)
两种格式的配置文件,yml和 properties文件都属于配置文件,功能一样。
Spring Cloud 构建于 Spring Boot 之上, 在 Spring Boot 中有两种上下文,一种是bootstrap
,另外一种是 application
。
1. 不使用bootstrap的后果
在springcloud官网,使用consul的案例当中,反复在提示这一句话,那么这到底是为什么呢?
首先在上面示例当中我使用的是bootstrap.yml,并没有使用application.yml,那么使用application.yml到底会有什么后果?
通过将bootstrap改为application后,项目直接启动报错。
在上一篇我写的Consul作为注册中心文章当中,并没有用bootstrap,而是用的application,项目照样运行正常,他和本篇项目最大的区别就是使用了consul的key/value配置,那也就意味着,consul配置中心相关的配置,必须要放到bootstrap.yml当中,下面我们会进行证实这个问题。
2. 两个的区别
区别:
bootstrap.yml
和application.yml
都可以用来配置参数。- bootstrap.yml 用来程序引导时执行,
应用于更加早期配置信息读取
。可以理解成系统级别的一些参数配置,这些参数一般是不会变动的。 - application.yml
可以用来定义应用级别的
, 应用程序特有配置信息,可以用来配置后续各个模块中需使用的公共参数等。如果搭配 config 使用,application.yml里面定义的文件可以实现动态替换
。
加载顺序:
- 若application.yml 和bootstrap.yml 在同-目录下:
bootstrap.yml 先加载,application.yml后加载
- bootstrap.yml 用于应用程序上下文的引导阶段。bootstrap.yml 由父Spring ApplicationContext加载。
属性覆盖问题:
- application.yml 与 bootstrap 存在相同的配置项,还是
会覆盖 bootstrap
,而 application.yml 里面的内容可以动态替换。
3. 测试application和bootstrap
针对于application和bootstrap两个配置文件的几个场景进行测试:
(1) 测试application和bootstrap属性覆盖的问题
关于覆盖的问题,可以拿上面的案例直接测试,创建application.yml,然后修改端口号为8008,直接启动项目,项目可以启动成功,并且端口是8008,而并没有取bootstrap.yml当中的端口,
证明application会覆盖了bootstrap配置的属性
。
(2) 测试在consul的配置文件当中配置了端口,bootstrap也配置了端口,application并没有配置端口
首先运行过程中修改consul当中的端口是不会影响程序的端口的
启动的时候,consul配置的端口会覆盖bootstrap配置的端口,最终会取consul的端口
(3) 测试在consul的配置文件当中配置了端口,bootstrap也配置了端口,application也配置端口
经过测试,发现也是取的consul的配置的端口
通过以上三次测试可以得出结论:consul配置 > application.yml > bootstrap.yml
4. 使用注意
假如我们用到了consul作为配置中心,最重要的一点就是,需要将consul配置中心的相关配置需要放到bootstrap.yml当中,为什么非得放到bootstrap当中?
以上面案例为准,我们的mysql相关配置并没有在项目配置文件配置,完全是基于consul的配置,那也就意味着必须要让consul优先加载,如果consul配置中心相关配置是在application当中,而不在bootstrap,就会导致在程序当中注入mysql相关配置的时候找不到,因为consul还没加载,所以我们必须要让consul的配置中心相关配置放到bootstrap当中。bootstrap会优先与application加载。
bootstrap.yml:
spring:cloud:consul:# Consul 服务器地址host: localhostport: 8500# 配置中心相关配置config:# 是否启用配置中心,默认值 true 开启enabled: true# 设置配置的基本文件夹,默认值config 可以理解为配置文件所在的最外层文件夹prefix: config# 设置应用的文件夹名称,默认值application 一般建议设置为微服务应用名称default-context: orderService# 配置环境分隔符,默认值","和default-context配置项搭配# 例如应用orderService 分别有环境 default, dev, test, prod# 只需 config 文件下创建 orderService, orderService-dev, orderService-test, orderService-prod文件夹profile-separator: '-'# 指定配置格式为yamLformat: yaml# Consul Key/Values 中的Key, Value 对应整个配置文件data-key: orderServiceConfig# 以上配置可以理解为:加载 config/orderService/ 文件夹下Key 为orderServiceConfig 的Value 对应的配置watch:# 是否开启自动刷新,默认值true 开启enabled: true# 刷新频率,单位:毫秒,默认值1000delay: 1000
application.yml:
正常来说除去consul配置中心的相关配置,其余配置是都可以放在consul当中的,就算完全不要application也是可以的。当然profiles.active还是有必要要的,他决定了取consul当中哪个配置文件。
server:port: 8009 # 端口spring:application:name: config-demo # 应用名称profiles:active: dev # 指定环境,默认加载default环境cloud:consul:discovery:register: true # 是否需要注册instance-id: ${spring.application.name}-01 # 注册实例id(必须唯一)service-name: ${spring.application.name} # 服务名称port: ${server.port} # 服务端口(默认就是当前服务端口)prefer-ip-address: true # 是否使用ip地址注册(开启后可以在web界面看到实例ip)ip-address: ${spring.cloud.client.ip-address} # 服务请求ip(默认就是当前服务ip)
5. 区分环境
在实际开发当中我们一般都会分为好几个环境,dev、prod、test,不要配置中心的时候还好区分,但是一旦有了配置中心,就意味着又多了个bootstrap.yml配置文件,那我们应该怎么应对多个环境的配置呢?
这是我们项目的方式:
bootstrap-test.properties
:就是单纯的放了consul的配置中心相关配置。application-dev.properties
:这个就是我们开发时候使用的配置文件,profiles设置为dev,开发的时候根本不使用consul配置中心,consul上的所有配置,在application-dev
上都有,这样就是为了避免共用consul配置,老是有人改consul上的配置。application.properties
:就是放了一些基本上不会改变的属性。- 我们用的是docker和jekins,然后发版的时候直接使用profiles设置为test,然后通过
docker run
命令,修改consul的地址。也就是bootstrap-test.properties
存的地址,实际上就是个测试环境的consul地址。
五、总结
HashiCorp 公司的Consul可谓是一款全能组件。可用于提供服务发现和服务配置的工具。用go语言开发,具有很好的可移植性,被Spring Cloud纳入其中。
在注册中心方面, Netflix Eureka停止新版本开发, Consul成为了优秀的可替代方案。
在配置中心方面, Consul 亦可替代 Spring Cloud Config作为配置中心使用,且无需配合Git, SVN等工具,无需配合Bus消息总线即可实现集群配置更新。
一旦使用consul的配置中心,那么配置中心相关配置一定要放到bootstrap.yml当中!
SpringCloud使用Consul作为配置中心相关推荐
- SpringCloud Consul Config 配置中心 (二)
上次配置中心启动命令为consul agent -dev,这样数据不会持久化,重新启动consul后key/value配置的信息会丢失. 实现数据持久化,使用如下命令启动,-data-dir 为数据保 ...
- consul作为配置中心
Conusl可以作为注册中心,也可以作为配置中心. 作为配置中心,使用起来也很方便,大多数都是配置. Consul的安装这里不说了,主要是说明java后端怎么使用,所以本次采用windows版本的co ...
- Consul作为配置中心,配置Asp.Net Core应用程序 依据key/value动态更新
Consul作为配置中心,配置Asp.Net Core应用程序 依据key/value自动更新 https://github.com/wintoncode/Winton.Extensions.Conf ...
- SpringCloud学习系列之四-----配置中心(Config)使用详解
前言 本篇主要介绍的是SpringCloud中的分布式配置中心(SpringCloud Config)的相关使用教程. SpringCloud Config Config 介绍 Spring Clou ...
- SpringCloud Consul Config 配置中心(一)
用 Consul 存储键值对,实现分布式配置中心,支持不需要重启配置中心服务就能读取更新后的属性. 在前面开发基础上,稍作调整,暂只调整日志服务. 1.在日志服务里添加maven依赖 <depe ...
- Spring Cloud 采用Consul做配置中心
-----------------pom.xml依赖,主要是spring-cloud-starter-consul-config <dependency><groupId>or ...
- springcloud 使用git作为配置中心
springcloud提供了一整微服务解决方案,在其组件体系中,有一个很重要的模块就是分布式配置中心 首先,需要明确一个配置中心提供的核心功能应该有什么 提供服务端和客户端支持 集中管理各环境的配置文 ...
- SpringCloud与SpringConfig分布式配置中心
Github上配置SpringCloud的配置文件: 问题 微服务意味着要将单体应用中的业务拆分成一个个子服务,每个服务的粒度相对较小,因此系统中会出现大量的服务.由于每个服务都需要必要的配置信息才能 ...
- SpringCloud 为什么需要使用配置中心
作者:波波烤鸭 https://dpb-bobokaoya-sm.blog.csdn.net 一. 为什么需要使用配置中心 1 服务配置的现状 2 常用的配置管理解决方案的缺点 3 为什么要使用 s ...
最新文章
- python学习-day2_课堂作业
- 树莓派 raspberry安全关机命令重启命令
- 当下全球最炙手可热的八位少年创业者
- poj 1873 枚举+凸包
- hibernate07--关联映射
- Java----代码优化篇
- lua虚拟机字节码修改_Java虚拟机(JVM)面试题大集合
- python input函数详解_对Python3中的input函数详解
- puppet详解(六)——exec资源详解
- UE4联网机制和多人游戏总结 (第一部分)
- ArcGIS软件中的坐标系及数据类型的概念
- linux下svn命令使用大全
- 【开箱】索尼A6000微单入手
- android动态设置渐变背景
- Bitmovin首席执行官Stefan:开发者正在构建视频产品的未来
- 合作创新,携手共赢 共筑坚实数字底座
- 从零开始搭建免费小程序商城
- java石头剪刀布界面_利用Java模拟石头剪刀布游戏
- log4j.properties详解与例子
- QQ/微信/支付宝 收款码 美化的教程 超级好看