配置中心設(shè)計(jì)與實(shí)踐
配置中心定義
服務(wù)集群的統(tǒng)一配置存儲(chǔ)和管理系統(tǒng),配置中心的特點(diǎn):
- 獨(dú)立于程序的只讀變量
- 伴隨應(yīng)用這個(gè)生命周期
- 多種加載方式
- 權(quán)限控制,環(huán)境選擇
解決的問題
- 配置熱刷新,減少服務(wù)重啟
- 隨著業(yè)務(wù)和功能的復(fù)雜,需要配置的參數(shù)越來越多,不同服務(wù)依賴同一變量
- 對配置項(xiàng)的管理:環(huán)境,權(quán)限,生效時(shí)間等
可選方案
ZooKeeper、etcd可以作為配置中心,但二者直接作為配置中心缺少便捷的管理工具,缺乏權(quán)限管理機(jī)制。
開源產(chǎn)品
- Spring Cloud Config
- 淘寶的Diamond(阿里內(nèi)部使用,針對Spring框架定制)
- 百度Disconf(針對Spring項(xiàng)目,依賴ZooKeeper)
- 攜程Apollo(默認(rèn)依賴Eureka做服務(wù)發(fā)現(xiàn),存儲(chǔ)依賴MySQL)
通過比較分析Apollo的功能最為豐富
Apollo詳解
核心概念:
- application(應(yīng)用):通過appId標(biāo)識(shí)應(yīng)用自身
- environment(環(huán)境):Apollo客戶端獲取當(dāng)前應(yīng)用運(yùn)行的環(huán)境,例如:server.properties.env
- cluster(集群):不同的服務(wù)集群中同一個(gè)配置項(xiàng)可以有不同的值,例如:Zookeeper的地址
- namespace(命名空間):類似Spring Cloud Config的application.yml為公共配置,其他配置項(xiàng)都引入這個(gè)配置,命名空間可以設(shè)置多層。
架構(gòu)設(shè)計(jì)
服務(wù)端設(shè)計(jì)

image.png
圖中從下向上看:
- Config Service提供配置的讀取、推送等功能,服務(wù)對象是Apollo客戶端
- Admin Service提供配置的修改、發(fā)布等功能,服務(wù)對象是Apollo Portal(管理界面)
- Config Service和Admin Service都是多實(shí)例、無狀態(tài)部署,所以需要將自己注冊到Eureka中并保持心跳
- 在Eureka之上增加一層Meta Server用于封裝Eureka的服務(wù)發(fā)現(xiàn)接口
- Client通過域名訪問Meta Server獲取Config Service服務(wù)列表(IP+Port),然后直接通過IP+Port訪問服務(wù),同時(shí)在Client側(cè)會(huì)做Load balance、錯(cuò)誤重試
- Portal通過域名訪問Meta Server獲取Admin Service服務(wù)列表(IP+Port),然后直接通過IP+Port訪問服務(wù),同時(shí)在Portal側(cè)做Load Balance、錯(cuò)誤重試
- 為了簡化不是,時(shí)間上會(huì)把Config Service、Eureka和Meta Server三個(gè)邏輯上的角色部署在同一個(gè)JVM進(jìn)程中
客戶端設(shè)計(jì)

image.png
實(shí)現(xiàn)原理:
- 客戶度和服務(wù)端保持一個(gè)長連接,從而能夠第一時(shí)間獲得配置更新的推送
- 客戶端還會(huì)定時(shí)通Apollo配置中心服務(wù)端拉取應(yīng)用的最新配置:
- 防止推送機(jī)制失效導(dǎo)致配置不更新
- 客戶端定時(shí)拉取時(shí)會(huì)上報(bào)本地版本,所以一般情況下拉取操作,服務(wù)端都會(huì)返回304-Not Modified
- 定時(shí)頻率默認(rèn)5分鐘,可以配置修改
- 客戶端從Apollo配置中心服務(wù)端獲取到應(yīng)用的最新配置后,會(huì)保存在內(nèi)存中
- 客戶端會(huì)把服務(wù)端獲取到的配置在本地文件系統(tǒng)緩存一份:
- 在遇到服務(wù)不可用、網(wǎng)絡(luò)不通時(shí),依然能從本地恢復(fù)配置
- 應(yīng)用程序從Apollo客戶端獲取最新的配置、訂閱配置更新通知
Apollo配置更新推送實(shí)現(xiàn)
長連接實(shí)際上通過HTTP Long Polling實(shí)現(xiàn):
- 客戶端發(fā)起一個(gè)HTTP請求到服務(wù)端
- 服務(wù)端保持住這個(gè)鏈接60秒
- 如果在60秒內(nèi)有客戶端關(guān)心的配置變化,被保持住的客戶端請求會(huì)立即返回,并告知客戶端有配置變化的namespace信息,客戶端會(huì)據(jù)此拉取對應(yīng)namespace的最新配置
- 如果在60秒內(nèi)沒有客戶端關(guān)心的配置變化,那么會(huì)返回HTTP狀態(tài)碼304給客戶端
- 客戶端收到服務(wù)端請求后立即重新發(fā)起連接,回到第一步
- 考慮到會(huì)有輸完客戶端向服務(wù)端發(fā)起長連接,在服務(wù)端使用了async server(Spring DeferredResult)來服務(wù)HTTP Long Polling請求
消息隊(duì)列設(shè)計(jì)與實(shí)踐
消息隊(duì)列定義
消息隊(duì)列技術(shù)是分布式應(yīng)用間交換信息的一種技術(shù):
- 消息隊(duì)列可駐留在內(nèi)存或磁盤上,隊(duì)列存儲(chǔ)消息直到它們被應(yīng)用程序取走
- 通過消息隊(duì)列,應(yīng)用程序可獨(dú)立地執(zhí)行,不需要直達(dá)彼此的配置或再繼續(xù)執(zhí)行前不需要等到消費(fèi)方接受此消息
應(yīng)用場景:
- 異步通信
- 業(yè)務(wù)解耦:基于消息模型,關(guān)注“通知”,而非關(guān)注“處理”
- 錯(cuò)峰與流量控制
- 廣播
- 保證時(shí)序
消息隊(duì)列模型
- Pub/Sub發(fā)布訂閱(廣播):使用Topic作為通信載體
- P2P(點(diǎn)對點(diǎn)):使用Queue作為通信載體
業(yè)界產(chǎn)品
- RabbitMQ(Erlang)
- ZeroMQ(傳輸層,C語言)
- Apache ActiveMQ(Java)
- Redis
- Apache Kafaka(Scala,高可用:Zookeeper)
- Apache RocketMQ
- NSQ(Go)
- beanstalkd
生產(chǎn)環(huán)境推薦
高吞吐、可靠性可容忍場景,如日志處理:Kafaka
高可靠場景,如電商訂單消息:RocketMQ
RocketMQ
包括四個(gè)部分:
- NameServer集群:提供輕量級(jí)的服務(wù)發(fā)現(xiàn)和Topic路由信息。Broker定時(shí)發(fā)送路由信息到NameServer中
- Broker:提供輕量級(jí)Topic和Queue機(jī)制。支持push和pull兩種模式,有自身容錯(cuò)機(jī)制(2 Copies 或 3 Copies)
- Producer集群:通過負(fù)載均衡,向Broker集群發(fā)送消息。發(fā)送過程中支持快速衰竭和低延遲。擁有相同的Producer Group
- Consumer集群:消費(fèi)者,支持分布式部署的push和pull模式,同時(shí)也支持幾圈消費(fèi)和消息廣播
分布式請求跟蹤系統(tǒng)設(shè)計(jì)與實(shí)踐
實(shí)現(xiàn)方案:
基于日志的分布式請求跟蹤系統(tǒng):
- 業(yè)務(wù)侵入小
- 將每個(gè)系統(tǒng)分散的日志聚合起來,進(jìn)行海量日志分析,生成有價(jià)值的數(shù)據(jù)
核心調(diào)用鏈:
- 每次請求都生成一個(gè)全局唯一的ID(TraceID),通過它將不同系統(tǒng)生成的日志串聯(lián)在一起,重組成調(diào)用鏈
- 開發(fā)人員通過分布式請求跟蹤鏈排查問題,也可以對多個(gè)請求進(jìn)行統(tǒng)計(jì)和分析
應(yīng)用場景:
- 調(diào)用鏈追蹤:以圖形化的方式梳理出各個(gè)Server端集群之間的調(diào)用關(guān)系,并記錄整個(gè)調(diào)用過程的耗時(shí),協(xié)助開發(fā)人員分析系統(tǒng)瓶頸與熱點(diǎn)。
- 調(diào)用鏈路分析:整理集群之間的調(diào)用關(guān)系,計(jì)算出整個(gè)調(diào)用鏈路的關(guān)鍵節(jié)點(diǎn)、直接依賴、間接依賴、依賴強(qiáng)度等
- 調(diào)用來源分析:針對某一特定集群,整理出其他集群對其調(diào)用情況,防止錯(cuò)誤調(diào)用情況的發(fā)生
- 調(diào)用量統(tǒng)計(jì):實(shí)時(shí)統(tǒng)計(jì)各個(gè)集群的調(diào)用次數(shù)、QPS、平均耗時(shí)、最大耗時(shí)等信息,可以根據(jù)相關(guān)信息進(jìn)行容量規(guī)劃