成人免费xxxxx在线视频软件_久久精品久久久_亚洲国产精品久久久_天天色天天色_亚洲人成一区_欧美一级欧美三级在线观看

微服務配置中心, 這個方案 Go 里用起來不輸 SpringCloud

開發 架構
今天給大家講了微服務配置中心的實現方案,先介紹了下 SpringCloudConfig 標準下的使用方案,因為Spring生態比較完整,對這方面支持的比較好,像ETCD、Consul甚至Git什么的都支持拿來做配置中心。

微服務架構設計模式里有一條講到,要設計可配置的服務。把服務從單體架構細分成微服務后,所有配置屬性都集中存儲在一個位置,更易于管理。這個集中存儲管理配置的地方,就是配置中心。

使用配置中心還有一個好處就是,往往都支持應用配置的熱更新,這樣就不需要像修改本地配置那樣進行發版部署了。

但是這么好的事兒就沒有缺點了嗎?當然有,除非有基礎設施支持,否則它需要額外的人力進行設計和運維。不過好在有各種開源框架比如 Spring Cloud Config,能使服務接入配置中心,沒有什么侵入性。至少在表面使用上感覺不到有變化。

那么在 Go 里有沒有類似的方案呢?經過我這周的試驗探索,還真發現了,這個方案落地也很簡單,今天就跟大家簡單說說。更詳細的還得是大家上手操作起來才能感受到,本方案涉及的代碼太多,可以給我的公眾號:網管叨bi叨,發送消息【go-config】獲取項目下載地址。

分享軟件開發和系統架構設計基礎、Go 語言和Kubernetes。

有人可能會說遠程配置中心,我就把配置放在 ETCD 上,項目啟動的時候拉下來不就行了?先別著急,咱先看看隔壁家 Spring 是怎么實現這個事兒,有沒有我們可以學習的地方。

Spring 的配置和配置中心

用過 Spring 的同學都接觸過,在 Java 的項目里都有一個resources?目錄,這個目錄里一般都會有類似名字叫application.properties 的配置文件。

圖片

配置文件

也有可能配置文件的后綴名是.yaml?,那么屬性配置的格式就是YAML格式的。

在這些配置文件里設置的屬性配置,都可以通過可以通過@Value注解注入到對象的屬性上,比如假設我們在配置文件里設定了訂單的折扣為95折的配置

order:
discount: 95

那在代碼里,我們就能像下面這樣,把屬性配置的值綁定到類實例的屬性上:

public class CoffeeOrderController {

@Value("${order.discount}")
private Integer discount;

......
}

后來,因為微服務流行起來了,大家又對自己的服務拆得樂此不疲,所以 Spring 家族里后來又有了 SpringCloud,像我們知道的知名廠商 Alibaba、Netflix 都按它這個標準開源自己內部使用的組件,就有了我們天天看到的各種資料推廣文里面的 SpringCloud-Netflix,SpringCloud- Alibaba這些。

SpringCloud- Alibaba在國內因為阿里的關系使用更廣泛一些,它里面提供的配置中心方案是一個叫 Nacos 的組件,因為有 SpringCloudConfig 這個標準存在,不管各個廠商的遠程配置中心是用什么組件,都需要實現 SpringCloudConfig 里的標準。

最直觀的好處就是,比如說我把應用的屬性配置放到了遠程的 Nacos 上,比如這樣:

圖片

遠程配置中心 Nacos

但是在應用程序我們仍然可以繼續使用 @Value注解拿到放在遠程配置中心的屬性值。如果本地和遠程配置中心都有的話,以本地磁盤里的配置優先。

是不是很方便?這就類似應用里使用的是一個門面模式,下層加載使用的組件提供的driver來完成項目配置的載入。

那在 Go 里面有沒有類似的方案呢?有,雖然沒有 SpringCloud 這個支持的組件那么全,但是支持 ETCD 和 Consul 做配置中心,也夠用了。

Go 項目的配置和配置中心

聊到 Go 項目的配置和配置中心,我見過的幾十個項目里,是的,前幾年待過的兩個拿融資多的創業公司里,項目就是很多,不停地嘗試各種方向的業務,不然投資人那不好說啊,咳咳。有的,做做沒有效果就放棄了 T—_—T。

說回來,咱們配置的事兒,在這幾十個項目里基本上分成兩大派,有用 Viper 或者另一個Yaml開源庫直接操作本地文件的。還有一派是直接讀 ETCD ,拿下來把字節流轉到本地配置對象的。

那有沒有一種方案能兼容本地配置和遠程配置中心兩種模式的?

我看了一下 Viper 是支持從遠程 ETCD 或者 Consul 取配置的。

但是呢,經過我的試驗,發現官網的給的例子有BUG,從 ETCD 上根本讀不了配置,更別提熱更新了,這點我們先按下不表,我先給大家介紹下 Viper 的基本使用。

主要是我也沒從頭用過,以前用的項目架子里是別人搭好的,哈哈~,不過你們面試的時候可別這么說大實話,今天看完我的文章,至少配置中心這塊的架構選型,我是可以吹吹的,你們呢?

怎么安裝 Viper 包什么的,我就不說了,官網上都有,文末會附上官網的鏈接,下面直接上代碼。假如,不是假如,我真在項目配置文件里寫了個數據庫連接信息的YAML配置。

database:
type: mysql
dsn: "user:pass@tcp(localhost:30306)/db_name?charset=utf8&parseTime=True&loc=Local"
maxopen: 100
maxidle: 10
maxlifetime: 300

然后用 Viper 怎么讀這個配置呢?這里直接在配置文件目錄下用一個 Go 的 init 函數,在函數里把配置用 Viper 反序列化到一個全局變量里,供項目使用。

type databaseConfig struct {// 配置屬性跟類型字段不同名是要加下面這個tag
Type string `mapstructure:"type"`
DSN string `mapstructure:"dsn"`
MaxOpenConn int `mapstructure:"maxopen""`
MaxIdleConn int `mapstructure:"maxidle"`
MaxLifeTime time.Duration `mapstructure:"maxlifetime"`
}
var Database *databaseConfig

func init() {
// 獲取當前文件的路徑
_, filename, _, _ := runtime.Caller(0)
// 配置文件目錄的路徑
configBaseDir := path.Dir(filename)
vp := viper.New()
vp.AddConfigPath(configBaseDir)
vp.SetConfigType("yaml")
err := vp.ReadInConfig()
if err != nil {
panic(err)
}
vp.UnmarshalKey("database", &Database)
Database.MaxLifeTime *= time.Second
}

除了把配置項反序列化到結構體類型里,還能通過類似 Spring 里的@Value那種方式讀單個配置項的值。

vp.Get("database.type")

不過我更傾向于反序列化到結構體這種方式,使用起來更方便,同時熱更新配置時這種方式也更方便些。

項目里實例化數據庫連接的時候,就可以像這樣,用上我們的配置啦。

// 具體完整實例代碼,實在太多
// 請給我的公眾號:網管叨bi叨,發送消息【go-config】來領取。
db, err := gorm.Open(config.Database.Type, config.Database.DSN)
if err != nil {
panic(err)
}
db.DB().SetMaxOpenConns(config.Database.MaxOpenConn)
db.DB().SetMaxIdleConns(config.Database.MaxIdleConn)
db.DB().SetConnMaxLifetime(config.Database.MaxLifeTime)
if err = db.DB().Ping(); err != nil {
panic(err)
}

下面我們接著來說,Viper 使用遠程配置中心的情況。這里我給大家安利下我的 ETCD 集群 K8s 搭建教程:用Kubernetes搭建Etcd集群和WebUI,不然如果你本地沒有 ETCD 的話,不太好實踐,除非…你嚯嚯下你們公司測試環境的ETCD,嘿嘿,保命要緊,還是在自己電腦上搭建吧。

另外安利下我的 K8s 教程,上面用的Nacos也是我用 K8s 搭建的,在教程里都有,在公眾號網管叨bi叨回復k8s就能拿到教程,絕對實用。

下面我們給項目加一個 redis 連接信息的配置

redis:
address: "localhost:6579"
password: "DFgsdfhshf"
dbnumber: 0
maxactive: 100
maxidle: 20

把這個配置放到遠程的ETCD 配置中心里:

圖片

ETCD 中的配置

后來我按照官網的例子,死活讀不到我這個key 對應的配置,在網上查了一下,究其原因,是因為 Viper 依賴 crypt 庫,而 crypt 截至目前還不支持新版 ETCD 的 API。

ETCD 的 KV 中可以存儲加密的數據,Viper 在獲取的時候通過 crypt 自動解密,這個初衷是好的,但是公司里的配置中心基本上都是內網訪問,再則加密存儲的話,我就不能像上面這樣直接在客戶端里進行KV編輯了,有什么辦法呢?

看網上有技術大佬分析,可以通過重新實現remoteConfigFactory接口;

type remoteConfigFactory interface {
Get(rp RemoteProvider) (io.Reader, error)
Watch(rp RemoteProvider) (io.Reader, error)
WatchChannel(rp RemoteProvider) (<-chan *RemoteResponse, chan bool)
}

這個接口的具體實現我就不放上來了實在是太多,可以自己下載項目去看,下載鏈接獲取方式,給我的公眾號「網管叨bi叨」發送消息【go-config】獲取項目下載鏈接。

使用 Viper 讀取遠程配置,還需要匿名導入它提供的一個庫。

_ "github.com/spf13/viper/remote"

下面演示一下使用 Viper 讀取遠程配置和熱更新配置的代碼。

type RedisConfig struct {
Address string `mapstructure:"address"`
Password string `mapstructure:"password"`
DbNumber int `mapstructure:"dbnumber"`
MaxActive int `mapstructure:"maxactive"`
MaxIdle int `mapstructure:"maxidle"`
}
var Redis *RedisConfig

func init() {
// 初始化 Viper 和上面例子里的一樣,這里省略
...
代碼里省略一切error處理
// 告訴Viper遠程ETCD里的KV在哪里找
err := vp.AddRemoteProvider("etcd", "http://127.0.0.1:32379", "root/config/viper-test/config")
vp.SetConfigType("yaml")
err = vp.ReadInConfig()
err = vp.ReadRemoteConfig()
vp.UnmarshalKey("database", &Database)
Database.MaxLifeTime *= time.Second
vp.UnmarshalKey("redis", &Redis)
// 這里簡單輸出一下 redis 的配置,就不做其他演示了
fmt.Printf("Redis Config: %v\n", Redis)
// 監聽KV變更,進行熱更新
go watchRemoteConfig(vp)
}

監聽配置變更,進行熱更新這塊,我暫時實現的簡單點,用了下輪詢,后面有好的方法了再更新。

func watchRemoteConfig(vp *viper.Viper) {
for {
time.Sleep(5 * time.Second)
err := vp.WatchRemoteConfigOnChannel()
if err != nil {
zlog.Error("Read Config Server Error", zap.Error(err))
return
}
// 監控遠程配置的變更
vp.UnmarshalKey("redis", &Redis)
fmt.Printf("Redis Config: %v\n", Redis)
}
}

這里演示的配置熱更新我就是簡單向控制臺輸出了一下 Redis 的配置,啟動后我試了一下,在ETCD里把配置修改后能直接在項目里變更過來,下面是我把Redis配置的端口從 6579 改成 6580 的一個演示。

圖片

配置動態更新

總結

今天給大家講了微服務配置中心的實現方案,先介紹了下 SpringCloudConfig 標準下的使用方案,因為Spring生態比較完整,對這方面支持的比較好,像ETCD、Consul甚至Git什么的都支持拿來做配置中心。

Go 里邊的 Viper 庫也很強大,只是用 Etcd 當配置中心的時候需要我們自己做些擴展,雖然沒有那么開箱即用,但是研究問題動手解決的過程還是很有意思的。

對了,Viper 支持同時使用本地和遠程配置,本地配置優先級高于遠程,大家不要弄混了。

這里我再給個建議像是服務器啟動參數 server.port,application.name這類幾乎是項目創建完后就不會再改的配置,放在本地配置文件就好。

責任編輯:武曉燕 來源: 網管叨bi叨
相關推薦

2021-06-30 09:20:18

NuShell工具Linux

2021-09-18 08:52:45

人工智能

2020-01-06 13:42:29

Linux極客腳本語言

2021-01-04 09:35:55

微服務架構配置中心

2018-04-20 07:22:59

物聯網互聯網IoT

2021-03-10 09:54:43

RustNuShell系統

2020-12-08 11:20:43

Windows微軟數據

2025-01-13 00:00:07

Go語言微服務

2024-12-10 08:27:28

2012-07-11 09:34:39

微軟云計算

2022-05-22 21:16:46

TypeScriptOmit 工具

2024-07-04 11:33:33

2019-04-15 13:52:18

微服務配置中心Apollo

2021-01-14 09:55:21

Java微服務Go

2020-01-22 16:29:52

機器學習人工智能計算機

2025-03-31 08:35:00

Eureka微服務架構

2022-08-29 06:27:15

Nacos微服務

2022-05-09 08:56:27

Go淺拷貝接口

2024-05-21 10:28:51

API設計架構

2021-03-09 09:33:42

網關授權微服務
點贊
收藏

51CTO技術棧公眾號

主站蜘蛛池模板: 久久久资源| 亚洲一区自拍 | 99在线国产| 亚洲国产精品福利 | 黄色大片视频 | 亚洲精品一区二区三区中文字幕 | 国产精品69毛片高清亚洲 | 亚欧午夜 | 国产免费观看一级国产 | www.色53色.com | 国产www. | 国产a区| 亚洲在线视频 | 日韩综合在线视频 | 午夜影院网站 | 精品乱人伦一区二区三区 | 日韩中文字幕免费 | 欧美一级毛片久久99精品蜜桃 | 青春草91 | 亚洲精品日日夜夜 | 亚洲 欧美 综合 | 国产精品久久777777 | 欧美日韩在线免费 | 国产在线中文字幕 | 日韩在线视频网址 | 欧美在线观看一区 | 欧美爱爱视频网站 | 亚洲综合色视频在线观看 | 一区二区三区四区免费观看 | 免费一区| 中文字幕av在线一二三区 | 成人精品国产一区二区4080 | 成人高潮片免费视频欧美 | 精品久久一 | 成人做爰www免费看视频网站 | 久久久影院 | 武道仙尊动漫在线观看 | 成人免费淫片aa视频免费 | 91在线精品视频 | 日韩一区二区在线视频 | 黄色网址在线播放 |