信任網域遷移
此任務說明如何在不變更授權政策的情況下,從一個信任網域遷移到另一個信任網域。
在 Istio 1.4 中,我們引入了一個 alpha 功能,以支援授權策略的信任域遷移。這表示如果 Istio 網格需要變更其信任域,就不需要手動變更授權策略。在 Istio 中,如果一個工作負載在命名空間 foo
中使用服務帳戶 bar
執行,並且系統的信任域是 my-td
,則該工作負載的身分是 spiffe://my-td/ns/foo/sa/bar
。預設情況下,Istio 網格信任域是 cluster.local
,除非您在安裝期間指定它。
開始之前
在開始這項任務之前,請執行以下操作
閱讀Istio 授權概念。
安裝具有自訂信任域並啟用相互 TLS 的 Istio。
$ istioctl install --set profile=demo --set meshConfig.trustDomain=old-td
在
default
命名空間中部署httpbin 範例,並在default
和curl-allow
命名空間中部署 curl 範例$ kubectl label namespace default istio-injection=enabled $ kubectl apply -f @samples/httpbin/httpbin.yaml@ $ kubectl apply -f @samples/curl/curl.yaml@ $ kubectl create namespace curl-allow $ kubectl label namespace curl-allow istio-injection=enabled $ kubectl apply -f @samples/curl/curl.yaml@ -n curl-allow
套用以下授權策略,以拒絕所有對
httpbin
的請求,但來自curl-allow
命名空間中的curl
的請求除外。$ kubectl apply -f - <<EOF apiVersion: security.istio.io/v1 kind: AuthorizationPolicy metadata: name: service-httpbin.default.svc.cluster.local namespace: default spec: rules: - from: - source: principals: - old-td/ns/curl-allow/sa/curl to: - operation: methods: - GET selector: matchLabels: app: httpbin --- EOF
請注意,授權策略可能需要數十秒才能傳播到 sidecar。
驗證來自以下位置的對
httpbin
的請求default
命名空間中的curl
被拒絕。$ kubectl exec "$(kubectl get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 403
curl-allow
命名空間中的curl
被允許。$ kubectl exec "$(kubectl -n curl-allow get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -n curl-allow -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 200
在沒有信任網域別名的情況下遷移信任網域
安裝具有新信任域的 Istio。
$ istioctl install --set profile=demo --set meshConfig.trustDomain=new-td
重新部署 istiod 以取得信任域變更。
$ kubectl rollout restart deployment -n istio-system istiod
Istio 網格現在使用新的信任域
new-td
執行。重新部署
httpbin
和curl
應用程式,以取得來自新 Istio 控制平面的變更。$ kubectl delete pod --all
$ kubectl delete pod --all -n curl-allow
驗證來自
default
命名空間和curl-allow
命名空間中curl
的對httpbin
的請求都被拒絕。$ kubectl exec "$(kubectl get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 403
$ kubectl exec "$(kubectl -n curl-allow get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -n curl-allow -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 403
這是因為我們指定了一個授權策略,該策略拒絕所有對
httpbin
的請求,但old-td/ns/curl-allow/sa/curl
身分 (這是curl-allow
命名空間中curl
應用程式的舊身分) 的請求除外。當我們遷移到上述新的信任域 (即new-td
) 時,此curl
應用程式的身分現在是new-td/ns/curl-allow/sa/curl
,這與old-td/ns/curl-allow/sa/curl
不同。因此,之前允許從curl-allow
命名空間中的curl
應用程式發送到httpbin
的請求現在被拒絕。在 Istio 1.4 之前,使此操作生效的唯一方法是手動變更授權策略。在 Istio 1.4 中,我們引入了一種簡單的方法,如下所示。
使用信任網域別名遷移信任網域
安裝具有新信任域和信任域別名的 Istio。
$ cat <<EOF > ./td-installation.yaml apiVersion: install.istio.io/v1alpha1 kind: IstioOperator spec: meshConfig: trustDomain: new-td trustDomainAliases: - old-td EOF $ istioctl install --set profile=demo -f td-installation.yaml -y
在不變更授權策略的情況下,驗證來自以下位置的對
httpbin
的請求default
命名空間中的curl
被拒絕。$ kubectl exec "$(kubectl get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 403
curl-allow
命名空間中的curl
被允許。$ kubectl exec "$(kubectl -n curl-allow get pod -l app=curl -o jsonpath={.items..metadata.name})" -c curl -n curl-allow -- curl http://httpbin.default:8000/ip -sS -o /dev/null -w "%{http_code}\n" 200
最佳實務
從 Istio 1.4 開始,在編寫授權策略時,您應考慮在策略中使用值 cluster.local
作為信任域部分。例如,它應該是 cluster.local/ns/curl-allow/sa/curl
,而不是 old-td/ns/curl-allow/sa/curl
。請注意,在這種情況下,cluster.local
不是 Istio 網格信任域 (信任域仍然是 old-td
)。但是,在授權策略中,cluster.local
是一個指向目前信任域 (即 old-td
(以及稍後的 new-td
)) 及其別名的指標。通過在授權策略中使用 cluster.local
,當您遷移到新的信任域時,Istio 將會偵測到這一點,並將新的信任域視為舊的信任域,而無需您包含別名。
清理
$ kubectl delete authorizationpolicy service-httpbin.default.svc.cluster.local
$ kubectl delete deploy httpbin; kubectl delete service httpbin; kubectl delete serviceaccount httpbin
$ kubectl delete deploy curl; kubectl delete service curl; kubectl delete serviceaccount curl
$ istioctl uninstall --purge -y
$ kubectl delete namespace curl-allow istio-system
$ rm ./td-installation.yaml