ServiceMesh最火项目:Istio架构解析
Istio 是一個(gè)開源的服務(wù)網(wǎng)格,可為分布式微服務(wù)架構(gòu)提供所需的基礎(chǔ)運(yùn)行和管理要素。隨著各組織越來越多地采用云平臺(tái),開發(fā)者必須使用微服務(wù)設(shè)計(jì)架構(gòu)以實(shí)現(xiàn)可移植性,而運(yùn)維人員必須管理包含混合云部署和多云部署的大型分布式應(yīng)用。Istio 采用一種一致的方式來保護(hù)、連接和監(jiān)控微服務(wù),降低了管理微服務(wù)部署的復(fù)雜性。
從架構(gòu)設(shè)計(jì)上來看,Istio 服務(wù)網(wǎng)格在邏輯上分為控制平面和數(shù)據(jù)平面兩部分。其中,控制平面 Pilot 負(fù)責(zé)管理和配置代理來路由流量,并配置 Mixer 以實(shí)施策略和收集遙測(cè)數(shù)據(jù);數(shù)據(jù)平面由一組以 Sidecar 方式部署的智能代理(Envoy)組成,這些代理可以調(diào)節(jié)和控制微服務(wù)及 Mixer 之間所有的網(wǎng)絡(luò)通信。
作為代理,Envoy 非常適合服務(wù)網(wǎng)格的場(chǎng)景,但要發(fā)揮 Envoy 的最大價(jià)值,就需要使它很好地與底層基礎(chǔ)設(shè)施或組件緊密配合。Envoy 構(gòu)成了服務(wù)網(wǎng)格的數(shù)據(jù)平面,Istio 提供的支撐組件則是創(chuàng)建了控制平面。
一方面,我們?cè)?Envoy 中看到,可以使用靜態(tài)配置文件或使用一組發(fā)現(xiàn)服務(wù)來配置一組服務(wù)代理,以便在運(yùn)行時(shí)發(fā)現(xiàn)監(jiān)聽器、端點(diǎn)和集群。Istio 在 Pilot 中實(shí)現(xiàn)了這些 Envoy 代理的 xDS API。
另一方面,Envoy 的服務(wù)發(fā)現(xiàn)依賴于某種服務(wù)注冊(cè)表來發(fā)現(xiàn)服務(wù)端點(diǎn)。Istio Pilot 實(shí)現(xiàn)了這個(gè) API,但也將 Envoy 從任何特定的服務(wù)注冊(cè)實(shí)現(xiàn)中抽象出來。當(dāng) Istio 部署在 Kubernetes 上時(shí),Kubernetes 的服務(wù)注冊(cè)表是 Istio 用于服務(wù)發(fā)現(xiàn)的。其它注冊(cè)表也可以像 HashiCorp 的 Consul 那樣使用。Envoy 數(shù)據(jù)平面完全不受這些實(shí)施細(xì)節(jié)的影響。
此外,Envoy 代理可以發(fā)出很多指標(biāo)和遙測(cè)數(shù)據(jù),這些遙測(cè)數(shù)據(jù)發(fā)送到何處,取決于 Envoy 的配置。Istio 提供遙測(cè)接收器 Mixer 作為其控制平面的一部分,Envoy 代理可以將這些數(shù)據(jù)發(fā)送到 Mixer。Envoy 還將分布式跟蹤數(shù)據(jù)發(fā)送到開放式跟蹤引擎(遵循 Open Tracing API)。Istio 可以支持兼容的開放式跟蹤引擎并配置 Envoy 將其跟蹤數(shù)據(jù)發(fā)送到該位置。
剖析 Istio 控制平面
Istio 的控制平面和 Envoy 的數(shù)據(jù)平面共同構(gòu)成了一個(gè)引人注目的服務(wù)網(wǎng)格實(shí)現(xiàn)。兩者都擁有蓬勃發(fā)展和充滿活力的社區(qū),并且面向下一代服務(wù)架構(gòu)。Istio 是獨(dú)立于平臺(tái)的,可運(yùn)行于各種環(huán)境中,包括跨云、內(nèi)部部署、Kubernetes、Mesos 等。你可以在 Kubernetes 上部署 Istio 或在具有 Consul 的 Nomad 上部署。Istio 目前支持在 Kubernetes 上部署的服務(wù)、使用 Consul 注冊(cè)的服務(wù)以及在虛擬機(jī)上部署的服務(wù)。
其中,控制平面部分包括了 Pilot、Mixer、Citadel 和 Galley 四個(gè)組件。參見 Istio 架構(gòu)一圖。
1. Pilot
Istio 的 Pilot 組件用于管理流量,可以控制服務(wù)之間的流量流動(dòng)和 API 調(diào)用,通過 Pilot 可以更好地了解流量,以便在問題出現(xiàn)之前發(fā)現(xiàn)問題。這使得調(diào)用更加可靠、網(wǎng)絡(luò)更加強(qiáng)健,即使遇到不利條件也能讓應(yīng)用穩(wěn)如磐石。借助 Istio 的 Pilot,你能夠配置熔斷器、超時(shí)和重試等服務(wù)級(jí)屬性,并設(shè)置常見的連續(xù)部署任務(wù),如金絲雀發(fā)布、A/B 測(cè)試和基于百分比拆分流量的分階段發(fā)布。Pilot 為 Envoy 代理提供服務(wù)發(fā)現(xiàn)功能,為智能路由和彈性能力(如超時(shí)、重試、熔斷器等)提供流量管理功能。Pilot 將控制流量行為的高級(jí)路由規(guī)則轉(zhuǎn)換為特定于 Envoy 代理的配置,并在運(yùn)行時(shí)將它們傳播到 Envoy。此外,Istio 提供了強(qiáng)大的開箱即用故障恢復(fù)功能,包括超時(shí)、支持超時(shí)預(yù)算和變量抖動(dòng)的重試機(jī)制、發(fā)往上游服務(wù)的并發(fā)連接和請(qǐng)求數(shù)限制、對(duì)負(fù)載均衡池中的每個(gè)成員進(jìn)行的定期主動(dòng)運(yùn)行狀況檢查,以及被動(dòng)運(yùn)行狀況檢查。
Pilot 將平臺(tái)特定的服務(wù)發(fā)現(xiàn)機(jī)制抽象化并將其合成為標(biāo)準(zhǔn)格式,符合數(shù)據(jù)平面 API 的任何 Sidecar 都可以使用這種標(biāo)準(zhǔn)格式。這種松散耦合使得 Istio 能夠在多種環(huán)境下運(yùn)行(例如 Kubernetes、Consul、Nomad),同時(shí)可保持用于流量管理的操作界面相同。
2. Mixer
Istio 的 Mixer 組件提供策略控制和遙測(cè)收集功能,將 Istio 的其余部分與各個(gè)后端基礎(chǔ)設(shè)施后端的實(shí)現(xiàn)細(xì)節(jié)隔離開來。Mixer 是一個(gè)獨(dú)立于平臺(tái)的組件,負(fù)責(zé)在服務(wù)網(wǎng)格上執(zhí)行訪問控制和使用策略,并從 Envoy 代理和其他服務(wù)收集遙測(cè)數(shù)據(jù)。代理提取請(qǐng)求級(jí)屬性,發(fā)送到 Mixer 進(jìn)行評(píng)估。
Mixer 中包括一個(gè)靈活的插件模型,使其能夠接入到各種主機(jī)環(huán)境和后端基礎(chǔ)設(shè)施,從這些細(xì)節(jié)中抽象出 Envoy 代理和 Istio 管理的服務(wù)。利用 Mixer,你可以精細(xì)控制網(wǎng)格和后端基礎(chǔ)設(shè)施后端之間的所有交互。
與必須節(jié)省內(nèi)存的 Sidecar 代理不同,Mixer 獨(dú)立運(yùn)行,因此它可以使用相當(dāng)大的緩存和輸出緩沖區(qū),充當(dāng) Sidecar 的高度可伸縮且高度可用的二級(jí)緩存。
Mixer 旨在為每個(gè)實(shí)例提供高可用性。它的本地緩存和緩沖區(qū)可以減少延遲時(shí)間,還有助于屏蔽后端基礎(chǔ)設(shè)施后端故障,即使后端沒有響應(yīng)也是如此。
3. Citadel
Istio Citadel 安全功能提供強(qiáng)大的身份驗(yàn)證功能、強(qiáng)大的策略、透明的 TLS 加密以及用于保護(hù)服務(wù)和數(shù)據(jù)的身份驗(yàn)證、授權(quán)和審計(jì)(AAA)工具,Envoy 可以終止或向網(wǎng)格中的服務(wù)發(fā)起 TLS 流量。為此,Citadel 需要支持創(chuàng)建、簽署和輪換證書。Istio Citadel 提供特定于應(yīng)用程序的證書,可用于建立雙向 TLS 以保護(hù)服務(wù)之間的流量。
借助 Istio Citadel,確保只能從經(jīng)過嚴(yán)格身份驗(yàn)證和授權(quán)的客戶端訪問包含敏感數(shù)據(jù)的服務(wù)。Citadel 通過內(nèi)置身份和憑證管理提供了強(qiáng)大的服務(wù)間和最終用戶身份驗(yàn)證。可用于升級(jí)服務(wù)網(wǎng)格中未加密的流量,并為運(yùn)維人員提供基于服務(wù)標(biāo)識(shí)而不是網(wǎng)絡(luò)控制的強(qiáng)制執(zhí)行策略的能力。Istio 的配置策略在服務(wù)器端配置平臺(tái)身份驗(yàn)證,但不在客戶端強(qiáng)制實(shí)施該策略,同時(shí)允許你指定服務(wù)的身份驗(yàn)證要求。Istio 的密鑰管理系統(tǒng)可自動(dòng)生成、分發(fā)、輪換與撤銷密鑰和證書。
Istio RBAC 為 Istio 網(wǎng)格中的服務(wù)提供命名空間級(jí)別、服務(wù)級(jí)別和方法級(jí)別的訪問權(quán)限控制,包括易于使用的基于角色的語義、服務(wù)到服務(wù)和最終用戶到服務(wù)的授權(quán),并在角色和角色綁定方面提供靈活的自定義屬性支持。
Istio 可以增強(qiáng)微服務(wù)及其通信(包括服務(wù)到服務(wù)和最終用戶到服務(wù)的通信)的安全性,且不需要更改服務(wù)代碼。它為每個(gè)服務(wù)提供基于角色的強(qiáng)大身份機(jī)制,以實(shí)現(xiàn)跨集群、跨云端的交互操作。
4. Galley
Galley 用于驗(yàn)證用戶編寫的 Istio API 配置。隨著時(shí)間的推移,Galley 將接管 Istio 獲取配置、處理和分配組件的頂級(jí)責(zé)任。它負(fù)責(zé)將其他的 Istio 組件與從底層平臺(tái)(例如 Kubernetes)獲取用戶配置的細(xì)節(jié)中隔離開來。
總而言之,通過 Pilot,Istio 可在部署規(guī)模逐步擴(kuò)大的過程中幫助你簡(jiǎn)化流量管理。通過 Mixer,借助強(qiáng)健且易于使用的監(jiān)控功能,能夠快速有效地檢測(cè)和修復(fù)問題。通過 Citadel,減輕安全負(fù)擔(dān),讓開發(fā)者可以專注于其他關(guān)鍵任務(wù)。
Istio 的架構(gòu)設(shè)計(jì)中有幾個(gè)關(guān)鍵目標(biāo),這些目標(biāo)對(duì)于系統(tǒng)應(yīng)對(duì)大規(guī)模流量和高性能的服務(wù)處理至關(guān)重要。
- 最大化透明度:要采用 Istio,應(yīng)該讓運(yùn)維和開發(fā)人員只需付出很少的代價(jià)就可以從中獲得實(shí)際價(jià)值。為此,Istio 將自身自動(dòng)注入到服務(wù)間所有的網(wǎng)絡(luò)路徑中。Istio 使用 Envoy 代理來捕獲流量,并且在可能的情況下自動(dòng)對(duì)網(wǎng)絡(luò)層進(jìn)行編程,以便通過這些代理路由流量,而無需對(duì)已部署的應(yīng)用程序代碼進(jìn)行太多的更改,甚至不需要任何更改。在 Kubernetes 中,Envoy 代理被注入到 pod 中,通過 iptables 規(guī)則來捕獲流量。一旦注入 Envoy 代理到 pod 中并且修改路由規(guī)則,Istio 就能夠調(diào)節(jié)所有流量。這個(gè)原則也適用于性能。當(dāng)將 Istio 用于部署時(shí),運(yùn)維人員可以發(fā)現(xiàn),為提供這些功能而增加的資源開銷是很小的。所有組件和 API 在設(shè)計(jì)時(shí)都必須考慮性能和規(guī)模。
- 可擴(kuò)展性:隨著運(yùn)維人員和開發(fā)人員越來越依賴 Istio 提供的功能,系統(tǒng)必然和他們的需求一起成長(zhǎng)。在我們繼續(xù)添加新功能的同時(shí),最需要的是能夠擴(kuò)展策略系統(tǒng),集成其他策略和控制來源,并將網(wǎng)格行為信號(hào)傳播到其他系統(tǒng)進(jìn)行分析。策略運(yùn)行時(shí)支持標(biāo)準(zhǔn)擴(kuò)展機(jī)制以便插入到其他服務(wù)中。此外,它允許擴(kuò)展詞匯表,以允許基于網(wǎng)格生成的新信號(hào)來強(qiáng)制執(zhí)行策略。
- 可移植性:使用 Istio 的生態(tài)系統(tǒng)在很多方面都有所不同。Istio 必須能夠以最少的代價(jià)運(yùn)行在任何云或本地環(huán)境中。將基于 Istio 的服務(wù)移植到新環(huán)境應(yīng)該是輕而易舉的,而使用 Istio 將一個(gè)服務(wù)同時(shí)部署到多個(gè)環(huán)境中也是可行的,例如可以在混合云上部署以實(shí)現(xiàn)冗余災(zāi)備。
- 策略一致性:策略應(yīng)用于服務(wù)之間的 API 調(diào)用,可以很好地控制網(wǎng)格行為。但對(duì)于無需在 API 級(jí)別表達(dá)的資源來說,對(duì)資源應(yīng)用策略也同樣重要。例如,將配額應(yīng)用到機(jī)器學(xué)習(xí)訓(xùn)練任務(wù)消耗的 CPU 數(shù)量上,比將配額應(yīng)用到啟動(dòng)這個(gè)工作的調(diào)用上更為有用。因此,Istio 將策略系統(tǒng)維護(hù)為具有自己的 API 的獨(dú)特服務(wù),而不是將其放到代理中,這允許服務(wù)根據(jù)需要直接與其集成。
剖析 Istio 數(shù)據(jù)平面
當(dāng)介紹服務(wù)網(wǎng)格的概念時(shí),提到了服務(wù)代理的概念以及如何使用代理構(gòu)建一個(gè)服務(wù)網(wǎng)格,以調(diào)節(jié)和控制微服務(wù)之間的所有網(wǎng)絡(luò)通信。Istio 使用 Envoy 代理作為默認(rèn)的開箱即用服務(wù)代理,這些 Envoy 代理與參與服務(wù)網(wǎng)格的所有應(yīng)用程序?qū)嵗黄疬\(yùn)行,但不在同一個(gè)容器進(jìn)程中,形成了服務(wù)網(wǎng)格的數(shù)據(jù)平面。只要應(yīng)用程序想要與其他服務(wù)通信,就會(huì)通過服務(wù)代理 Envoy 進(jìn)行。由此可見,Envoy 代理是數(shù)據(jù)平面和整個(gè)服務(wù)網(wǎng)格架構(gòu)中的關(guān)鍵組成部分。
1. Envoy 代理
Envoy 最初是由 Lyft 開發(fā)的,用于解決構(gòu)建分布式系統(tǒng)時(shí)出現(xiàn)的一些復(fù)雜的網(wǎng)絡(luò)問題。它于 2016 年 9 月作為開源項(xiàng)目提供,一年后加入了云原生計(jì)算基金會(huì)(CNCF)。Envoy 是用 C++ 語言實(shí)現(xiàn)的,具有很高的性能,更重要的是,它在高負(fù)載運(yùn)行時(shí)也非常穩(wěn)定和可靠。網(wǎng)絡(luò)對(duì)應(yīng)用程序來說應(yīng)該是透明的,當(dāng)網(wǎng)絡(luò)和應(yīng)用程序出現(xiàn)問題時(shí),應(yīng)該很容易確定問題的根源。正是基于這樣的一種設(shè)計(jì)理念,將 Envoy 設(shè)計(jì)為一個(gè)面向服務(wù)架構(gòu)的七層代理和通信總線。
為了更好地理解 Envoy,我們需要先搞清楚相關(guān)的幾個(gè)基本術(shù)語:
- 進(jìn)程外(Out of Process)架構(gòu):Envoy 是一個(gè)獨(dú)立進(jìn)程,Envoy 之間形成一個(gè)透明的通信網(wǎng)格,每個(gè)應(yīng)用程序發(fā)送消息到本地主機(jī)或從本地主機(jī)接收消息,但無需關(guān)心網(wǎng)絡(luò)拓?fù)洹?/li>
- 單進(jìn)程多線程模型:Envoy 使用了單進(jìn)程多線程的架構(gòu)模型。一個(gè)主線程管理各種瑣碎的任務(wù),而一些工作子線程則負(fù)責(zé)執(zhí)行監(jiān)聽、過濾和轉(zhuǎn)發(fā)功能。
- 下游(Downstream):連接到 Envoy 并發(fā)送請(qǐng)求、接收響應(yīng)的主機(jī)叫下游主機(jī),也就是說下游主機(jī)代表的是發(fā)送請(qǐng)求的主機(jī)。
- 上游(Upstream):與下游相對(duì),接收請(qǐng)求的主機(jī)叫上游主機(jī)。
- 監(jiān)聽器(Listener):監(jiān)聽器是命名網(wǎng)絡(luò)地址,包括端口、unix domain socket 等,可以被下游主機(jī)連接。Envoy 暴露一個(gè)或者多個(gè)監(jiān)聽器給下游主機(jī)連接。每個(gè)監(jiān)聽器都獨(dú)立配置一些網(wǎng)絡(luò)級(jí)別(即三層或四層)的過濾器。當(dāng)監(jiān)聽器接收到新連接時(shí),配置好的本地過濾器將被實(shí)例化,并開始處理后續(xù)事件。一般來說監(jiān)聽器架構(gòu)用于執(zhí)行絕大多數(shù)不同的代理任務(wù),例如限速、TLS 客戶端認(rèn)證、HTTP 連接管理、MongoDB sniff?ing、原始 TCP 代理等。
- 集群(Cluster):集群是指 Envoy 連接的一組邏輯相同的上游主機(jī)。
- xDS 協(xié)議:在 Envoy 中 xDS 協(xié)議代表的是多個(gè)發(fā)現(xiàn)服務(wù)協(xié)議,包括集群發(fā)現(xiàn)服務(wù)(CDS,
Cluster Discovery Service)、監(jiān)聽器發(fā)現(xiàn)服務(wù)(LDS,Listener Discovery Service)、路由發(fā)現(xiàn)服務(wù)(RDS,Route Discovery Service)、端點(diǎn)發(fā)現(xiàn)服務(wù)(EDS,Endpoint Discovery Service),以及密鑰發(fā)現(xiàn)服務(wù)(SDS,Secret Discovery Service)。
Envoy 代理有許多功能可用于服務(wù)間通信,例如,暴露一個(gè)或者多個(gè)監(jiān)聽器給下游主機(jī)連接,通過端口暴露給外部的應(yīng)用程序;通過定義路由規(guī)則處理監(jiān)聽器中傳輸?shù)牧髁?#xff0c;并將該流量定向到目標(biāo)集群,等等。后續(xù)章節(jié)會(huì)進(jìn)一步分析這幾個(gè)發(fā)現(xiàn)服務(wù)在 Istio 中的角色和作用。
在了解了 Envoy 的術(shù)語之后,你可能想盡快知道 Envoy 到底起到了什么作用?
首先,Envoy 是一種代理,在網(wǎng)絡(luò)體系架構(gòu)中扮演著中介的角色,可以為網(wǎng)絡(luò)中的流量管理添加額外的功能,包括提供安全性、隱私保護(hù)或策略等。在服務(wù)間調(diào)用的場(chǎng)景中,代理可以為客戶端隱藏服務(wù)后端的拓?fù)浼?xì)節(jié),簡(jiǎn)化交互的復(fù)雜性,并保護(hù)后端服務(wù)不會(huì)過載。例如,后端服務(wù)實(shí)際上是運(yùn)行的一組相同實(shí)例,每個(gè)實(shí)例能夠處理一定量的負(fù)載。
其次,Envoy 中的集群(Cluster)本質(zhì)上是指 Envoy 連接到的邏輯上相同的一組上游主機(jī)。那么客戶端如何知道在與后端服務(wù)交互時(shí)要使用哪個(gè)實(shí)例或 IP 地址?Envoy 作為代理起到了路由選擇的作用,通過服務(wù)發(fā)現(xiàn)(SDS,Service Discovery Service),Envoy 代理發(fā)現(xiàn)集群中的所有成員,然后通過主動(dòng)健康檢查來確定集群成員的健康狀態(tài),并根據(jù)健康狀態(tài),通過負(fù)載均衡策略決定將請(qǐng)求路由到哪個(gè)集群成員。而在 Envoy 代理處理跨服務(wù)實(shí)例的負(fù)載均衡過程中,客戶端不需要知道實(shí)際部署的任何細(xì)節(jié)。
2. Envoy 的啟動(dòng)配置
Envoy 目前提供了兩個(gè)版本的 API,即 v1 和 v2,從 Envoy 1.5.0 起就有 v2 API 了,為了能夠讓用戶順利地向 v2 版本 API 遷移,Envoy 啟動(dòng)的時(shí)候設(shè)置了一個(gè)參數(shù)--v2-conf?ig-only。通過這個(gè)參數(shù),可以明確指定 Envoy 使用 v2 API 的協(xié)議。幸運(yùn)的是,v2 API 是 v1 的一個(gè)超集,兼容 v1 的 API。在當(dāng)前的 Istio 1.0 之后的版本中,明確指定了其支持 v2 的 API。通過查看使用 Envoy 作為 Sidecar 代理的容器啟動(dòng)命令,可以看到如下類似的啟動(dòng)參數(shù),其中指定了參數(shù)--v2-config-only:
$ /usr/local/bin/envoy -c /etc/istio/proxy/envoy-rev0.json --restart-epoch 0 --drain-time-s 45 --parent-shutdown-time-s 60 --service-cluster ratings --service-node sidecar~172.33.14.2~ratings-v1-8558d4458d-ld8x9.default~default.svc.cluster.local --max-obj-name-len 189 --allow-unknown-fields -l warn --v2-config-only其中,參數(shù) -c 表示的是基于版本 v2 的引導(dǎo)配置文件的路徑,格式為 JSON,也支持其他格式,如 YAML、Proto3等。它會(huì)首先作為版本 v2 的引導(dǎo)配置文件進(jìn)行解析,若解析失敗,會(huì)根據(jù) [--v2-conf?ig-only] 選項(xiàng)決定是否作為版本 v1 的 JSON 配置文件進(jìn)行解析。其他參數(shù)解釋如下,以便讀者及時(shí)理解 Envoy 代理啟動(dòng)時(shí)的配置信息:
- restart-epoch 表示熱重啟周期,對(duì)于第一次啟動(dòng)默認(rèn)為 0,每次熱重啟后都應(yīng)該增加它。
- service-cluster 定義 Envoy 運(yùn)行的本地服務(wù)集群名稱。
- service-node 定義 Envoy 運(yùn)行的本地服務(wù)節(jié)點(diǎn)名稱。
- drain-time-s 表示熱重啟期間 Envoy 將耗盡連接的時(shí)間(秒),默認(rèn)為 600 秒(10 分鐘)。通常耗盡時(shí)間應(yīng)小于通過 --parent-shutdown-time-s 選項(xiàng)設(shè)置的父進(jìn)程關(guān)閉時(shí)間。
- parent-shutdown-time-s 表示 Envoy 在熱重啟時(shí)關(guān)閉父進(jìn)程之前等待的時(shí)間(秒)。
- max-obj-name-len 描述的是集群 cluster、路由配置 route_conf?ig 以及監(jiān)聽器 listener 中名稱字段的最大長(zhǎng)度,以字節(jié)為單位。此選項(xiàng)通常用于自動(dòng)生成集群名稱的場(chǎng)景,通常會(huì)超過 60 個(gè)字符的內(nèi)部限制。默認(rèn)為 60。
- Envoy 的啟動(dòng)配置文件分為兩種方式:靜態(tài)配置和動(dòng)態(tài)配置。具體表現(xiàn)為:
- 靜態(tài)配置是將所有信息都放在配置文件中,啟動(dòng)的時(shí)候直接加載。
- 動(dòng)態(tài)配置需要提供一個(gè) Envoy 的服務(wù)端,用于動(dòng)態(tài)生成 Envoy 需要的服務(wù)發(fā)現(xiàn)接口,也就是通常說的 xDS,通過發(fā)現(xiàn)服務(wù)來動(dòng)態(tài)調(diào)整配置信息,Istio 實(shí)現(xiàn)了 v2 的 xDS API。
3. Envoy 靜態(tài)與動(dòng)態(tài)配置
Envoy 是由 JSON 或 YAML 格式的配置文件驅(qū)動(dòng)的智能代理,對(duì)于已經(jīng)熟悉 Envoy 或 Envoy 配置的用戶來說,相信應(yīng)該已經(jīng)知道了 Envoy 的配置也有不同的版本。初始版本 v1 是 Envoy 啟動(dòng)時(shí)配置 Envoy 的原始方式。此版本已被棄用,以支持 Envoy 配置的 v2 版本。Envoy 的參考文檔(https://www.envoyproxy.io/docs)還提供了明確區(qū)分 v1 和 v2 的文檔。本文將只關(guān)注 v2 配置,因?yàn)樗亲钚碌陌姹?#xff0c;也是 Istio 使用的版本。
Envoy 版本 v2 的配置 API 建立在 gRPC 之上,v2 API 的一個(gè)重要特性是可以在調(diào)用 API 時(shí)利用流功能來減少 Envoy 代理匯聚配置所需的時(shí)間。實(shí)際上,這也消除了輪詢 API 的弊端,允許服務(wù)器將更新推送到 Envoy 代理,而不是定期輪詢代理。
Envoy 的架構(gòu)使得使用不同類型的配置管理方法成為可能。部署中采用的方法將取決于實(shí)現(xiàn)者的需求。簡(jiǎn)單部署可以通過全靜態(tài)配置來實(shí)現(xiàn),更復(fù)雜的部署可以遞增地添加更復(fù)雜的動(dòng)態(tài)配置。主要分為以下幾種情況:
- 全靜態(tài):在全靜態(tài)配置中,實(shí)現(xiàn)者提供一組監(jiān)聽器和過濾器鏈、集群和可選的 HTTP 路由配置。動(dòng)態(tài)主機(jī)發(fā)現(xiàn)僅能通過基于 DNS 的服務(wù)發(fā)現(xiàn)。配置重載必須通過內(nèi)置的熱重啟機(jī)制進(jìn)行。
- 僅SDS/EDS:在靜態(tài)配置之上,Envoy 可以通過該機(jī)制發(fā)現(xiàn)上游集群中的成員。
- SDS/EDS 和 CDS:Envoy 可以通過該機(jī)制發(fā)現(xiàn)使用的上游集群。
- SDS/EDS、CDS 和 RDS:RDS 可以在運(yùn)行時(shí)發(fā)現(xiàn)用于 HTTP 連接管理器過濾器的整個(gè)路由配置。
- SDS/EDS、CDS、RDS 和 LDS:LDS 可以在運(yùn)行時(shí)發(fā)現(xiàn)整個(gè)監(jiān)聽器。這包括所有的過濾器堆棧,包括帶有內(nèi)嵌到 RDS 的應(yīng)用的 HTTP 過濾器。
靜態(tài)配置
我們可以使用 Envoy 的配置文件指定監(jiān)聽器、路由規(guī)則和集群。如下示例提供了一個(gè)非常簡(jiǎn)單的 Envoy 配置:
static_resources:listeners:- name: httpbin-demoaddress:socket_address: { address: 0.0.0.0, port_value: 15001 }filter_chains:- filters:- name: envoy.http_connection_managerconfig:stat_prefix: egress_httproute_config:name: httpbin_local_routevirtual_hosts:- name: httpbin_local_servicedomains: ["*"]routes:- match: { prefix: "/" }route:auto_host_rewrite: truecluster: httpbin_servicehttp_filters:- name: envoy.routerclusters:- name: httpbin_serviceconnect_timeout: 5stype: LOGICAL_DNS# Comment out the following line to test on v6 networksdns_lookup_family: V4_ONLYlb_policy: ROUND_ROBINhosts: [{ socket_address: { address: httpbin, port_value: 8000 }}]在這個(gè)簡(jiǎn)單的 Envoy 配置文件中,我們聲明了一個(gè)監(jiān)聽器,它在端口 15001 上打開一個(gè)套接字并為其附加一個(gè)過濾器鏈。過濾器 http_connection_manager 在 Envoy 配置中使用路由指令(在此示例中看到的簡(jiǎn)單路由指令是匹配所有虛擬主機(jī)的通配符),并將所有流量路由到 httpbin_service 集群。配置的最后一部分定義了 httpbin_service 集群的連接屬性。在此示例中,我們指定端點(diǎn)服務(wù)發(fā)現(xiàn)的類型為 LOGICAL_DNS、與上游 httpbin 服務(wù)通信時(shí)的負(fù)載均衡算法為 ROUND_ROBIN。
這是一個(gè)簡(jiǎn)單的配置文件,用于創(chuàng)建監(jiān)聽器傳入的流量,并將所有流量路由到 httpbin 集群。它還指定要使用的負(fù)載均衡算法的設(shè)置以及要使用的連接超時(shí)配置。
你會(huì)注意到很多配置是明確指定的,例如指定了哪些監(jiān)聽器,路由規(guī)則是什么,我們可以路由到哪些集群等。這是完全靜態(tài)配置文件的示例。
有關(guān)這些參數(shù)更多信息的解釋,請(qǐng)參閱 Envoy 的文檔(www.envoyproxy.io/docs/envoy/latest/intro/arch_overview/service_discovery#logical-dns)。
在前面的部分中,我們指出 Envoy 能夠動(dòng)態(tài)配置其各種設(shè)置。下面將介紹 Envoy 的動(dòng)態(tài)配置以及 Envoy 如何使用 xDS API 進(jìn)行動(dòng)態(tài)配置。
動(dòng)態(tài)配置
Envoy 可以利用一組 API 進(jìn)行配置更新,而無需任何停機(jī)或重啟。Envoy 只需要一個(gè)簡(jiǎn)單的引導(dǎo)配置文件,該配置文件將配置指向正確的發(fā)現(xiàn)服務(wù) API,其余動(dòng)態(tài)配置。Envoy 進(jìn)行動(dòng)態(tài)配置的 API 通常統(tǒng)稱為 xDS 服務(wù),具體包括如下:
- 監(jiān)聽器發(fā)現(xiàn)服務(wù)(LDS):一種允許 Envoy 查詢整個(gè)監(jiān)聽器的機(jī)制,通過調(diào)用該 API 可以動(dòng)態(tài)添加、修改或刪除已知監(jiān)聽器;每個(gè)監(jiān)聽器都必須具有唯一的名稱。如果未提供名稱,Envoy 將創(chuàng)建一個(gè) UUID。
- 路由發(fā)現(xiàn)服務(wù)(RDS):Envoy 動(dòng)態(tài)獲取路由配置的機(jī)制,路由配置包括 HTTP 標(biāo)頭修改、虛擬主機(jī)以及每個(gè)虛擬主機(jī)中包含的單個(gè)路由規(guī)則。每個(gè) HTTP 連接管理器都可以通過 API 獨(dú)立地獲取自身的路由配置。RDS 配置隸屬于監(jiān)聽器發(fā)現(xiàn)服務(wù) LDS 的一部分,是 LDS 的一個(gè)子集,用于指定何時(shí)應(yīng)使用靜態(tài)和動(dòng)態(tài)配置,以及指定使用哪個(gè)路由。
- 集群發(fā)現(xiàn)服務(wù)(CDS):一個(gè)可選的 API,Envoy 將調(diào)用該 API 來動(dòng)態(tài)獲取集群管理成員。Envoy 還將根據(jù) API 響應(yīng)協(xié)調(diào)集群管理,根據(jù)需要添加、修改或刪除已知的集群。在 Envoy 配置中靜態(tài)定義的任何集群都不能通過 CDS API 進(jìn)行修改或刪除。
- 端點(diǎn)發(fā)現(xiàn)服務(wù)(EDS):一種允許 Envoy 獲取集群成員的機(jī)制,基于 gRPC 或 RESTJSON 的 API,它是 CDS 的一個(gè)子集;集群成員在 Envoy 術(shù)語中稱為端點(diǎn)(Endpoint)。對(duì)于每個(gè)集群,Envoy 從發(fā)現(xiàn)服務(wù)獲取端點(diǎn)。EDS 是首選的服務(wù)發(fā)現(xiàn)機(jī)制。
- 密鑰發(fā)現(xiàn)服務(wù)(SDS):用于分發(fā)證書的 API;SDS 最重要的好處是簡(jiǎn)化證書管理。如果沒有此功能,在 Kubernetes 部署中,必須將證書創(chuàng)建為密鑰并掛載到 Envoy 代理容器中。如果證書過期,則需要更新密鑰并且需要重新部署代理容器。使用密鑰發(fā)現(xiàn)服務(wù) SDS,那么 SDS 服務(wù)器會(huì)將證書推送到所有 Envoy 實(shí)例。如果證書過期,服務(wù)器只需將新證書推送到 Envoy 實(shí)例,Envoy 將立即使用新證書而無需重新部署。
- 聚合發(fā)現(xiàn)服務(wù)(ADS):上述其他 API 的所有更改的序列化流;你可以使用此單個(gè) API 按順序獲取所有更改;ADS 并不是一個(gè)實(shí)際意義上的 xDS,它提供了一個(gè)匯聚的功能,在需要多個(gè)同步 xDS 訪問的時(shí)候,ADS 可以在一個(gè)流中完成。
配置可以使用上述服務(wù)中的一個(gè)或其中幾個(gè)的組合,不必全部使用它們。需要注意的一點(diǎn)是,Envoy 的 xDS API 是建立在最終一致性的前提下,正確的配置最終會(huì)收斂。例如,Envoy 最終可能會(huì)使用新路由獲取RDS的更新,該路由將流量路由到尚未在 CDS 中更新的集群。這意味著,路由可能會(huì)引入路由錯(cuò)誤,直到更新 CDS。Envoy 引入了聚合發(fā)現(xiàn)服務(wù) ADS 來解決這種問題,而 Istio 實(shí)現(xiàn)了聚合發(fā)現(xiàn)服務(wù) ADS,并使用 ADS 進(jìn)行代理配置的更改。
例如,Envoy 代理要?jiǎng)討B(tài)發(fā)現(xiàn)監(jiān)聽器,可以使用如下配置:
dynamic_resources:lds_config:api_config_source:api_type: GRPCgrpc_services:- envoy_grpc:cluster_name: xds_cluster clusters: - name: xds_clusterconnect_timeout: 0.25stype: STATIClb_policy: ROUND_ROBINhttp2_protocol_options: {}hosts: [{ socket_address: { address: 127.0.0.3, port_value: 5678 }}]通過上面的配置,我們不需要在配置文件中顯式配置每個(gè)監(jiān)聽器。我們告訴 Envoy 使用 LDS API 在運(yùn)行時(shí)發(fā)現(xiàn)正確的監(jiān)聽器配置值。但是,我們需要明確配置一個(gè)集群,這個(gè)集群就是 LDS API 所在的位置,也就是該示例中定義的集群 xds_cluster。
在靜態(tài)配置的基礎(chǔ)上,比較直觀地表示出各個(gè)發(fā)現(xiàn)服務(wù)所提供的信息。
在靜態(tài)配置的基礎(chǔ)上,比較直觀地表示出各個(gè)發(fā)現(xiàn)服務(wù)所提供的信息。
本文摘自于《Istio 服務(wù)網(wǎng)格解析與實(shí)戰(zhàn)》,經(jīng)出版方授權(quán)發(fā)布。本書由阿里云高級(jí)技術(shù)專家王夕寧撰寫,詳細(xì)介紹 Istio 的基本原理與開發(fā)實(shí)戰(zhàn),包含大量精選案例和參考代碼可以下載,可快速入門 Istio 開發(fā)。Gartner 認(rèn)為,2020 年服務(wù)網(wǎng)格將成為所有領(lǐng)先的容器管理系統(tǒng)的標(biāo)配技術(shù)。本書適合所有對(duì)微服務(wù)和云原生感興趣的讀者,推薦大家對(duì)本書進(jìn)行深入的閱讀。
原文鏈接
本文為云棲社區(qū)原創(chuàng)內(nèi)容,未經(jīng)允許不得轉(zhuǎn)載。
總結(jié)
以上是生活随笔為你收集整理的ServiceMesh最火项目:Istio架构解析的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【深度学习】基于 Alluxio 数据缓
- 下一篇: 汽车产业云上多地域高可用消息系统构建