4-微服務架構下的服務發現

本文出自Nginx官網,是微服務介紹系列文章的第四篇。原文地址:https://www.nginx.com/blog/service-discovery-in-a-microservices-architecture/

1.介紹

在第一篇文章中比較了微服務架構的應用和單體應用的差異,討論了微服務架構的優點與缺點;第二篇文章和第三篇文章中討論了進程間通信相關的問題;在本篇文章中我們討論服務發現相關的問題。

2.爲什麼使用服務發現

爲了訪問REST接口或者Thrift接口的服務,你需要知道服務實例的IP地址和端口號。對部署在物理機上的傳統應用而言,應用的IP地址相對固定;發起請求時查詢配置文件獲取服務地址,在服務地址變化時更新配置文件。

在基於雲的微服務應用中,事情變複雜了:服務實例的地址是動態分配的;甚至,由於自動伸縮、服務宕機、服務更新等原因導致服務的實例集合也是變化的,如下圖所示:


客戶端需要使用更復雜的服務發現機制來解決問題。主要有兩種服務發現模式:客戶端發現和服務端發現。

3.客戶端服務發現模式

使用客戶端服務發現時,客戶端負責決定可用服務實例的網絡地址,並在它們中間進行負載均衡。客戶端查詢包含所有可用服務實例的服務註冊表,使用負載均衡算法選擇一個可用的服務,發出服務請求。過程如下圖所示:


服務實例啓動後,向服務註冊表註冊網絡地址;服務終止時,服務註冊表會刪除對應記錄;服務註冊表使用心跳機制定期更新。

Netflix OSS是客戶端服務發現的例子。Netflix Eureka是服務註冊表,它使用REST風格的接口,提供服務註冊管理和可用服務查詢功能。Netflix Ribbon在Eureka的配合下實現負載均衡。

客戶端服務發現模式有很多優點和缺點:這種模式相對簡單,除了服務註冊表之外,其他模塊相對穩定;由於知道哪些服務可用,客戶端就可能做一些更智能的、應用特有的負載均衡策略,比如一致哈希等;一個顯著缺點是將客戶端和服務註冊表耦合在一起,必須根據客戶端使用的開發語言和框架實現服務發現邏輯。

4.服務端服務發現模式

在服務端服務發現模式下,客戶端向服務端的負載均衡器發送請求,負載均衡器查詢服務註冊表,將請求路由到對應的服務實例。像客戶端服務發現模式一樣,服務實例實現向服務註冊表註冊和註銷的功能,示意圖如下:


         AWSElastic Load Balancer (ELB)是服務端服務發現的例子。ELB一般用於來自互聯網的外部負載均衡,實際上,它也可以用於私有云內部的負載均衡。客戶端使用域名訪問ELB,ELB在一組註冊的雲主機或者雲容器之間做負載均衡;ELB中沒有專門的服務註冊表,雲主機直接向ELB註冊。

         NGINXPlus或NGINX作爲HTTP服務器和負載均衡器,也可以作爲服務端服務發現的負載均衡器,比如,可以使用Consul Template動態配置NGINX作爲反向代理。Consul Template能根據Consul service registry存儲的配置數據定期生成配置文件;在文章(https://www.airpair.com/scalable-architecture-with-docker-consul-and-nginx)提到的例子中,Consul Template能動態生成反向代理的配置文件nginx.conf,並執行命令告訴Nginx重新加載配置。使用HTTP接口或者DNS能實現更復雜的Nginx的動態配置。

         像Kubernetes和Marathon等部署環境,集羣中的每個服務實例都需要運行一個代理作爲服務端服務發現的負載均衡器,客戶端請求發送到代理,代理將請求透明轉發到集羣下的某個可用實例。

         服務端服務發現模式也有一些優點和缺點,最大的好處就是服務發現的細節從客戶端剝離了,客戶端不需要實現服務發現的代碼,只需要向負載均衡器發服務請求;況且,有些部署環境已經免費實現了負載均衡的功能。服務端服務發現模式的缺點是,如果部署環境不提供負載均衡功能,你需要實現和管理一個高可用的負載均衡系統,這不是件簡單的事。

5. 服務註冊表

服務註冊表是服務發現機制的關鍵部分,它是保存服務實例網絡地址的數據庫。服務註冊表必須是高可用並保證數據是最新的。客戶端能緩存從服務註冊表取得的服務實例信息,但是這些信息最終會過時,因此包含集羣服務的服務註冊表需要使用複製協議來保證緩存信息的一致性。

就像之前提到的,Netflix Eureka是服務註冊表的一個示例,它爲服務註冊和服務查詢提供REST風格的API。服務實例使用POST請求註冊網絡地址,每隔30秒使用PUT請求刷新狀態。服務註冊表項可以使用DELETE請求主動移除,也會因爲註冊超時被動移除;客戶端使用GET請求獲取可用服務實例。

Netflix通過在每個Amazon EC2可用區域中運行一個或多個Eureka服務器來實現高可用性。Eureka服務器運行在具有彈性IP的EC2實例上,使用DNS TEXT保存Eureka集羣的配置,實現從可用區域到一組Eureka實例網絡地址的映射;Eureka服務啓動後,它會查詢DNS獲取集羣配置,定位到所屬集羣,獲取一個可用的彈性IP。

Eureka 客戶端查詢DNS獲取服務端地址,一般情況下,客戶端傾向與在一個可用區域內使用同一個服務端;如果本區域內的服務端都不可用,纔會使用另外一個可用區域的服務端。

其他服務註冊表包括:

etcd:一致的、分佈式、高可用、使用鍵值存儲的工具,可用於配置共享和服務發現,在Kubernetes和Cloud Foundry中使用。

Consul:另外一個服務配置和服務發現工具,支持服務健康檢查。

Apache Zookeeper:一個廣泛應用的、高效的,應用於分佈式系統的服務協調工具,之前是Hadoop的一個子項目,現在是頂級項目。

Kubernetes、Marathon和AWS沒有單獨的服務註冊表,服務註冊表是它們架構的內置功能。

6.服務註冊選項

有一系列不同的方法實現服務註冊表中服務的註冊和註銷:一種方法是讓服務自己註冊,叫做自注冊模式;另外一種方式是使用第三方組件管理服務註冊,叫做第三方註冊模式。

自注冊模式

當使用自注冊模式時,服務自己負責向服務註冊表註冊和註銷;如果需要,服務實例還需要定期發送心跳以避免超時;下圖展示了這種結構:


Netflix OSS Eureka是自注冊模式的一個例子,Eureka客戶端處理所有服務註冊和服務註銷的問題。在Spring Cloud項目中,使用Eureka很容易實現服務自動註冊,方式是在Java配置類中使用@EnableEurekaClient聲明。

自注冊模式有明顯的優點和缺點:優點是實現簡單,服務註冊時不需要查詢其他系統模塊;缺點是將服務端和服務註冊表耦合在一起,需要根據服務端不同的編程語言和框架實現相應的註冊和註銷邏輯。

第三方註冊模式

使用第三方註冊模式,服務端不用考慮服務註冊和註銷,工作由第三方服務註冊器完成。服務註冊器通過輪詢部署環境或者訂閱事件的方式跟蹤運行服務的變化,當發現新的服務,將其註冊到註冊表中;當服務終止在註冊表中註銷。下圖展示了該模式的結構:


開源的Registrator是服務註冊器的一個例子,它能自動註冊和註銷Docker容器中服務實例,支持多種服務註冊表(包括etcd和Consul)。

另外一個服務註冊器的例子是NetflixOSS Prana,主要用於非JVM語言編寫的服務,它是一個與服務實例並行運行的sidecar應用程序,使用Netflix Eureka註冊和註銷服務實例。

一些部署環境內置了服務註冊器功能:通過可伸縮組創建的Amazon EC2實例可以自動註冊(使用ELB),Kubernetes的服務也能夠實現自動註冊。

使用第三方服務註冊的最大好處是服務和服務註冊表解耦,你不需要根據服務端使用開發語言和框架實現服務註冊邏輯,服務註冊由專門的服務集中負責;缺點是如果部署環境沒有實現服務註冊功能,需要單獨開發和管理一個高可用的服務註冊系統。

7.總結

在微服務架構下,服務實例是動態變化的,服務實例的IP地址是動態分配的,客戶端要請求服務,必須使用服務發現機制。

服務註冊表是服務發現機制的關鍵組成部分,它是所有可用服務實例的數據庫,它提供管理接口和查詢接口;服務實例使用管理接口實現服務的註冊和註銷,系統的其他組成部分使用查詢接口獲取可用服務。

有兩種主要的服務發現模式:客戶端服務發現和服務端服務發現。在使用客戶端服務發現的系統中,客戶端查詢服務註冊表,獲取可用服務,發出服務請求;在使用服務端服務發現的系統中,客戶端向服務路由器發請求,服務路由器查詢服務註冊表,將服務請求轉發給服務實例。

服務註冊也有兩種主要的方式:一種是自注冊模式,服務自己向服務註冊表註冊;另一種是第三方註冊模式,第三方組件代表服務實例進行服務註冊和註銷。

在某些部署環境下,需要使用Netflix Eureka、etcd或者Apache Zookeeper等服務註冊器構建自己的服務發現機制;另外一些部署環境可能內置了服務發現功能,比如,使用Kubernetes和Marathon能實現服務的註冊和註銷,可它們也需要在每一個集羣主機上運行一個代理,充當服務端服務發現的路由器。

Nginx作爲HTTP反向代理服務器和負載均衡器,也能實現服務端服務發現和負載均衡。可以使用Consul Template將服務註冊表的更新推送給Nginx,並調用配置更新指令更新配置;Nginx Plus支持其他動態配置機制:使用DNS從服務註冊表中獲取服務實例信息,提供遠程配置接口進行遠程配置。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章