天天看點

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

之前在 Apache/dubbo-go(以下簡稱 dubbo-go )社群中,有同志希望配置檔案可以放置于配置管理中心,不僅放置于本地。放置于本地及配置管理中心究竟有什麼不一樣呢?

放置于本地,每次更新需要重新開機,配置檔案管理困難,無法做到實時更新即刻生效。本地檔案還依賴人工版本控制,在微服務的場景下,大大的增加了運維的成本與難度。

而配置管理中心提供統一的配置檔案管理,提供檔案更新實時同步,統一版本控制,權限管理等功能。

目标

基于以上幾個背景,可以總結出以下 目标

  • 與 dubbo 現有的配置中心内的配置檔案相容,降低新增語言棧的學習成本;
  • 支援多種配置檔案格式;
  • 支援主流配置中心,适應不一樣的使用場景,實作高擴充的配置下發;

配置中心

配置中心在 dubbo-go 中主要承擔以下場景的職責:

  • 作為外部化配置中心,即存儲 dubbo.properties 配置檔案,此時,key 值通常為檔案名如 dubbo.properties , value 則為配置檔案内容。
  • 存儲單個配置項,如各種開關項、常量值等。
  • 存儲服務治理規則,此時 key 通常按照 “服務名 + 規則類型” 的格式來組織,而 value 則為具體的治理規則。

就目前而言,dubbo-go 首要支援 dubbo 中所有支援的各種開源配置中心,包括:

  • Apollo :攜程架構部門研發的分布式配置中心,能夠集中化管理應用不同環境、不同叢集的配置,配置修改後能夠實時推送到應用端,并且具備規範的權限、流程治理等特性,适用于微服務配置管理場景。
  • zookeeper :一個分布式的,開放源碼的分布式應用程式協調服務,是 Google 的 Chubby 一個開源的實作,是 Hadoop 和 Hbase 的重要元件。它是一個為分布式應用提供一緻性服務的軟體,提供的功能包括:配置維護、域名服務、分布式同步、組服務等。
  • nacos : Alibaba 開源的配置管理元件,提供了一組簡單易用的特性集,幫助您實作動态服務發現、服務配置管理、服務及流量管理。

而考慮到某些公司内部有自身的研發的配置中心,又或者目前流行而 dubbo 尚未支援的配置中心,如 etcd,我們的核心在于設計一套機制,允許我們——也包括使用者——可以通過擴充接口新的實作,來快速接入不同的配置中心。

那在 dubbo-go 中究竟怎麼實作呢?我們的答案是:基于動态的插件機制在啟動時按需加載配置中心的不同實作。

實作該部分功能放置于一個獨立的子項目中,見:

https://github.com/apache/dubbo-go/tree/master/config_center

dubbo-go設計

原邏輯為:啟動時讀取本地配置檔案,将其加載進記憶體,通過配置檔案中的配置讀取注冊中心的資訊擷取服務提供者,注冊服務消費者。

有些讀者會有點困惑,不是說好了使用配置中心的,為什麼現在又要讀取本地配置呢?答案就是,讀取的這部分資訊分成兩部分:

  1. 使用什麼作為配置中心;
  2. 該配置中心的中繼資料,比如說使用 zookeeper 作為配置中心,那麼 zookeeper 的連結資訊就是中繼資料,畢竟我們隻有在知道了連結資訊之後才能連上 zookeeper;

在改造的時候,需要考慮以下的問題

  1. 如何實作支援多個配置中心?如何實作按需加載?

通過抽象

DynamicConfiguration

讓開發者可以快速支援多個配置中心。

使用者導入指定的元件包後,在啟動階段将需要的元件加載進記憶體中,以便給程式按需調用,如下圖綠色部分。

  1. 配置中心的配置加載階段在什麼時候?

應在讀取配置檔案階段後,讀取并解析本地配置檔案中配置中心資訊。初始化配置中心連結,讀取 /dubbo/config/dubbo/dubbo.properties 與 /dubbo/config/dubbo/應用名/dubbo.properties ,并将其加載到記憶體之中覆寫原有配置,監聽其變更,實時更新至記憶體,如下圖藍色部分。

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

ConfigCenterFactory

使用者加載對應配置中心子產品後,在初始化階段加入各配置中心子產品往其中注冊其初始化類。

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

DynamicConfigurationFactory

整個動态配置中心的關鍵點就在 DynamicConfigurationFactory 上,其中通過解析内部自定義的 URL ,擷取其協定類型,反射其參數,用于建立配置中心的連結。

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

如:

配置檔案中配置

config_center:
  protocol: zookeeper
  address: 127.0.0.1:2181
  namespace: test           

dubbo-go 内部會解析為

zookeeper://127.0.0.1:2181?namespace=test           

在内部傳遞,用于初始化配置中心連結。

PS:在 dubbo-go 中到處可見這種内部協定,透徹了解這個内部協定對閱讀 dubbo-go 代碼很有幫助。

DynamicConfiguration

該接口規定了各個配置中心需要實作的功能:

  • 配置資料反序列化方式:目前隻有 Properties 轉換器,參見: DefaultConfigurationParser 。
  • 增加監聽器:用于增加監聽資料變化後增加特定邏輯(受限于配置中心 client 端實作)。
  • 删除監聽器:删除已有監聽器(受限于配置中心 client 端實作,目前所知 nacos client 沒有提供該方法)。
  • 擷取路由配置:擷取路由表配置。
  • 擷取應用級配置:擷取應用層級配置,如:協定類型配置等。
dubbo-go 中如何實作遠端配置管理?目标配置中心總結

實作

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

優先考慮與現有 dubbo 設計相容,進而降低使用者的學習成本,

dubbo-admin

作為服務提供者實作應用級配置管理, dubbo-go 作為消費端實作配置下發管理功能。下面以 zookeeper 為例,對服務提供者與服務消費者進行整體流程分析。

如何存儲配置管理

dubbo-admin 配置管理中增加 global 配置,zookeeper 中會自動生成其對應配置節點,内容均為 dubbo-admin 中設定的配置。

  • /dubbo/config/dubbo/dubbo.properties 對應全局配置檔案。
  • /dubbo/config/dubbo/ 應用名 /dubbo.properties 對應指定應用配置檔案。

節點路徑

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

上圖展示了 dubbo.properties 檔案在 zookeeper 和 Apollo 中的存儲結構:

  • 命名空間 namespace 都為:dubbo
  • 分組 group :全局級别為 dubbo , 所有應用共享;應用級别為應用名 demo-provider ,隻對該應用生效
  • key : dubbo.properties
  • app_id : 自由指定,預設: dubbo ,最好與 zookeeper  namespace 一緻
  • cluster : 自由指定,最好與 zookeeper group 一緻
  • 命名空間 namespace : dubbo.properties

zookeeper 與 Apollo 最大的不一樣就在于 dubbo.properties 所在的節點。

實作配置管理中心支援

以 Apollo 為例,簡單的介紹,如何實作支援一個新的配置管理中心。

選擇配置管理中心 Client / SDK

本例中使用的 Apollo Go Client 為:

https://github.com/zouyx/agollo

 。

PS: 如沒找到,自己實作也是可以的哦。

因為每個配置管理中心的存儲結構各有特點,導緻 dubbo 在使用外部配置管理中心時,存儲配置節點的結構不一樣。在 

dubbo-configcenter

 找到希望支援的配置管理中心,而本例中 Apollo 則在 

ApolloDynamicConfiguration.java

注釋中表明,Apollo namespace = governance (governance .properties) 用于治理規則,namespace = dubbo (dubbo.properties) 用于配置檔案。

實作 DynamicConfiguration

建立建立用戶端方法,最好用戶端保持為單例。

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

以下為必須實作的方法,以下方法用于擷取配置中心配置。

  • GetInternalProperty:在配置檔案(Apollo 為 namespace)中,根據 key 擷取對應 value;
  • GetRule:擷取治理配置檔案(Apollo 為 namespace);
  • GetProperties:擷取整個配置檔案(Apollo 為 namespace);

可選擇實作的方法,如不實作,則不能動态更新 dubbo-go 中配置資訊。

  • RemoveListener
  • AddListener

而 Parser & SetParser 使用預設實作即可,預設為 Properties 轉換器。

更多資訊,參考:

dubbo-go-apollo

使用方法

從上面的設計裡面,也能大概猜到怎麼使用了:

dubbo-go 中如何實作遠端配置管理?目标配置中心總結

很顯然,使用配置中心并不複雜,隻需要把對應的依賴引入進來。在包初始化的時候,會建立出來對應的配置中心的實作。比如說加載 zookeeper 或者 Apollo 作為配置中心:

_ "github.com/apache/dubbo-go/config_center/zookeeper"           
_ "github.com/apache/dubbo-go/config_center/apollo"           

當然僅僅加載還不夠,比如說雖然我加載了 zookeeper,但是我還需要知道怎麼連上這個配置中心,即前面提到的配置中心的中繼資料,這部分資訊是需要在本地配置出來的。比如說:

config_center:
  protocol: "zookeeper"
  address: "127.0.0.1:2181"           

如果需要使用 Apollo 作為配置中心,請提前建立 namespace: dubbo.properties,用于配置管理。

config_center:
  protocol: "apollo"
  address: "127.0.0.1:8070"
  app_id: test_app
  cluster: dev           

總結

更加具體的實作,我就不詳細論述,大家可以去看源碼,歡迎大家持續關注,或者貢獻代碼。

整個配置中心的功能,麻雀雖小,但五髒俱全。目前并不算是十分完善,但是整個架構層面上來說,是走在了正确的路上。從擴充性來說,是比較便利。目前支援的配置中心還不夠豐富,隻有 zookeeper 與 Apollo ,支援的配置檔案格式也隻有 properties ,雖然能滿足基本使用場景,距離完善還有還長遠的路。

未來計劃:

  1. nacos(等待釋出 )
  2. etcd(正在開發)
  3. consul(未支援)
  4. 豐富的檔案配置格式,如: yml , xml 等

本文作者:鄒毅賢,Github ID @zouyx,開源愛好者,就職于 SheIn 供應鍊部門,負責供應鍊開放平台。