Spring Cloud系列之Eureka
Spring Cloud系列之配置中心Config
Spring Cloud系列之gateway
Spring Cloud系列之Feign
Spring Cloud系列之Hystrix
Spring Cloud系列之鏈路追蹤
配置中心可以簡單的理解為一個服務(wù)模塊佑惠,開發(fā)人員或運維人員可以通過界面對配種中心進行配置,下面相關(guān)的微服務(wù)連接到配置中心上面就可以實時連接獲取到配置中心上面修改的參數(shù)齐疙。更新的方式一般有兩種
pull模式膜楷,服務(wù)定時去拉取配置中心的數(shù)據(jù)
push模式,服務(wù)一直連接到配置中心上剂碴,一旦配置有變成把将,配種中心將把變更的參數(shù)推送到對應(yīng)的微服務(wù)上
這兩種做法其實各有利弊
pull可以保證一定可以拉取得到數(shù)據(jù),pull一般采用定時拉取的方式忆矛,即使某一次出現(xiàn)網(wǎng)絡(luò)沒有拉取得到數(shù)據(jù)察蹲,那在下一次定時器也將可以拉取得到數(shù)據(jù),最終保證能更新得到配置
push也有好處催训,避免pull定時器獲取存在時延洽议,基本可以做到準(zhǔn)實時的更新,但push也存在問題漫拭,如果有網(wǎng)絡(luò)抖動亚兄,某一次push沒有推送成功,將丟失這次配置的更新
目前比較流行的配種中心開源組件有Spring Cloud Config采驻,百度的disconf审胚,阿里的Nacos,還有攜程的apollo礼旅。
實現(xiàn)原理大同小異
實踐
config server搭建
- 引入依賴
<?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">
<parent>
<artifactId>dy-springcloud</artifactId>
<groupId>com.dy</groupId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<modelVersion>4.0.0</modelVersion>
<groupId>com.dy</groupId>
<artifactId>config-server</artifactId>
<dependencies>
<!--config server端依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-config-server</artifactId>
</dependency>
<!--config server端也注冊到注冊中心-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
</dependencies>
</project>
- 配置文件
#eureka 參數(shù)配置
eureka:
# 此實例注冊到eureka服務(wù)端的唯一的實例ID,其組成為${spring.application.name}:${spring.application.instance_id:${random.value}}
instance:
# 與此實例相關(guān)聯(lián)的主機名膳叨,是其他實例可以用來進行請求的準(zhǔn)確名稱
hostname: localhost
# 獲取實例的ip地址
prefer-ip-address: true
# eureka客戶需要多長時間發(fā)送心跳給eureka服務(wù)器,表明它仍然活著,默認(rèn)為30 秒
lease-renewal-interval-in-seconds: 10
# Eureka服務(wù)器在接收到實例的最后一次發(fā)出的心跳后痘系,需要等待多久才可以將此實例刪除菲嘴,默認(rèn)為90秒
lease-expiration-duration-in-seconds: 30
client:
# 注冊自己
register-with-eureka: true
# 是否拉取服務(wù)
fetch-registry: true
# 配置注冊中心服務(wù)地址
service-url:
# eureka 服務(wù)地址
defaultZone: http://172.16.10.16:10001/eureka
server:
port: 10002
spring:
application:
name: config-server
cloud:
# cloud配置中心相關(guān)配置
config:
server:
# git相關(guān)配置
git:
# git 地址
uri: https://gitee.com/dai-yong-1/config-server-dy.git
# git用戶名
username: xxxx
# git密碼
password: xxxxx
# 配置文件所在文件夾
search-paths: config-yml
配置中心git倉庫如下:
- 啟動類
/**
* @Description:
* @author: dy
*/
@EnableConfigServer //聲明當(dāng)前應(yīng)用是config server服務(wù)
@EnableDiscoveryClient //開啟Eureka客戶端發(fā)現(xiàn)功能
@SpringBootApplication
public class ConfigServerApplication {
public static void main(String[] args) {
SpringApplication.run(ConfigServerApplication.class, args);
}
}
config client 搭建
- 引入依賴
<dependencies>
<!--配置中心相關(guān)依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-config</artifactId>
</dependency>
<!--erueka客戶端相關(guān)依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
</dependencies>
- 配置類
server:
port: 11001
spring:
application:
name: user-service
cloud:
config:
enabled: true
# 與遠程倉庫中的配置文件的application保持一致
name: user-service
# 遠程倉庫中的配置文件的profile保持一致
profile: dev
# 遠程倉庫中的 分支 版本保持一致
label: master
# config server地址
uri: http://localhost:10002/
# 配置的用戶名密碼
username: root
password: root
在git倉庫里面我們新建了一個配置文件user-service-dev.yml,配置內(nèi)容如下:
dy:
config:
app-id: 110
app-name: 'user-service-name'
使用的時候在config client端我們新建一個配置文件:
package com.dy.user.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Configuration;
import org.springframework.stereotype.Component;
/**
* @Description:
* @author: dy
*/
@Data
@Component
@Configuration
@ConfigurationProperties(prefix = "dy.config")
public class AppInfo {
private String appId;
private String appName;
}
測試類如下:
package com.dy.user.resource;
import com.dy.user.client.UserClient;
import com.dy.user.config.AppInfo;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
/**
* @Description:
* @author: dy
*/
@Slf4j
@RestController
@RequestMapping(UserClient.MAPPING)
public class UserResource implements UserClient {
@Autowired
private AppInfo appinfo;
@Override
public String getUserId() {
return "======111111222>>"+appinfo.getAppId();
}
}
運行結(jié)果如下:
如此我們就大致實現(xiàn)了配置中心的基礎(chǔ)功能
config刷新功能
但是如果我們線上實時修改了git倉庫里面的配置文件內(nèi)容汰翠,那我們的客戶端怎么及時讀取git倉庫里面實時的文件內(nèi)容呢龄坪?
spring cloud config給我們提供了兩種方式:
config配置手動刷新
自動刷新
config配置手動刷新
- 引入依賴
<!-- 健康監(jiān)測依賴 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>
- 添加配置
management:
#啟用監(jiān)控 默認(rèn)打開health和info,* 表示開放所有端口
endpoints:
web:
exposure:
include: *
#打印健康信息詳情
endpoint:
health:
show-details: always
-
引用類里面添加注解@RefreshScope
該注解處代理的bean會在調(diào)用/refresh接口時被清空
@Slf4j
@RestController
@RequestMapping(UserClient.MAPPING)
@RefreshScope
public class UserResource implements UserClient {
@Autowired
private AppInfo appinfo;
@Override
public String getUserId() {
log.info("==============請求來了===============");
return "======111111222>>"+appinfo.getAppId();
}
}
先修改git倉庫配置文件內(nèi)容
再調(diào)用http://localhost:11001/actuator/refresh 進行手動刷新,注意是:post方式訪問
請求接口我們可以發(fā)現(xiàn)內(nèi)容改變了
雖然手動刷新可以避免我們重啟服務(wù)复唤,但是每次去刷腳本跑接口刷新每個服務(wù)感覺十分不便健田,那有什么更好的方式呢?
config自動刷新
在微服務(wù)架構(gòu)體系中佛纫,我們可以接口消息總線bus實現(xiàn)配置的自動更新抄课,也就是Spring Cloud Config+Spring Cloud Bus
Spring Cloud Bus是基于MQ的唱星,支持Rabbitmq/Kafka,是Spring Cloud的消息總線方案跟磨。
具體實現(xiàn)流程如下:
具體實現(xiàn)如下(mq我們使用的是Rabbitmq):
config server端
- 引入依賴
<!-- spring cloud bus消息總線依賴 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-bus-amqp</artifactId>
</dependency>
- 添加配置
server:
port: 10002
spring:
application:
name: config-server
# 這里我們用的rabbitmq
rabbitmq:
addresses: amqp://192.168.2.56:5672
username: sxw_demo
password: sxw_demo
cloud:
# cloud配置中心相關(guān)配置
config:
server:
# git相關(guān)配置
git:
# git 地址
uri: https://gitee.com/dai-yong-1/config-server-dy.git
# git用戶名
username: 15828101225
# git密碼
password: hd961740841
# 配置文件所在文件夾
search-paths: config-yml
#eureka 參數(shù)配置
eureka:
# 此實例注冊到eureka服務(wù)端的唯一的實例ID,其組成為${spring.application.name}:${spring.application.instance_id:${random.value}}
instance:
# 與此實例相關(guān)聯(lián)的主機名间聊,是其他實例可以用來進行請求的準(zhǔn)確名稱
hostname: localhost
# 獲取實例的ip地址
prefer-ip-address: true
# eureka客戶需要多長時間發(fā)送心跳給eureka服務(wù)器,表明它仍然活著,默認(rèn)為30 秒
lease-renewal-interval-in-seconds: 10
# Eureka服務(wù)器在接收到實例的最后一次發(fā)出的心跳后抵拘,需要等待多久才可以將此實例刪除哎榴,默認(rèn)為90秒
lease-expiration-duration-in-seconds: 30
client:
# 注冊自己
register-with-eureka: true
# 不拉取服務(wù)
fetch-registry: true
# 配置服務(wù)地址
service-url:
# eureka 服務(wù)地址,如果是集群的話僵蛛;需要指定其它集群eureka地址 ,如果是多臺eureka server 地址以逗號隔開
defaultZone: http://172.16.10.16:10001/eureka
management:
#啟用監(jiān)控 默認(rèn)打開health和info,* 表示開放所有端口
endpoints:
web:
exposure:
include: "*"
#打印健康信息詳情尚蝌,
endpoint:
health:
show-details: always
config client端
- 引入依賴
<!-- spring cloud bus消息總線依賴 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-bus-amqp</artifactId>
</dependency>
- 添加配置
server:
port: 11001
spring:
application:
name: user-service
rabbitmq:
addresses: amqp://192.168.2.56:5672
username: sxw_demo
password: sxw_demo
zipkin:
# zipkin server的請求地址
base-url: http://localhost:10005/
sender:
#web 客戶端將蹤跡日志數(shù)據(jù)通過網(wǎng)絡(luò)請求http的方式發(fā)送到服務(wù)端
#rabbit 客戶端將蹤跡日志數(shù)據(jù)通過mp rabbit的方式發(fā)送到服務(wù)端
#kafka 客戶端將蹤跡日志數(shù)據(jù)通過mp kafka的方式發(fā)送到服務(wù)端
type: web
sleuth:
sampler:
probability: 1 # 采樣率
cloud:
config:
enabled: true
# 與遠程倉庫中的配置文件的application保持一致
name: user-service
# 遠程倉庫中的配置文件的profile保持一致
profile: dev
# 遠程倉庫中的 分支 版本保持一致
label: master
# config server地址
uri: http://localhost:10002/
# 配置的用戶名密碼
username: root
password: root
運行項目操作步驟如下:
修改git倉庫配置文件內(nèi)容
向config server發(fā)起post請求http://localhost:10002/actuator/bus-refresh
調(diào)用接口就可以發(fā)現(xiàn)拉取到了最新文件內(nèi)容信息
如果要實現(xiàn)修改完遠程git文件自動刷新配置的話,可以在git上面添加一個WebHooks, URL需要把本地的 http://localhost:10002/actuator/bus-refresh映射成公網(wǎng)IP.可以使用第三方內(nèi)網(wǎng)穿透實現(xiàn).具體如下: