本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。
EKS 控制平面
Amazon Elastic Kubernetes Service (EKS) 是一項受管 Kubernetes 服務,可讓您輕鬆地在 AWS 上執行 Kubernetes,而無需安裝、操作和維護您自己的 Kubernetes 控制平面或工作者節點。它執行上游 Kubernetes 並通過 Kubernetes 認證。此一致性可確保 EKS 支援 Kubernetes APIs,就像您可以在 EC2 或內部部署上安裝的開放原始碼社群版本一樣。在上游 Kubernetes 上執行的現有應用程式與 Amazon EKS 相容。
EKS 會自動管理 Kubernetes 控制平面節點的可用性和可擴展性,並自動取代運作狀態不佳的控制平面節點。
EKS 架構
EKS 架構旨在消除任何可能影響 Kubernetes 控制平面可用性和耐用性的單一故障點。
由 EKS 管理的 Kubernetes 控制平面會在 EKS 受管 VPC 內執行。EKS 控制平面包含 Kubernetes API 伺服器節點等叢集。執行 API 伺服器、排程器等元件並在自動擴展群組中kube-controller-manager
執行的 Kubernetes API 伺服器節點。EKS 在 AWS 區域 內的不同可用區域 (AZs) 中執行至少兩個 API 伺服器節點。同樣地,為了耐久性,在跨越三個 AZs 的自動調整規模群組中,也會執行已加密的伺服器節點。EKS 會在每個 AZ 中執行 NAT Gateway,而 API 伺服器和 等伺服器會在私有子網路中執行。此架構可確保單一 AZ 中的事件不會影響 EKS 叢集的可用性。
當您建立新的叢集時,Amazon EKS 會為您用來與叢集通訊的受管 Kubernetes API 伺服器建立高可用性端點 (使用 等工具kubectl
)。受管端點使用 NLB 來負載平衡 Kubernetes API 伺服器。EKS 也會在不同AZs佈建兩個 ENI ,以促進與工作者節點的通訊。
EKS 資料平面網路連線

您可以設定 Kubernetes 叢集的 API 伺服器是否可從公有網際網路 (使用公有端點) 或透過 VPC (使用 EKS 受管 ENIs) 或兩者連線。
無論使用者和工作者節點使用公有端點或 EKS 受管 ENI 連線至 API 伺服器,都有連線的備援路徑。
建議
檢閱下列建議。
監控控制平面指標
監控 Kubernetes API 指標可讓您深入了解控制平面效能並識別問題。運作狀態不佳的控制平面可能會影響叢集內執行之工作負載的可用性。例如,寫入不良的控制器可能會使 API 伺服器超載,進而影響應用程式的可用性。
Kubernetes 會在/metrics
端點公開控制平面指標。
您可以使用 檢視公開的指標kubectl
:
kubectl get --raw /metrics
這些指標會以 Prometheus 文字格式
您可以使用 Prometheus 來收集和存放這些指標。2020 年 5 月,CloudWatch 新增了在 CloudWatch Container Insights 中監控 Prometheus 指標的支援。因此,您也可以使用 Amazon CloudWatch 來監控 EKS 控制平面。您可以使用 教學課程來新增 Prometheus Scrape 目標:Prometheus KPI 伺服器指標來收集指標,並建立 CloudWatch 儀表板來監控叢集的控制平面。
您可以在此處apiserver_request_duration_seconds
可以指出 API 請求執行的時間長度。
請考慮監控這些控制平面指標:
API 伺服器
指標 | 描述 |
---|---|
|
每個動詞、試轉值、群組、版本、資源、範圍、元件和 HTTP 回應碼的中斷請求計數器。 |
|
每個動詞、試轉值、群組、版本、資源、子資源、範圍和元件的回應延遲分佈,以秒為單位。 |
|
以秒為單位的許可控制器延遲長條圖,以名稱識別,並針對每個操作和 API 資源和類型 (驗證或認可) 進行細分。 |
|
許可 Webhook 拒絕的計數。依名稱、操作、Rejection_code、類型 (驗證或許可)、錯誤_類型 (calling_webhook_error、apiserver_internal_error、no_error) 識別 |
|
請求延遲,以秒為單位。被動詞和 URL 分解。 |
|
HTTP 請求數量,依狀態碼、方法和主機分割。 |
etcd
指標 | 描述 |
---|---|
|
每個操作和物件類型的 Etcd 請求延遲,以秒為單位。 |
|
Etcd 資料庫大小。 |
請考慮使用 Kubernetes 監控概觀儀表板
下列 Prometheus 查詢可用來監控目前大小的 等。查詢假設有kube-apiserver
任務呼叫 從 API 指標端點抓取指標,且 EKS 版本低於 1.26 版。
max(etcd_db_total_size_in_bytes{job="kube-apiserver"} / (8 * 1024 * 1024 * 1024))
重要
當超過資料庫大小限制時, etcd 會發出無空間警示,並停止進一步的寫入請求。換言之,叢集會變成唯讀,而所有變更物件的請求,例如建立新 Pod、擴展部署等,都會遭到叢集的 API 伺服器拒絕。
叢集身分驗證
EKS 目前支援兩種類型的身分驗證:承載/服務帳戶字符
建立 EKS 叢集的 IAM 使用者或角色會自動取得叢集的完整存取權。您可以透過編輯 aws-auth 組態對應來管理對 EKS 叢集的存取。
如果您設定錯誤aws-auth
且無法存取叢集,您仍然可以使用叢集建立者的使用者或角色來存取 EKS 叢集。
萬一您無法在 AWS 區域中使用 IAM 服務,您也可以使用 Kubernetes 服務帳戶的承載字符來管理叢集。
建立允許在叢集中執行所有動作super-admin
的帳戶:
kubectl -n kube-system create serviceaccount super-admin
建立提供超級管理員叢集管理員角色的角色繫結:
kubectl create clusterrolebinding super-admin-rb --clusterrole=cluster-admin --serviceaccount=kube-system:super-admin
取得服務帳戶的秘密:
SECRET_NAME=`kubectl -n kube-system get serviceaccount/super-admin -o jsonpath='{.secrets[0].name}'`
取得與秘密相關聯的字符:
TOKEN=`kubectl -n kube-system get secret $SECRET_NAME -o jsonpath='{.data.token}'| base64 --decode`
將服務帳戶和字符新增至 kubeconfig
:
kubectl config set-credentials super-admin --token=$TOKEN
將 中的目前內容設定為kubeconfig
使用超級管理員帳戶:
kubectl config set-context --current --user=super-admin
最終kubeconfig
應如下所示:
apiVersion: v1 clusters: - cluster: certificate-authority-data:<REDACTED> server: https://<CLUSTER>.gr7.us-west-2.eks.amazonaws.com name: arn:aws:eks:us-west-2:<account number>:cluster/<cluster name> contexts: - context: cluster: arn:aws:eks:us-west-2:<account number>:cluster/<cluster name> user: super-admin name: arn:aws:eks:us-west-2:<account number>:cluster/<cluster name> current-context: arn:aws:eks:us-west-2:<account number>:cluster/<cluster name> kind: Config preferences: {} users: #- name: arn:aws:eks:us-west-2:<account number>:cluster/<cluster name> # user: # exec: # apiVersion: client.authentication.k8s.io/v1alpha1 # args: # - --region # - us-west-2 # - eks # - get-token # - --cluster-name # - <<cluster name>> # command: aws # env: null - name: super-admin user: token: <<super-admin sa's secret>>
許可 Webhook
Kubernetes 有兩種類型的許可 Webhook:驗證許可 Webhook 和變更許可 Webhook
為了避免影響叢集關鍵操作,請避免設定如下所示的「全部捕捉」 Webhook:
- name: "pod-policy.example.com" rules: - apiGroups: ["*"] apiVersions: ["*"] operations: ["*"] resources: ["*"] scope: "*"
或者,確定 Webhook 具有故障開啟政策,其逾時短於 30 秒,以確保如果 Webhook 無法使用,這不會影響叢集關鍵工作負載。
封鎖具有不安全的 Pod sysctls
Sysctl
是 Linux 公用程式,可讓使用者在執行時間修改核心參數。這些核心參數可控制作業系統行為的各個層面,例如網路、檔案系統、虛擬記憶體和程序管理。
Kubernetes 允許指派 Pod 的sysctl
設定檔。Kubernetes 分類systcls
為安全和不安全。安全sysctls
會在容器或 Pod 中命名,而設定不會影響節點或節點本身上的其他 Pod。相反地,不安全的 sysctl 預設為停用,因為它們可能會中斷其他 Pod 或使節點不穩定。
由於預設為sysctls
停用不安全,因此 kubelet 不會建立具有不安全sysctl
設定檔的 Pod。如果您建立這類 Pod,排程器會重複將這類 Pod 指派給節點,而節點無法啟動。此無限迴圈最終會對叢集控制平面造成壓力,使叢集不穩定。
考慮使用 OPA Gatekeepersysctls
。
處理叢集升級
自 2021 年 4 月起,Kubernetes 發行週期已從每年四個版本 (每季一次) 變更為每年三個版本。新的次要版本 (例如 1.21 或 1.22) 大約每 15 週
叢集端點連線
使用 Amazon EKS (Elastic Kubernetes Service) 時,您可能會在 Kubernetes 控制平面擴展或修補等事件期間遇到連線逾時或錯誤。這些事件可能會導致 kube-apiserver 執行個體遭到取代,可能會導致解析 FQDN 時傳回不同的 IP 地址。本文件概述 Kubernetes API 消費者維持可靠連線的最佳實務。
注意
實作這些最佳實務可能需要更新用戶端組態或指令碼,才能有效地處理新的 DNS 重新解析和重試策略。
主要問題來自 DNS 用戶端快取,以及 EKS 端點 - 公有端點的公有 NLB 或私有端點的 X-ENI 的可能過時 IP 地址。取代 kube-apiserver 執行個體時,完整網域名稱 (FQDN) 可能會解析為新的 IP 地址。不過,由於 DNS 存留時間 (TTL) 設定在 AWS 受管 Route 53 區域中設定為 60 秒,用戶端可能會在短時間內繼續使用過期的 IP 地址。
為了緩解這些問題,Kubernetes API 取用者 (例如 kubectl、CI/CD 管道和自訂應用程式) 應實作下列最佳實務:
-
實作 DNS 重新解析
-
使用退避和抖動實作重試。例如,請參閱這篇名為 Failures Happen 的文章
-
實作用戶端逾時。設定適當的逾時,以防止長時間執行的請求封鎖您的應用程式。請注意,某些 Kubernetes 用戶端程式庫,特別是 OpenAPI 產生器所產生的程式庫,可能不允許輕鬆設定自訂逾時。
-
使用 kubectl 的範例 1:
kubectl get pods --request-timeout 10s # default: no timeout
-
使用 Python 的範例 2:Kubernetes 用戶端提供 _request_timeout 參數
-
透過實作這些最佳實務,您可以在與 Kubernetes API 互動時大幅改善應用程式的可靠性和彈性。請記得徹底測試這些實作,特別是在模擬失敗條件下,以確保它們在實際擴展或修補事件期間如預期般運作。
執行大型叢集
EKS 會主動監控控制平面執行個體上的負載,並自動進行擴展以確保高效能。不過,在執行大型叢集時,您應該考慮 Kubernetes 內的潛在效能問題和限制,以及 AWS 服務中的配額。
-
使用
iptables
kube-proxy
時,根據 ProjectCalico 團隊執行的測試,超過 1000 個服務的叢集可能會遇到網路延遲。解決方案是切換到kube-proxy在 ipvs 模式下執行。 -
如果 CNI 需要請求 Pod 的 IP 地址,或者如果您需要經常建立新的 EC2 執行個體,您可能也會遇到 EC2 API 請求限流。 EC2 您可以透過設定 CNI 快取 IP 地址來減少呼叫 EC2 API。您可以使用較大的 EC2 執行個體類型來減少 EC2 擴展事件。