ISTIO文檔解讀學習(三)

                                      Istio安全

將單一應用程序分解爲微服務可提供各種好處,包括更好的靈活性、可伸縮性以及服務複用的能力。但是,微服務也有特殊的安全需求:1)爲了抵禦中間人攻擊,需要流量加密。2)爲了提供靈活的服務訪問控制,需要雙向 TLS 和細粒度的訪問策略。3)要審覈誰在什麼時候做了什麼,需要審計工具。istio安全整體概述

 

Istio 中的安全性涉及多個組件:1)Citadel 用於密鑰和證書管理。2)Sidecar 和周邊代理 實現客戶端和服務器之間的安全通信。3)Pilot 將授權策咯和安全信息發給代理。4)Mixer 管理授權和審計

上圖Istio 安全架構。在服務間通信開始時,雙方必須與其身份信息交換憑證以用於相互認證目的。在客戶端,根據安全信息檢查服務器的標識,以查看它是否是該服務的授權運行程序。在服務器端,服務器可以根據授權策略確定客戶端可以訪問哪些信息,審覈誰在什麼時間訪問了什麼,根據服務向客戶收費並拒絕任何未能支付賬單的客戶訪問服務。Istio 身份模型中,Istio 可以使用可以對服務實例進行分組的其他身份,例如服務名稱。不同平臺上的 Istio 服務標識:1)Kubernetes: Kubernetes 服務帳戶。2)GKE/GCE: 可以使用 GCP 服務帳戶。3)GCP: GCP 服務帳戶。4)AWS: AWS IAM 用戶/角色帳戶。5)本地(非 Kubernetes): 用戶帳戶、自定義服務帳戶、服務名稱、Istio 服務帳戶或 GCP 服務帳戶。自定義服務帳戶引用現有服務帳戶,就像客戶的身份目錄管理的身份一樣。

SPIFFE:一種標準,提供了一個框架規範,該框架能夠跨異構環境引導和向服務發佈身份。Istio 安全性和 SPIRE(是 SPIFFE 的實現)在 PKI 實現細節上有所不同。Istio 提供更全面的安全解決方案,包括身份驗證、授權和審計。PKI:Istio PKI 建立在 Istio Citadel 之上,可爲每個工作負載安全地提供強大的工作負載標識。Istio 使用 X.509 證書來攜帶 SPIFFE 格式的身份。PKI 還可用於大規模自動化密鑰和證書輪換。Istio 支持在 Kubernetes pod 和本地計算機上運行的服務。目前每個方案使用不同的證書密鑰配置機制。Kubernetes 方案: 1) Citadel 監視 Kubernetes apiserver,爲每個現有和新的服務帳戶創建 SPIFFE 證書和密鑰對。Citadel 將證書和密鑰對存儲爲Kubernetes secret。2) 創建 pod 時,Kubernetes 會根據其服務帳戶通過Kubernetes secret volume 將證書和密鑰對掛載到 pod 上。3) Citadel 監視每個證書的生命週期,並通過重寫 Kubernetes secret 自動輪換證書。4) Pilot 生成安全命名信息,該信息定義了哪些 Service Account 可以運行哪些服務。Pilot 然後將安全命名信息傳遞給 envoy sidecar。

認證: Istio 提供兩種類型的身份驗證:傳輸身份驗證,也稱爲服務間身份驗證:驗證建立連接的直接客戶端。 Istio 提供雙向TLS作爲傳輸身份驗證的完整堆棧解決方案。 無需更改服務代碼即可打開此功能。這個解決方案:1)爲每個服務提供強大的身份,表示其角色,以實現跨羣集和雲的互操作性。2)保護服務到服務通信和最終用戶到服務的通信。3)提供密鑰管理系統,以自動執行密鑰和證書生成,分發和輪換。來源身份認證,也稱爲最終用戶身份驗證:驗證作爲最終用戶或設備發出請求的原始客戶端。Istio 通過 JSON Web Token(JWT)驗證和 ORY HydraKeycloakAuth0Firebase AuthGoogle Auth 和自定義身份驗證來簡化開發人員體驗,並且輕鬆實現請求級別的身份驗證。在這兩種情況下Istio都通過自定義 K8s API 將身份認證策略存儲在 Istio 配置存儲中。Pilot 會在適當的時候爲每個代理保持最新狀態以及密鑰。此外Istio 支持在寬容模式(permissive mode)下進行身份驗證,幫助瞭解策略更改在其生效之前如何影響安全狀態。雙向 TLS 認證:Istio 隧道通過客戶端和服務器端進行服務間(service-to-service)通信Envoy代理。爲了使客戶端通過雙向 TLS 調用服務端,遵循以下步驟:1、Istio 將出站流量從客戶端重新路由到客戶端的本地 sidecar Envoy。2、客戶端 Envoy 與服務器端 Envoy 開始雙向 TLS 握手。在握手期間,客戶端 Envoy 還做了安全命名檢查,以驗證服務器證書中顯示的服務帳戶是否被授權運行到目標服務。3、客戶端 Envoy 和服務器端 Envoy 建立了一個雙向的 TLS 連接,Istio 將流量從客戶端 Envoy 轉發到服務器端 Envoy。4、授權後,服務器端 Envoy 通過本地 TCP 連接將流量轉發到服務器服務。寬容模式:Istio 雙向 TLS 具有一個寬容模式(permissive mode),允許 service 同時接受純文本流量和雙向 TLS 流量。這個功能極大的提升了雙向 TLS 的入門體驗。安全命名:安全命名信息包含從編碼在證書中的服務器標識到被發現服務或 DNS 引用的服務名稱的 N-到-N 映射。從身份 A 到服務名稱 B 的映射意味着“允許 A 並授權其運行服務 B。Pilot 監視 Kubernetes apiserver,生成安全的命名信息,並將其安全地分發給 sidecar Envoy。

認證架構:網格操作者使用 .yaml 文件來指定策略。部署後策略將保存在 Istio 配置存儲中。Pilot、Istio 控制器監視配置存儲。一有任何的策略變更,Pilot 會將新策略轉換爲適當的配置,告知 Envoy sidecar 代理如何執行所需的身份驗證機制。Pilot 可以獲取公鑰並將其附加到 JWT 驗證配置。或者Pilot 提供 Istio 系統管理的密鑰和證書的路徑,並將它們掛載到應用程序 pod 以進行雙向 TLS。Istio 異步發送配置到目標端點。代理收到配置後新的身份驗證要求會立即生效。發送請求的客戶端服務負責遵循必要的身份驗證機制。對於源身份驗證(JWT),應用程序負責獲取 JWT 憑據並將其附加到請求。對於雙向 TLS,Istio 提供目標規則。可以使用目標規則來指示客戶端代理使用 TLS 與服務器端預期的證書進行初始連接。

 

Istio 將兩種類型的身份驗證以及憑證中的其他聲明(如果適用)輸出到下一層:授權。此外可以指定將傳輸或原始身份驗證中的哪個身份作爲委託人使用。認證策略:認證策略是對服務收到的請求生效的,要在雙向 TLS 中指定客戶端認證策略,需要在 DetinationRule 中設置 TLSSettings。和其他的 Istio 配置一樣,可以用 .yaml 文件的形式來編寫認證策略,然後使用部署。策略存儲範圍:Istio 可以在命名空間範圍或網絡範圍存儲中存儲身份認證策略,命名空間範圍存儲中的策略只能影響同一命名空間中的服務。網格範圍內的策略可以影響網格中的所有服務。爲防止衝突和濫用,只能在網格範圍存儲中定義一個策略。該策略必須命名爲 default 並且有一個空的 targets: 部分。傳輸認證peers: 部分定義了策略中傳輸身份驗證支持的身份驗證方法和相關參數。該部分可以列出多個方法,並且只有一個方法必須滿足認證才能通過。但是從 Istio 0.7 版本開始,當前支持的唯一傳輸身份驗證方法是雙向 TLS。默認的雙向 TLS 模式爲 STRICT。因此,mode: STRICT 等效於以下內容:- mtls:{}、- mtls: 、- mtls: null三種效果一樣。如果不指定雙向 TLS 模式,則對等方無法使用 Transport 身份驗證,並且 Istio 拒絕綁定到 Sidecar 的雙向 TLS 連接。在應用程序層,服務仍可以處理它們自己的雙向 TLS 會話。來源身份認證:部署文件origins: 部分定義了原始身份驗證支持的身份驗證方法和相關參數。Istio 僅支持 JWT 原始身份驗證。但是策略可以列出不同發行者的多個 JWT。與傳輸身份驗證類似,要想通過身份驗證必須通過其中的一個。

授權:Istio 的授權功能爲 Istio 網格中的工作負載提供網格級別、命名空間級別和工作負載級別的訪問控制。它提供了:1)工作負載間和最終用戶到工作負載的授權。2)一個簡單的 API,它包括一個單獨的並且很容易使用和維護的AuthorizationPlicy CRD。3)靈活的語義,運維人員可以在 Istio 屬性上自定義條件。4)高性能,因爲 Istio 授權是在 Envoy 本地強制執行的。5)高兼容性,原生支持 HTTP、HTTPS 和 HTTP2,以及任意普通 TCP 協議。istio授權架構如下

 

每個 Envoy 代理都運行一個授權引擎,該引擎在運行時授權請求。當請求到達代理時,授權引擎根據當前授權策略評估請求上下文,並返回授權結果 ALLOWDENY。無需顯式啓用 Istio 的授權功能,只需在工作負載上應用 AuthorizationPolicy 即可實現訪問控制。如果沒有對工作負載應用 AuthorizationPolicy,則不會執行訪問控制,也就是說,將允許所有請求。如果有任何 AuthorizationPolicy 應用到工作負載,則默認情況下將拒絕對該工作負載的訪問,除非策略中聲明的規則明確允許了。目前,AuthorizationPolicy 僅支持 ALLOW 動作。 這意味着,如果將多個授權策略應用於同一工作負載,它們的效果是累加的。授權策略:要配置 Istio 授權策略,請創建一個 AuthorizationPolicy(AP) 資源。授權策略包括選擇器和規則列表。 選擇器指定策略所適用的目標,而規則指定什麼條件下允許什麼。 具體來說:目標AP裏的 selector 部分, from 部分來源列表。什麼 rule 中的 to 部分,操作列表。條件  rule 中的 when 部分。自定義條件列表。策略目標:策略範圍(目標)由 metadata/namespace 和可選的 selector 確定。metadata/namespace 告訴該策略適用於哪個命名空間。如果設置爲根命名空間,則該策略將應用於網格中的所有命名空間。根命名空間的值是可配置的,默認值爲 istio-system。 如果設置爲普通命名空間,則該策略將僅適用於指定的命名空間。工作負載 selector 可用於進一步限制策略的應用範圍。 selector 使用 pod 標籤來選擇目標工作負載。 工作負載選擇器包含 {key: value} 對的列表,其中 key 是標籤的名稱。 如果未設置,則授權策略將應用於與授權策略相同的命名空間中的所有工作負載。值匹配:大部分字段都支持完全匹配、前綴匹配、後綴匹配和存在匹配,但有一些例外情況(例如,when 部分下的key 字段,source 部分下的 ipBlocksto 部分下的 ports 字段僅支持完全匹配)。

在普通 TCP 協議上使用 Istio 授權:Istio 授權支持工作負載使用任意普通 TCP 協議,如 MongoDB。 在這種情況下,可以按照與 HTTP 工作負載相同的方式配置授權策略。 不同之處在於某些字段和條件僅適用於 HTTP 工作負載。 這些字段包括:1)授權策略對象 source 部分中的 request_principals 字段。2)授權策略對象 operation 部分中的 hostsmethodspaths 字段,如下列出了支持的條件。

名稱 描述 支持的協議 示例
request.headers HTTP 請求頭,需要用 [] 括起來 HTTP only key: request.headers[User-Agent]
values: ["Mozilla/*"]
source.ip IP 地址,支持單個 IPCIDR HTTP and TCP key: source.ip
values: ["10.1.2.3"]
source.namespace 源負載實例命名空間,需啓用雙向 TLS HTTP and TCP key: source.namespace
values: ["default"]
source.principal 源負載的標識,需啓用雙向 TLS HTTP and TCP key: source.principal
values: ["cluster.local/ns/default/sa/productpage"]
request.auth.principal 已認證過 principal 的請求。 HTTP only key: request.auth.principal
values: ["accounts.my-svc.com/104958560606"]
request.auth.audiences 此身份驗證信息的目標主體 HTTP only key: request.auth.audiences
values: ["my-svc.com"]
request.auth.presenter 證書的頒發者 HTTP only key: request.auth.presenter
values: ["123456789012.my-svc.com"]
request.auth.claims Claims 來源於 JWT。需要用 [] 括起來 HTTP only key: request.auth.claims[iss]
values: ["*@foo.com"]
destination.ip 目標 IP 地址,支持單個 IPCIDR HTTP and TCP key: destination.ip
values: ["10.1.2.3", "10.2.0.0/16"]
destination.port 目標 IP 地址上的端口,必須在 [0,65535] 範圍內 HTTP and TCP key: destination.port
values: ["80", "443"]
connection.sni 服務器名稱指示,需啓用雙向 TLS HTTP and TCP key: connection.sni
values: ["www.example.com"]
experimental.envoy.filters.* 用於過濾器的實驗性元數據匹配,包裝的值 [] 作爲列表匹配 HTTP and TCP key: experimental.envoy.filters.network.mysql_proxy[db.table]
values: ["[update]"]

對雙向 TLS 的依賴:Istio 使用雙向 TLS 將某些信息從客戶端安全地傳遞到服務器。在使用授權策略中的以下任何字段之前,必須先啓用雙向 TLS:1) source 部分下的 principals 字段,2)source部分下的 namespaces 字段。3)source.principal 自定義條件。4)source.namespace自定義條件。5)connection.sni自定義條件。如果不使用授權策略中的上述任何字段,則雙向 TLS 不是必須的。

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