日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Istio 中的授权策略详解

發(fā)布時間:2023/12/4 编程问答 59 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Istio 中的授权策略详解 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

本文節(jié)選自 ServiceMesher 社區(qū)出品的開源電子書《Istio Handbook——Istio 服務(wù)網(wǎng)格進階實踐》,閱讀地址:https://www.servicemesher.com/istio-handbook/

授權(quán)功能是 Istio 中安全體系的一個重要組成部分,它用來實現(xiàn)訪問控制的功能,即判斷一個請求是否允許通過,這個請求可以是從外部進入 Istio 內(nèi)部的請求,也可以是在 Istio 內(nèi)部從服務(wù) A 到服務(wù) B 的請求。可以把授權(quán)功能近似地認為是一種四層到七層的“防火墻”,它會像傳統(tǒng)防火墻一樣,對數(shù)據(jù)流進行分析和匹配,然后執(zhí)行相應(yīng)的動作。

本節(jié)所有概念和操作都基于 Istio 1.6 版本。

授權(quán)功能是通過授權(quán)策略 (AuthorizationPolicy) 來進行配置和使用的,下面是一個完整的授權(quán)策略示例:

apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-policynamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- from:- source:principals: ["cluster.local/ns/default/sa/sleep"]to:- operation:methods: ["GET"]paths: ["/info*"]when:- key: request.auth.claims[iss]values: ["https://foo.com"]

這個授權(quán)策略的含義是:篩選出?foo?這個 namespace 中含有?app: httpbin?label 的 pod,對發(fā)送到這些 pod 的請求進行匹配,如果匹配成功,則放行當前請求,匹配規(guī)則如下:發(fā)起請求的 pod 的 Service Account 需要是?cluster.local/ns/default/sa/sleep?,請求使用 HTTP 協(xié)議,請求的具體方法類型是?GET?,請求的 URL 為?/info*?,并且請求中需要包含由?https://foo.com?簽發(fā)的有效的 JWT Token。

從這個例子中可以看出一個授權(quán)策略主要包含以下幾個部分:

?name:授權(quán)策略的名稱,僅用于標識授權(quán)策略本身,不會影響規(guī)則的匹配和執(zhí)行。?namespace:當前授權(quán)策略對象所在的 namespace ,可以使用這個字段配置不同作用范圍的授權(quán)策略,詳見授權(quán)策略的作用范圍[1]。?selector:使用 label 來選擇當前授權(quán)策略作用于哪些 pod 上。注意,這里設(shè)置的是服務(wù)端的 pod ,因為最終這些規(guī)則會轉(zhuǎn)換成 Envoy 規(guī)則由服務(wù)端的 Envoy Proxy 來具體執(zhí)行。例如有 client 和 server 兩個 service ,它們的 pod 對應(yīng)的 label 分別為?app: client?和?app: server?,為了針對從 client 到 server 的請求進行配置授權(quán)策略,這里的 selector 應(yīng)該設(shè)置為?app: server。?action:可以為?ALLOW(默認值)或者?DENY。?rules:匹配規(guī)則,如果匹配成功,就會執(zhí)行對應(yīng)的 action ,詳見授權(quán)策略的規(guī)則詳解[2]

授權(quán)策略的作用范圍

授權(quán)策略可以按照作用域的大小分成三個不同的類型:全局策略、某個 namespace 內(nèi)的局部策略和具有明確 match label 的授權(quán)策略。下面分別進行說明。

全局策略

授權(quán)策略位于 istio 的 root namespace 中(例如?istio-system),且匹配所有的 pod。這種規(guī)則會作用于整個集群中的所有 pod。

下面的例子中有3個全局策略,第一個是全局?ALLOW?,第二個和第三個是全局?DENY?,后面這兩個作用類似,但又有重要的區(qū)別,詳見授權(quán)策略的匹配算法。

kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: global-allownamespace: istio-system spec:action: ALLOWrules:- {} EOFkubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: global-denynamespace: istio-system spec:action: DENYrules:- {} EOFkubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: global-denynamespace: istio-system spec:{} EOF

某個 namespace 內(nèi)的局部策略

授權(quán)策略位于除了 root namespace 之外的任何一個 namespace 中,且匹配所有的 pod ,這種情況下,這個策略會作用于當前 namespace 中的所有 pod。

下面的例子中是3個 namespace 級別的策略,第一個是?ALLOW?,第二個和第三個是?DENY?,像全局策略一樣,后面這兩個作用類似,但又有重要的區(qū)別,詳見授權(quán)策略的匹配算法。

kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: foo-namespace-allownamespace: foo spec:action: ALLOWrules:- {} EOFkubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: foo-namespace-denynamespace: foo spec:action: DENYrules:- {} EOFkubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: foo-namespace-denynamespace: foo spec:{} EOF

具有明確 match label 的授權(quán)策略

這種授權(quán)策略僅作用于當前 namespace 下使用?selector?字段匹配到的 pod。

kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-allownamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- {} EOF

授權(quán)策略的匹配算法

針對某一個請求,會按照一定的匹配算法來執(zhí)行相應(yīng)的授權(quán)策略:

1.如果有任何一條?DENY?授權(quán)策略匹配當前請求,則拒絕當前請求。2.針對當前 pod,如果沒有任何?ALLOW?授權(quán)策略,則放行當前請求。3.如果有任何一條?ALLOW?授權(quán)策略匹配當前請求,則放行當前請求。4.拒絕當前請求。

也就意味著,如果同時有?ALLOW?和?DENY?策略作用于同一個 pod 上,則?DENY?策略會優(yōu)先執(zhí)行,其它的?ALLOW?規(guī)則就會被忽略。

注意這個順序非常重要,有時又會比較隱晦,因此在配置比較復(fù)雜策略的時候需要多加小心。

在上文授權(quán)策略的作用范圍中提到授權(quán)策略在配置時,有一些細節(jié)上的差異,現(xiàn)結(jié)合授權(quán)策略的匹配算法進行一些分析。

spec:{}

這是一個?DENY?策略,作用于全局策略或者 namespace 級別(取決于策略所在 namespace 是否為 root namespace)。但是它并沒有對當前請求進行匹配,也就意味著按照授權(quán)策略的匹配算法在匹配的時候并不會優(yōu)先匹配到這條規(guī)則,因此可以將其作為一個“后備”策略,即全局或者 namespace 級別的一個默認策略。

spec:action: DENYrules:- {}

這條規(guī)則會真正地匹配當前的請求,又由于它是?DENY?規(guī)則,按照授權(quán)策略的匹配算法,它會首先得到執(zhí)行,也就意味著如果配置了一條這種全局或者 namespace 級別的規(guī)則,那么所有的其它?ALLOW?規(guī)則都不會得到執(zhí)行。因此這條規(guī)則在實際中并沒有什么價值。

spec:action: ALLOWrules:- {}

這條規(guī)則和上一條規(guī)則類似,但是它是?ALLOW?規(guī)則,因此按照授權(quán)策略的匹配算法,它的優(yōu)先級會低一些,因此也可以像第一條規(guī)則一樣作為一個全局或者 namespace 級別的默認策略。

授權(quán)策略的規(guī)則詳解

授權(quán)策略中最重要的是其中的?rule?字段,它指定了如何針對當前的請求進行匹配。如果一個授權(quán)策略中指定了多條?rule?規(guī)則,則它們之間是或的關(guān)系,即只要其中任意一條規(guī)則匹配成功,那么整個授權(quán)策略匹配成功,就會執(zhí)行相應(yīng)的 action ,下面是概述中提到的一個授權(quán)策略的例子:

apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-policynamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- from:- source:principals: ["cluster.local/ns/default/sa/sleep"]to:- operation:methods: ["GET"]paths: ["/info*"]when:- key: request.auth.claims[iss]values: ["https://foo.com"]

這里的?rules?是一個?rule?的列表。每一條?rule?規(guī)則包括三部分:from 、 to 和 when 。類似于防火墻規(guī)則,from 和 to 匹配當前請求從哪里來、到哪里去,when 會增加一些額外的檢測,當這些條件都滿足時,就會認為當前規(guī)則匹配成功。如果其中某一部分未進行配置,則認為其可以匹配成功。

在?rule?中進行配置時,所有的字符串類型都支持類似于通配符的匹配模式,例如?abc*?匹配 "abc" 和 "abcd" 等,*xyz?匹配 "xyz" 和 "axyz" 等,單獨的?*?匹配非空的字符串。

下面針對具體的字段詳細進行說明。

?from。針對請求的發(fā)送方進行匹配,主要包括 principals 、 requestPrincipals 、 namespaces 和 ipBlocks 四個部分。?principals。匹配發(fā)送方的身份,在 Kubernetes 中可以認為是 pod 的 Service Account。使用這個字段時,首先需要開啟 mTLS 功能,關(guān)于這部分內(nèi)容可參見對等認證。例如,當前請求是從 default namespace 中的 pod 中發(fā)出,且 pod 使用的 Service Account 名為?sleep,針對這個請求進行匹配,可將 principals 配置為[cluster.local/ns/default/sa/sleep]。?requestPrincipals。匹配請求中的 JWT Token 的?<issuer>/<subject>?字段組合。?namespaces。匹配發(fā)送方 pod 所在的 namespace。?ipBlocks。匹配請求的源 IP 地址段。?to。針對請求的接收方進行匹配。除了請求接收方,還會對請求本身進行匹配。包括以下字段:?hosts。目的 host。?ports。目的 port。?methods。是指當前請求執(zhí)行的 HTTP Method。針對 gRPC 服務(wù),這個字段需要設(shè)置為?POST。注意這個字段必須在 HTTP 協(xié)議時才進行匹配,如果請求不是 HTTP 協(xié)議,則認為匹配失敗。?paths。當前請求執(zhí)行的 HTTP URL Path。針對 gRPC 服務(wù),需要配置為?/package.service/method?格式。?when。這是一個 key/value 格式的 list 。這個字段會針對請求進行一些額外的檢測,當這些檢測全部匹配時才會認證當前規(guī)則匹配成功。例如?key: request.headers[User-Agent]?可以匹配 HTTP Header 中的?User-Agent?字段。所有可配置項可參見 Istio 官網(wǎng)上的?Authorization Policy Conditions[3]?說明。

針對以上字段,還有對應(yīng)的反向匹配操作,即“取反”匹配,包括 notPrincipals、notNamespaces 等。例如?notNamespaces: ["bar"]?表示當發(fā)送請求的 pod 不位于 "bar" 這個 namespace 中的時候匹配成功。

另外,在?rule?中會有非常多針對 JWT Token 進行匹配的字段,關(guān)于這部分可以查看 JWT 授權(quán)里的詳細分析。

下面針對上文列出來的授權(quán)策略給出一些實際的例子,一方面可以在實際環(huán)境中是如何使用這些策略的,另一方面也可以驗證前文所述的各種匹配字段、授權(quán)策略的匹配算法和授權(quán)策略的作用域。

操作示例

創(chuàng)建應(yīng)用

首先,創(chuàng)建客戶端和服務(wù)器端的 service 和對應(yīng)的 pod,使用的例子位于 istio 源代碼的?samples[4]?目錄中:

$ kubectl create ns foo $ kubectl apply -f <(istioctl kube-inject -f samples/httpbin/httpbin.yaml) -n foo $ kubectl apply -f <(istioctl kube-inject -f samples/sleep/sleep.yaml) -n foo

確認 pod 已正常運行:

$ kubectl get pod -n foo --show-labels NAME READY STATUS RESTARTS AGE LABELS httpbin-5d5df46d48-jndgh 2/2 Running 0 57s app=httpbin,istio.io/rev=,pod-template-hash=5d5df46d48,security.istio.io/tlsMode=isti o,version=v1 sleep-545684d78b-29x74 2/2 Running 0 56s app=sleep,istio.io/rev=,pod-template-hash=545684d78b,security.istio.io/tlsMode=istio $

確認可以正常訪問,且啟用了 mTLS 功能,關(guān)于 mTLS 功能的開啟和驗證請參見對等認證:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 200 $ $ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl http://httpbin.foo:8000/headers -s | grep X-Forwarded-Client-Cert"X-Forwarded-Client-Cert": "By=spiffe://cluster.local/ns/foo/sa/httpbin;Hash=e0f2132eb6ae920cec4b2ea16b9baa33ca388b719a2648636f7a75542852ff0e;Subject=\"\";URI=spiffe://cluster.local/ns/foo/sa/sleep"

全局策略測試

接下來創(chuàng)建一個全局默認的拒絕策略:

$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: global-denynamespace: istio-system spec:{} EOF

這時再進行驗證連通性:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 403

服務(wù)拒絕,表明全局拒絕策略生效。

接下來創(chuàng)建一個 httpbin pod 的?ALLOW?策略:

kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-allow-policynamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- to:- operation:methods: ["GET"] EOF

按照授權(quán)策略的匹配算法,應(yīng)該可以匹配到第3條規(guī)則,因此會執(zhí)行?ALLOW?動作,運行下面的命令進行驗證:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 200

測試 Rule 中的字段

下面我們以 Service Account 為例來進行說明。首先來檢查 sleep pod 所使用的的 Service Account:

$ kubectl get pod -l app=sleep -n foo -o jsonpath={.items...serviceAccountName} sleep

根據(jù) namespace 和 Service Account 構(gòu)造出 principals 字段,更新授權(quán)策略:

$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-allow-policynamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- from:- source:principals: ["cluster.local/ns/foo/sa/sleep"]to:- operation:methods: ["GET"] EOF

進行驗證:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 200

訪問仍然是放行狀態(tài),說明剛才的授權(quán)策略是生效的。

將授權(quán)策略中的 Service Account 改為一個其它值:

$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-allow-policynamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- from:- source:principals: ["cluster.local/ns/foo/sa/other-sa"]to:- operation:methods: ["GET"] EOF $ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 403

訪問失敗,因為授權(quán)策略中配置 Service Account 字段與實際的 Service Account 不匹配。

同樣地,可以配置 From、To 和 When 中的其它字段進行測試。

授權(quán)策略的匹配算法測試

首先,刪除之前創(chuàng)建的名為 httpbin-allow-policy 的授權(quán)策略,目前系統(tǒng)中僅存在一個全局的默認?DENY?策略。

kubectl delete authorizationpolicies httpbin-allow-policy -n foo

接下來創(chuàng)建一個匹配 "GET" 方法的?ALLOW?策略,名為 httpbin-allow-get:

$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-allow-getnamespace: foo spec:selector:matchLabels:app: httpbinaction: ALLOWrules:- to:- operation:methods: ["GET"] EOF

這時使用 "GET /ip" 請求進行測試,由于可以和 httpbin-allow-get 策略匹配,因此按照授權(quán)策略的匹配算法,可以匹配到第3條規(guī)則,因此可以正常訪問:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 200

使用 "POST /ip" 請求進行測試,與 httpbin-allow-get 策略不能匹配,因此會執(zhí)默認的全局?DENY?策略:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl -X POST "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 403

再創(chuàng)建一個 "/ip" 的?DENY?策略,名為 httpbin-deny-ip-url:

$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1beta1 kind: AuthorizationPolicy metadata:name: httpbin-deny-ip-urlnamespace: foo spec:selector:matchLabels:app: httpbinaction: DENYrules:- to:- operation:paths: ["/ip"] EOF

這時使用 "GET /ip" 請求進行測試:

$ kubectl exec $(kubectl get pod -l app=sleep -n foo -o jsonpath={.items..metadata.name}) -c sleep -n foo -- curl "http://httpbin.foo:8000/ip" -s -o /dev/null -w "sleep.foo to httpbin.foo: %{http_code}\n" sleep.foo to httpbin.foo: 403

可以看出執(zhí)行失敗。失敗的原因是 "GET /ip" 請求與我們剛才創(chuàng)建的 httpbin-allow-get 和 httpbin-deny-ip-url 兩個授權(quán)策略都會匹配,但是授權(quán)策略的匹配算法執(zhí)行到第1條規(guī)則時,會發(fā)現(xiàn)匹配 httpbin-deny-ip-url 授權(quán)策略,然后就會直接拒絕當前的請求。另一條授權(quán)策略 httpbin-allow-get 便無法得到執(zhí)行。

清理

執(zhí)行以下操作來清理我們創(chuàng)建過的各種資源:

$ kubectl delete authorizationpolicies httpbin-deny-ip-url -n foo $ kubectl delete authorizationpolicies httpbin-allow-get -n foo $ kubectl delete authorizationpolicies httpbin-allow-policy -n foo $ kubectl delete authorizationpolicies global-deny -n istio-system $ kubectl delete -f <(istioctl kube-inject -f samples/httpbin/httpbin.yaml) -n foo $ kubectl delete -f <(istioctl kube-inject -f samples/sleep/sleep.yaml) -n foo $ kubectl delete ns foo

總結(jié)

本節(jié)我們詳細分析了授權(quán)策略的概念和用法,也可以看出利用這些規(guī)則可以組合出非常復(fù)雜的場景,因此在使用復(fù)雜的授權(quán)策略時需要非常小心。另外,在授權(quán)策略中會涉及到很多針對請求中的 JWT Token 進行匹配的規(guī)則,相關(guān)的概念和用法會在下一節(jié)進行詳細闡述。

參考

?Authorization Policy[5]?Authorization Policy Conditions[6]?Authorization[7]

引用鏈接

[1]?授權(quán)策略的作用范圍:?#授權(quán)策略的作用范圍
[2]?授權(quán)策略的規(guī)則詳解:?#授權(quán)策略的規(guī)則詳解
[3]?Authorization Policy Conditions:?https://istio.io/latest/docs/reference/config/security/conditions/
[4]?samples:?https://github.com/istio/istio/tree/master/samples
[5]?Authorization Policy:?https://istio.io/latest/docs/reference/config/security/authorization-policy/
[6]?Authorization Policy Conditions:?https://istio.io/latest/docs/reference/config/security/conditions/
[7]?Authorization:?https://istio.io/latest/docs/tasks/security/authorization/

活動預(yù)告

Service Mesh Webinar #2

7 月 22 日(周三)晚 8 點,B 站直播《基于 MOSN 和 Istio Service Mesh 的服務(wù)治理實踐》,直播間 https://live.bilibili.com/21954520,點擊閱讀原文查看詳細信息。

Go 夜讀

Go 夜讀第 97 期我們可以從 MOSN 和相關(guān)的項目中學(xué)習(xí)到什么

點擊?閱讀原文?查看更多

總結(jié)

以上是生活随笔為你收集整理的Istio 中的授权策略详解的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。