天天看點

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

轉載:https://juejin.im/post/5c5408ee6fb9a049f154a160

ServiceMesher 2019年02月01日 閱讀 70

騰訊雲容器團隊内部Istio專題分享

本文轉載自:zhongfox.github.io/2019/01/30/…

今天分享的内容主要包括以下4個話題:

  • 1 Service Mesh: 下一代微服務
  • 2 Istio: 第二代 Service Mesh
  • 3 Istio 資料面
  • 4 Istio 控制面

首先我會和大家一起過一下 Service Mesh的發展曆程, 并看看Istio 為 Service Mesh 帶來了什麼, 這部分相對比較輕松. 接下來我将和大家分析一下Istio的主要架構, 重點是資料面和控制面的實作, 包括sidecar的注入, 流量攔截, xDS介紹, Istio流量模型, 分布式跟蹤, Mixer 的擴充卡模型等等, 中間也會穿插着 istio的現場使用demo.

1. Service Mesh: 下一代微服務

  • 應用通信模式演進
  • Service Mesh(服務網格)的出現
  • 第二代 Service Mesh
  • Service Mesh 的定義
  • Service Mesh 産品簡史
  • 國内Service Mesh 發展情況

1.1 應用通信模式演進: 網絡流控進入作業系統

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

在計算機網絡發展的初期, 開發人員需要在自己的代碼中處理伺服器之間的網絡連接配接問題, 包括流量控制, 緩存隊列, 資料加密等. 在這段時間内底層網絡邏輯和業務邏輯是混雜在一起.

随着技術的發展,TCP/IP 等網絡标準的出現解決了流量控制等問題。盡管網絡邏輯代碼依然存在,但已經從應用程式裡抽離出來,成為作業系統網絡層的一部分, 形成了經典的網絡分層模式.

1.2 應用通信模式演進: 微服務架構的出現

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

微服務架構是更為複雜的分布式系統,它給運維帶來了更多挑戰, 這些挑戰主要包括資源的有效管理和服務之間的治理, 如:

  • 服務注冊, 服務發現
  • 服務伸縮
  • 健康檢查
  • 快速部署
  • 服務容錯: 斷路器, 限流, 隔離艙, 熔斷保護, 服務降級等等
  • 認證和授權
  • 灰階釋出方案
  • 服務調用可觀測性, 名額收集
  • 配置管理

在微服務架構的實作中,為提升效率和降低門檻,應用開發者會基于微服務架構來實作微服務。微服務架構一定程度上為使用者屏蔽了底層網絡的複雜性及分布式場景下的不确定性。通過API/SDK的方式提供服務注冊發現、服務RPC通信、服務配置管理、服務負載均衡、路由限流、容錯、服務監控及治理、服務釋出及更新等通用能力, 比較典型的産品有:

  • 分布式RPC通信架構: COBRA, WebServices, Thrift, GRPC 等
  • 服務治理特定領域的類庫和解決方案: Hystrix, Zookeeper, Zipkin, Sentinel 等
  • 對多種方案進行整合的微服務架構: SpringCloud、Finagle、Dubbox 等

實施微服務的成本往往會超出企業的預期(内容多, 門檻高), 花在服務治理上的時間成本甚至可能高過進行産品研發的時間. 另外上述的方案會限制可用的工具、運作時和程式設計語言。微服務軟體庫一般專注于某個平台, 這使得異構系統難以相容, 存在重複的工作, 系統缺乏可移植性.

Docker 和Kubernetes 技術的流行, 為Pass資源的配置設定管理和服務的部署提供了新的解決方案, 但是微服務領域的其他服務治理問題仍然存在.

1.3 Sidecar 模式的興起

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Sidecar(有時會叫做agent) 在原有的用戶端和服務端之間加多了一個代理, 為應用程式提供的額外的功能, 如服務發現, 路由代理, 認證授權, 鍊路跟蹤 等等.

業界使用Sidecar 的一些先例:

  • 2013 年,Airbnb 開發了Synapse 和 Nerve,是sidecar的一種開源實作
  • 2014 年, Netflix 釋出了Prana,它也是一個sidecar,可以讓非 JVM 應用接入他們的 NetflixOSS 生态系統

1.4 Service Mesh(服務網格)的出現

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

直覺地看, Sidecar 到 Service Mesh 是一個規模的更新, 不過Service Mesh更強調的是:

  • 不再将Sidecar(代理)視為單獨的元件,而是強調由這些代理連接配接而形成的網絡
  • 基礎設施, 對應用程式透明

1.5 Service Mesh 定義

以下是Linkerd的CEO Willian Morgan給出的Service Mesh的定義:

A Service Mesh is a dedicated infrastructure layer for handling service-to-service communication. It’s responsible for the reliable delivery of requests through the complex topology of services that comprise a modern, cloud native application. In practice, the Service Mesh is typically implemented as an array of lightweight network proxies that are deployed alongside application code, without the application needing to be aware.

服務網格(Service Mesh)是緻力于解決服務間通訊的

基礎設施層

。它負責在現代雲原生應用程式的複雜服務拓撲來可靠地傳遞請求。實際上,Service Mesh 通常是通過一組

輕量級網絡代理

(Sidecar proxy),與應用程式代碼部署在一起來實作,且

對應用程式透明

1.6 第二代 Service Mesh

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

控制台對每一個代理執行個體了如指掌,通過控制台可以實作代理的通路控制和度量名額收集, 提升了服務網格的可觀測性和管控能力, Istio 正是這類系統最為突出的代表.

1.7 Service Mesh 産品簡史

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面
  • 2016 年 1 月 15 日,前 Twitter 的基礎設施工程師 William Morgan 和 Oliver Gould,在 GitHub 上釋出了 Linkerd 0.0.7 版本,采用Scala編寫, 他們同時組建了一個創業小公司 Buoyant,這是業界公認的第一個Service Mesh
  • 2016 年,Matt Klein在 Lyft 默默地進行 Envoy 的開發。Envoy 誕生的時間其實要比 Linkerd 更早一些,隻是在 Lyft 内部不為人所知
  • 2016 年 9 月 29 日在 SF Microservices 上,“Service Mesh”這個詞彙第一次在公開場合被使用。這标志着“Service Mesh”這個詞,從 Buoyant 公司走向社群.
  • 2016 年 9 月 13 日,Matt Klein 宣布 Envoy 在 GitHub 開源,直接釋出 1.0.0 版本。
  • 2016 年下半年,Linkerd 陸續釋出了 0.8 和 0.9 版本,開始支援 HTTP/2 和 gRPC,1.0 釋出在即;同時,借助 Service Mesh 在社群的認可度,Linkerd 在年底開始申請加入 CNCF
  • 2017 年 1 月 23 日,Linkerd 加入 CNCF。
  • 2017 年 3 月 7 日,Linkerd 宣布完成千億次産品請求
  • 2017 年 4 月 25 日,Linkerd 1.0 版本釋出
  • 2017 年 7 月 11 日,Linkerd 釋出版本 1.1.1,宣布和 Istio 項目內建
  • 2017 年 9 月, nginx突然宣布要搞出一個Servicemesh來, Nginmesh: github.com/nginxinc/ng…, 可以作為istio的資料面, 不過這個項目目前處于不活躍開發(This project is no longer under active development)
  • 2017 年 12 月 5 日,Conduit 0.1.0 版本釋出

Envoy 和 Linkerd 都是在資料面上的實作, 屬于同一個層面的競争, 是用 C++ 語言實作的,在性能和資源消耗上要比采用 Scala 語言實作的 Linkerd 小,這一點對于延遲敏感型和資源敏的服務尤為重要.

Envoy 對 作為 Istio 的标準資料面實作, 其最主要的貢獻是提供了一套标準資料面API, 将服務資訊和流量規則下發到資料面的sidecar中, 另外Envoy還支援熱重新開機. Istio早期采用了Envoy v1 API,目前的版本中則使用V2 API,V1已被廢棄.

通過采用該标準API,Istio将控制面和資料面進行了解耦,為多種資料面sidecar實作提供了可能性。事實上基于該标準API已經實作了多種Sidecar代理和Istio的內建,除Istio目前內建的Envoy外,還可以和Linkerd, Nginmesh等第三方通信代理進行內建,也可以基于該API自己編寫Sidecar實作.

将控制面和資料面解耦是Istio後來居上,風頭超過Service mesh鼻祖Linkerd的一招妙棋。Istio站在了控制面的高度上,而Linkerd則成為了可選的一種sidecar實作.

Conduit 的整體架構和 Istio 一緻,借鑒了 Istio 資料平面 + 控制平面的設計,而且選擇了 Rust 程式設計語言來實作資料平面,以達成 Conduit 宣稱的更輕、更快和超低資源占用.

1.8 似曾相識的競争格局

Kubernetes Istio
領域 容器編排 服務網格
主要競品 Swarm, Mesos Linkerd, Conduit
主要盟友 RedHat, CoreOS IBM, Lyft
主要競争對手 Docker 公司 Buoyant 公司
标準化 OCI: runtime spec, image spec XDS
插件化 CNI, CRI Istio CNI, Mixer Adapter
結果 Kubernetes 成為容器編排事實标準 ?

google 主導的Kubernetes 在容器編排領域取得了完勝, 目前在服務網格領域的打法如出一轍, 社群對Istio前景也比較看好.

Istio CNI 計劃在1.1 作為實驗特性, 使用者可以通過擴充方式定制sidecar的網絡.

1.9 國内Service Mesh 發展情況

  • 螞蟻金服開源SOFAMesh:
    • github.com/alipay/sofa…
    • 從istio fork
    • 使用Golang語言開發全新的Sidecar,替代Envoy
    • 為了避免Mixer帶來的性能瓶頸,合并Mixer部分功能進入Sidecar
    • Pilot和Citadel子產品進行了大幅的擴充和增強
    • 擴充RPC協定: SOFARPC/HSF/Dubbo
  • 華為:
    • go-chassis: github.com/go-chassis/… golang 微服務架構, 支援istio平台
    • mesher: github.com/go-mesh/mes… mesh 資料面解決方案
    • 國内首家提供Service Mesh公共服務的雲廠商
    • 目前(2019年1月)公有雲Istio 産品線上已經支援申請公測, 産品形态比較完善
  • 騰訊雲 TSF:
    • 基于 Istio、envoy 進行改造
    • 支援 Kubernetes、虛拟機以及裸金屬的服務
    • 對 Istio 的能力進行了擴充和增強, 對 Consul 的完整适配
    • 對于其他二進制協定進行擴充支援
  • 唯品會
    • OSP (Open Service Platform)
  • 新浪:
    • Motan: 是一套基于java開發的RPC架構, Weibo Mesh 是基于Motan

2. Istio: 第二代 Service Mesh

Istio來自希臘語,英文意思是「sail」, 意為「啟航」

  • 2.1 Istio 架構
  • 2.2 核心功能
  • 2.3 Istio 示範: BookInfo

2.1 Istio 架構

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Istio Architecture(圖檔來自Isio官網文檔)

  • 資料面
    • Sidecar
  • 控制面
    • Pilot:服務發現、流量管理
    • Mixer:通路控制、遙測
    • Citadel:終端使用者認證、流量加密

2.2 核心功能

  • 流量管理
  • 安全
  • 可觀察性
  • 多平台支援
  • 內建和定制

下面是我對Istio架構總結的思維導圖:

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

2.3 Istio 示範: BookInfo

以下是Istio官網經典的 BookInfo Demo, 這是一個多語言組成的異構微服務系統:

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Bookinfo Application(圖檔來自Isio官網文檔)

下面我将現場給大家進行示範, 從demo安裝開始, 并體驗一下istio的流控功能:

使用helm管理istio

下載下傳istio release: istio.io/docs/setup/…

安裝istio:

注意事項, 若要開啟sidecar自動注入功能, 需要:

  • 確定 kube-apiserver 啟動參數 開啟了ValidatingAdmissionWebhook 和 MutatingAdmissionWebhook
  • 給namespace 增加 label:

    kubectl label namespace default istio-injection=enabled

  • 同時還要保證 kube-apiserver 的 aggregator layer 開啟:

    --enable-aggregator-routing=true

    且證書和api server連通性正确設定.
如需解除安裝istio:

更多安裝選擇請參考: istio.io/docs/setup/…

安裝Bookinfo Demo:

Bookinfo 是一個多語言異構的微服務demo, 其中 productpage 微服務會調用 details 和 reviews 兩個微服務, reviews 會調用ratings 微服務, reviews 微服務有 3 個版本. 關于此項目更多細節請參考: istio.io/docs/exampl…

部署應用:

這将建立 productpage, details, ratings, reviews 對應的deployments 和 service, 其中reviews 有三個deployments, 代表三個不同的版本.

對入口流量進行配置:

該操作會建立bookinfo-gateway 的Gateway, 并将流量發送到productpage服務

此時通過bookinfo-gateway 對應的LB或者nodeport 通路/productpage 頁面, 可以看到三個版本的reviews服務在随機切換

基于權重的路由

通過CRD DestinationRule建立3 個reviews 子版本:

通過CRD VirtualService 調整個 reviews 服務子版本的流量比例, 設定 v1 和 v3 各占 50%

重新整理頁面, 可以看到無法再看到reviews v2的内容, 頁面在v1和v3之間切換.

基于内容路由

修改reviews CRD, 将jason 登入的使用者版本路由到v2, 其他使用者路由到版本v3.

重新整理頁面, 使用jason登入的使用者, 将看到v2 黑色星星版本, 其他使用者将看到v3 紅色星星版本.

更多BookInfo 示例, 請參閱: istio.io/docs/exampl…, 若要删除應用: 執行腳本

./samples/bookinfo/platform/kube/cleanup.sh

3. Istio 資料面

  • 3.1 資料面元件
  • 3.2 sidecar 流量劫持原理
  • 3.3 資料面标準API: xDS
  • 3.4 分布式跟蹤

3.1 資料面元件

Istio 注入sidecar實作:

  • 自動注入: 利用 Kubernetes Dynamic Admission Webhooks 對 建立的pod 進行注入: init container + sidecar
  • 手動注入: 使用

    istioctl kube-inject

注入Pod内容:

  • istio-init: 通過配置iptables來劫持Pod中的流量
  • istio-proxy: 兩個程序pilot-agent和envoy, pilot-agent 進行初始化并啟動envoy

Sidecar 自動注入實作

Istio 利用 Kubernetes Dynamic Admission Webhooks 對pod 進行sidecar注入

檢視istio 對這2個Webhooks 的配置 ValidatingWebhookConfiguration 和 MutatingWebhookConfiguration:

可以看出:

  • 命名空間

    istio-system

    中的服務

    istio-galley

    , 通過路由

    /admitpilot

    , 處理config.istio.io部分, rbac.istio.io, authentication.istio.io, networking.istio.io等資源的Validating 工作
  • 命名空間istio-system 中的服務

    istio-galley

    , 通過路由

    /admitmixer

    , 處理其他config.istio.io資源的Validating 工作
  • 命名空間istio-system 中的服務

    istio-sidecar-injector

    , 通過路由

    /inject

    , 處理其他

    v1/pods

    的CREATE, 同時需要滿足命名空間

    istio-injection: enabled

istio-init

資料面的每個Pod會被注入一個名為

istio-init

的initContainer, initContrainer是K8S提供的機制,用于在Pod中執行一些初始化任務.在Initialcontainer執行完畢并退出後,才會啟動Pod中的其它container.

istio-init ENTRYPOINT 和 args 組合的啟動指令:

istio-iptables.sh 源碼位址為 github.com/istio/istio…

istio-init 通過配置iptable來劫持Pod中的流量:

  • 參數

    -p 15001

    : Pod中的資料流量被iptable攔截,并發向15001端口, 該端口将由 envoy 監聽
  • 參數

    -u 1337

    : 用于排除使用者ID為1337,即Envoy自身的流量,以避免Iptable把Envoy發出的資料又重定向到Envoy, UID 為 1337,即 Envoy 所處的使用者空間,這也是 istio-proxy 容器預設使用的使用者, 見Sidecar

    istio-proxy

    配置參數

    securityContext.runAsUser

  • 參數

    -b 9080

    -d ""

    : 入站端口控制, 将所有通路 9080 端口(即應用容器的端口)的流量重定向到 Envoy 代理
  • 參數

    -i '*'

    -x ""

    : 出站IP控制, 将所有出站流量都重定向到 Envoy 代理

Init 容器初始化完畢後就會自動終止,但是 Init 容器初始化結果(iptables)會保留到應用容器和 Sidecar 容器中.

istio-proxy

istio-proxy 以 sidecar 的形式注入到應用容器所在的pod中, 簡化的注入yaml:

istio-proxy容器中有兩個程序pilot-agent和envoy:

可以看到:

  • /usr/local/bin/pilot-agent

    /usr/local/bin/envoy

    的父程序, Pilot-agent程序根據啟動參數和K8S API Server中的配置資訊生成Envoy的初始配置檔案(

    /etc/istio/proxy/envoy-rev0.json

    ),并負責啟動Envoy程序
  • pilot-agent 的啟動參數裡包括: discoveryAddress(pilot服務位址), Envoy 二進制檔案的位置, 服務叢集名, 監控名額上報位址, Envoy 的管理端口, 熱重新開機時間等

Envoy配置初始化流程:

  1. Pilot-agent根據啟動參數和K8S API Server中的配置資訊生成Envoy的初始配置檔案envoy-rev0.json,該檔案告訴Envoy從xDS server中擷取動态配置資訊,并配置了xDS server的位址資訊,即控制面的Pilot
  2. Pilot-agent使用envoy-rev0.json啟動Envoy程序
  3. Envoy根據初始配置獲得Pilot位址,采用xDS接口從Pilot擷取到Listener,Cluster,Route等d動态配置資訊
  4. Envoy根據擷取到的動态配置啟動Listener,并根據Listener的配置,結合Route和Cluster對攔截到的流量進行處理

檢視envoy 初始配置檔案:

3.2 sidecar 流量劫持原理

sidecar 既要作為服務消費者端的正向代理,又要作為服務提供者端的反向代理, 具體攔截過程如下:

  • Pod 所在的network namespace内, 除了envoy發出的流量外, iptables規則會對進入和發出的流量都進行攔截,通過nat redirect重定向到Envoy監聽的15001端口.
  • envoy 會根據從Pilot拿到的 XDS 規則, 對流量進行轉發.
  • envoy 的 listener 0.0.0.0:15001 接收進出 Pod 的所有流量,然後将請求移交給對應的virtual listener
  • 對于本pod的服務, 有一個http listener

    podIP+端口

    接受inbound 流量
  • 每個service+非http端口, 監聽器配對的 Outbound 非 HTTP 流量
  • 每個service+http端口, 有一個http listener:

    0.0.0.0+端口

    接受outbound流量

整個攔截轉發過程對業務容器是透明的, 業務容器仍然使用 Service 域名和端口進行通信, service 域名仍然會轉換為service IP, 但service IP 在sidecar 中會被直接轉換為 pod IP, 從容器中出去的流量已經使用了pod IP會直接轉發到對應的Pod, 對比傳統kubernetes 服務機制, service IP 轉換為Pod IP 在node上進行, 由 kube-proxy維護的iptables實作.

3.3 資料面标準API: xDS

xDS是一類發現服務的總稱,包含LDS,RDS,CDS,EDS以及 SDS。Envoy通過xDS API可以動态擷取Listener(監聽器), Route(路由),Cluster(叢集),Endpoint(叢集成員)以 及Secret(證書)配置

xDS API 涉及的概念:

  • Host
  • Downstream
  • Upstream
  • Listener
  • Cluster

Envoy 配置熱更新: 配置的動态變更,而不需要重新開機 Envoy:

  1. 新老程序采用基本的RPC協定使用Unix Domain Socket通訊.
  2. 新程序啟動并完成所有初始化工作後,向老程序請求監聽套接字的副本.
  3. 新程序接管套接字後,通知老程序關閉套接字.
  4. 通知老程序終止自己.

xDS 調試

Pilot在9093端口提供了下述調試接口:

Sidecar Envoy 也提供了管理接口,預設為localhost的15000端口,可以擷取listener,cluster以及完整的配置資料

可以通過以下指令檢視支援的調試接口:

或者forward到本地就行調試

相關的調試接口:

使用istioctl 檢視代理配置:

xDS 類型包括: listener, route, cluster, endpoint

對xDS 進行分析: productpage 通路 reviews 服務

檢視 product 的所有listener:

envoy 流量入口的listener:

以下是reviews的所有pod IP

對于目的位址是以上ip的http通路, 這些 ip 并沒有對應的listener, 是以會通過端口9080 比對到listener

0.0.0.0 9080

檢視listener

0.0.0.0 9080

:

檢視名為

9080

的 route:

可以看到, 在9080 這個route 中, 包含所有這個端口的http 路由資訊, 通過virtualHosts清單進行服務域名分發到各個cluster.

檢視virtualHosts

reviews.default.svc.cluster.local:9080

中的routes資訊, 可以看到jason 路由到了cluster

outbound|9080|v2|reviews.default.svc.cluster.local

檢視該cluster:

檢視其對應的endpoint:

該endpoint 即為 reviews 服務 V2 對應的 pod IP

XDS服務接口的最終一緻性考慮

遵循 make before break 模型

3.4 分布式跟蹤

以下是分布式全鍊路跟蹤示意圖:

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

一個典型的Trace案例(圖檔來自opentracing文檔中文版)

Jaeger 是Uber 開源的全鍊路跟蹤系統, 符合OpenTracing協定, OpenTracing 和 Jaeger 均是CNCF 成員項目, 以下是Jaeger 架構的示意圖:

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Jaeger 架構示意圖(圖檔來自Jaeger官方文檔)

分布式跟蹤系統讓開發者能夠得到可視化的調用流程展示。這對複雜的微服務系統進行問題排查和性能優化時至關重要.

Envoy 原生支援http 鍊路跟蹤:

  • 生成 Request ID:Envoy 會在需要的時候生成 UUID,并操作名為 [x-request-id] 的 HTTP Header。應用可以轉發這個 Header 用于統一的記錄和跟蹤.
  • 支援內建外部跟蹤服務:Envoy 支援可插接的外部跟蹤可視化服務。目前支援有:
    • LightStep
    • Zipkin 或者 Zipkin 相容的後端(比如說 Jaeger)
    • Datadog
  • 用戶端跟蹤 ID 連接配接:x-client-trace-id Header 可以用來把不信任的請求 ID 連接配接到受信的 x-request-id Header 上

跟蹤上下文資訊的傳播

  • 不管使用的是哪個跟蹤服務,都應該傳播 x-request-id,這樣在被調用服務中啟動相關性的記錄
  • 如果使用的是 Zipkin,Envoy 要傳播的是 B3 Header。(x-b3-traceid, x-b3-spanid, x-b3-parentspanid, x-b3-sampled, 以及 x-b3-flags. x-b3-sampled)
  • 上下文跟蹤并非零修改, 在調用下遊服務時, 上遊應用應該自行傳播跟蹤相關的 HTTP Header

4. Istio 控制面

  • 4.1 Pilot 架構
  • 4.2 流量管理模型
  • 4.3 故障處理
  • 4.4 Mixer 架構
  • 4.5 Mixer擴充卡模型
  • 4.6 Mixer 緩存機制

4.1 Pilot 架構

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Pilot Architecture(圖檔來自Isio官網文檔)

  • Rules API: 對外封裝統一的 API,供服務的開發者或者運維人員調用,可以用于流量控制。
  • Envoy API: 對内封裝統一的 API,供 Envoy 調用以擷取注冊資訊、流量控制資訊等。
  • 抽象模型層: 對服務的注冊資訊、流量控制規則等進行抽象,使其描述與平台無關。
  • 平台适配層: 用于适配各個平台如 Kubernetes、Mesos、Cloud Foundry 等,把平台特定的注冊資訊、資源資訊等轉換成抽象模型層定義的平台無關的描述。例如,Pilot 中的 Kubernetes 擴充卡實作必要的控制器來 watch Kubernetes API server 中 pod 注冊資訊、ingress 資源以及用于存儲流量管理規則的第三方資源的更改

4.2 流量管理模型

  • VirtualService
  • DestinationRule
  • ServiceEntry
  • Gateway

VirtualService

VirtualService 中定義了一系列針對指定服務的流量路由規則。每個路由規則都是針對特定協定的比對規則。如果流量符合這些特征,就會根據規則發送到服務系統資料庫中的目标服務, 或者目标服務的子集或版本, 比對規則中還包含了對流量發起方的定義,這樣一來,規則還可以針對特定客戶上下文進行定制.

Gateway

Gateway 描述了一個負載均衡器,用于承載網格邊緣的進入和發出連接配接。這一規範中描述了一系列開放端口,以及這些端口所使用的協定、負載均衡的 SNI 配置等内容

ServiceEntry

Istio 服務網格内部會維護一個與平台無關的使用通用模型表示的服務系統資料庫,當你的服務網格需要通路外部服務的時候,就需要使用 ServiceEntry 來添加服務注冊, 這類服務可能是網格外的 API,或者是處于網格内部但卻不存在于平台的服務系統資料庫中的條目(例如需要和 Kubernetes 服務溝通的一組虛拟機服務).

EnvoyFilter

EnvoyFilter 描述了針對代理服務的過濾器,用來定制由 Istio Pilot 生成的代理配置.

Kubernetes Ingress vs Istio Gateway

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面
  • 合并了L4-6和L7的規範, 對傳統技術棧使用者的應用遷入不友善
  • 表現力不足:
    • 隻能對 service、port、HTTP 路徑等有限字段比對來路由流量
    • 端口隻支援預設80/443

Istio Gateway:·

  • 定義了四層到六層的負載均衡屬性 (通常是SecOps或NetOps關注的内容)
    • 端口
    • 端口所使用的協定(HTTP, HTTPS, GRPC, HTTP2, MONGO, TCP, TLS)
    • Hosts
    • TLS SNI header 路由支援
    • TLS 配置支援(http 自動301, 證書等)
    • ip / unix domain socket

Kubernetes, Istio, Envoy xDS 模型對比

以下是對Kubernetes, Istio, Envoy xDS 模型的不嚴格對比

Kubernetes Istio Envoy xDS
入口流量 Ingress GateWay Listener
服務定義 Service - Cluster+Listener
外部服務定義 - ServiceEntry Cluster+Listener
版本定義 - DestinationRule Cluster+Listener
版本路由 - VirtualService Route
執行個體 Endpoint - Endpoint

Kubernetes 和 Istio 服務尋址的差別:

Kubernetes

:

  1. kube-dns: service domain -> service ip
  2. kube-proxy(node iptables): service ip -> pod ip
Istio

:

  1. kube-dns: service domain -> service ip
  2. sidecar envoy: service ip -> pod ip

4.3 故障處理

随着微服務的拆分粒度增強, 服務調用會增多, 更複雜, 扇入 扇出, 調用失敗的風險增加, 以下是常見的服務容錯處理方式:

控制端 目的 實作 Istio
逾時 client 保護client 請求等待逾時/請求運作逾時 timeout
重試 client 容忍server臨時錯誤, 保證業務整體可用性 重試次數/重試的逾時時間 retries.attempts, retries.perTryTimeout
熔斷 client 降低性能差的服務或執行個體的影響 通常會結合逾時+重試, 動态進行服務狀态決策(Open/Closed/Half-Open) trafficPolicy.outlierDetection
降級 client 保證業務主要功能可用 主邏輯失敗采用備用邏輯的過程(鏡像服務分級, 調用備用服務, 或者傳回mock資料) 暫不支援, 需要業務代碼按需實作
隔離 client 防止異常server占用過多client資源 隔離對不同服務調用的資源依賴: 線程池隔離/信号量隔離 暫不支援
幂等 server 容忍client重試, 保證資料一緻性 唯一ID/加鎖/事務等手段 暫不支援, 需要業務代碼按需實作
限流 server 保護server 常用算法: 計數器, 漏桶, 令牌桶 trafficPolicy.connectionPool

Istio 沒有無降級處理支援: Istio可以提高網格中服務的可靠性和可用性。但是,應用程式仍然需要處理故障(錯誤)并采取适當的回退操作。例如,當負載均衡池中的所有執行個體都失敗時,Envoy 将傳回 HTTP 503。應用程式有責任實作必要的邏輯,對這種來自上遊服務的 HTTP 503 錯誤做出合适的響應。

4.4 Mixer 架構

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

Mixer Topology(圖檔來自Isio官網文檔)

Istio 的四大功能點連接配接, 安全, 控制, 觀察, 其中「控制」和「觀察」的功能主要都是由Mixer元件來提供, Mixer 在Istio中角色:

  • 功能上: 負責政策控制和遙測收集
  • 架構上:提供插件模型,可以擴充和定制

4.5 Mixer Adapter 模型

  • Attribute
  • Template
  • Adapter
  • Instance
  • Handler
  • Rule

Attribute

Attribute 是政策和遙測功能中有關請求和環境的基本資料, 是用于描述特定服務請求或請求環境的屬性的一小段資料。例如,屬性可以指定特定請求的大小、操作的響應代碼、請求來自的 IP 位址等.

  • Istio 中的主要屬性生産者是 Envoy,但專用的 Mixer 擴充卡也可以生成屬性
  • 屬性詞彙表見: Attribute Vocabulary
  • 資料流向: envoy -> mixer

Template

Template 是對 adapter 的資料格式和處理接口的抽象, Template定義了:

  • 當處理請求時發送給adapter 的資料格式
  • adapter 必須實作的gRPC service 接口

每個Template 通過

template.proto

進行定義:

  • 名為

    Template

    的一個message
  • Name: 通過template所在的package name自動生成
  • template_variety: 可選Check, Report, Quota or AttributeGenerator, 決定了adapter必須實作的方法. 同時決定了在mixer的什麼階段要生成template對應的instance:
    • Check: 在Mixer’s Check API call時建立并發送instance
    • Report: 在Mixer’s Report API call時建立并發送instance
    • Quota: 在Mixer’s Check API call時建立并發送instance(查詢配額時)
    • AttributeGenerator: for both Check, Report Mixer API calls

Istio 内置的Templates: istio.io/docs/refere…

Adapter

封裝了 Mixer 和特定外部基礎設施後端進行互動的必要接口,例如 Prometheus 或者 Stackdriver

  • 定義了需要處理的模闆(在yaml中配置template)
  • 定義了處理某個Template資料格式的GRPC接口
  • 定義 Adapter需要的配置格式(Params)
  • 可以同時處理多個資料(instance)

Istio 内置的Adapter: istio.io/docs/refere…

Instance

代表符合某個Template定義的資料格式的具體實作, 該具體實作由使用者配置的 CRD, CRD 定義了将Attributes 轉換為具體instance 的規則, 支援屬性表達式

  • Instance CRD 是Template 中定義的資料格式 + 屬性轉換器
  • 内置的Instance 類型(其實就是内置 Template): Templates
  • 屬性表達式見: Expression Language
  • 資料流向: mixer -> adapter 執行個體

Handler

使用者配置的 CRD, 為具體Adapter提供一個具體配置, 對應Adapter的可運作執行個體

Rule

使用者配置的 CRD, 配置一組規則,這些規則描述了何時調用特定(通過Handler對應的)擴充卡及哪些Instance

結語

計算機科學中的所有問題,都可以用另一個層來解決,除了層數太多的問題

Kubernetes 本身已經很複雜, Istio 為了更高層控制的抽象, 又增加了很多概念. 複雜度堪比kubernetes.

可以看出istio 設計精良, 在處理微服務的複雜場景有很多優秀之處, 不過目前istio目前的短闆還是很明顯, 高度的抽象帶來了很多性能的損耗, 社群現在也有很多優化的方向, 像螞蟻金服開源的SofaMesh 主要是去精簡層, 試圖在sidecar裡去做很多mixer 的事情, 減少sidecar和mixer的同步請求依賴, 而一些其他的sidecar 網絡方案, 更多的是考慮去優化層, 優化sidecar 這一層的性能開銷.

在Istio 1.0 之前, 主要還是以功能的實作為主, 不過後面随着社群的積極投入, 相信Istio的性能會有長足的提升.

筆者之前從事過多年的服務治理相關的工作, 過程中切身體會到微服務治理的痛點, 是以也比較關注 service mesh的發展, 個人對istio也非常看好, 剛好今年我們中心容器産品今年也有這方面的計劃, 期待我們能在這個方向進行一些産品和技術的深耕.

騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

參考資料:

  • Service Mesh年度總結:群雄逐鹿烽煙起
  • Why You Should Care About Istio Gateways
  • Pattern: Service Mesh
  • Mixer Out Of Process Adapter Dev Guide
  • Mixer Out of Process Adapter Walkthrough
  • Envoy 中的 xDS REST 和 gRPC 協定詳解
  • Delayering Istio with AppSwitch
  • servicemesher 中文社群
騰訊雲容器團隊内部Istio專題分享騰訊雲容器團隊内部Istio專題分享1. Service Mesh: 下一代微服務2. Istio: 第二代 Service Mesh3. Istio 資料面4. Istio 控制面

繼續閱讀