Kubernetes
  • 序言
  • 基礎入門
    • Kubernetes 簡介
    • Kubernetes 基本概念
    • Kubernetes 101
    • Kubernetes 201
    • Kubernetes 集群
  • 核心原理
    • 核心原理
    • 架構原理
    • 設計理念
    • 核心組件
      • etcd
      • kube-apiserver
      • kube-scheduler
      • kube-controller-manager
      • kubelet
      • kube-proxy
      • kube-dns
      • Federation
      • kubeadm
      • hyperkube
      • kubectl
    • 資源對象
      • Autoscaling
      • ConfigMap
      • CronJob
      • CustomResourceDefinition
      • DaemonSet
      • Deployment
      • Ingress
      • Job
      • LocalVolume
      • Namespace
      • NetworkPolicy
      • Node
      • PersistentVolume
      • Pod
      • PodPreset
      • ReplicaSet
      • Resource Quota
      • Secret
      • SecurityContext
      • Service
      • ServiceAccount
      • StatefulSet
      • Volume
  • 部署配置
    • 部署指南
    • kubectl 安裝
    • 單機部署
    • 特性開關
    • 最佳配置
    • 版本支持
    • 集群部署
      • kubeadm
      • kops
      • Kubespray
      • Azure
      • Windows
      • LinuxKit
      • kubeasz
    • 附加組件
      • Addon-manager
      • DNS
      • Dashboard
      • 監控
      • 日誌
      • Metrics
      • GPU
      • Cluster Autoscaler
      • ip-masq-agent
    • Kubernetes-The-Hard-Way
      • 準備部署環境
      • 安裝必要工具
      • 創建計算資源
      • 配置創建證書
      • 配置生成配置
      • 配置生成密鑰
      • 部署 Etcd 群集
      • 部署控制節點
      • 部署計算節點
      • 配置 Kubectl
      • 配置網絡路由
      • 部署 DNS 擴展
      • 煙霧測試
      • 刪除集群
  • 插件擴展
    • API 擴展
      • Aggregation
      • CustomResourceDefinition
    • 訪問控制
      • 認證
      • RBAC 授權
      • 准入控制
    • Scheduler 擴展
    • 網絡插件
      • CNI
      • Flannel
      • Calico
      • Weave
      • Cilium
      • OVN
      • Contiv
      • SR-IOV
      • Romana
      • OpenContrail
      • Kuryr
    • 運行時插件 CRI
      • CRI-tools
      • Frakti
    • 存儲插件
      • 容器存儲接口 CSI
      • FlexVolume
      • glusterfs
    • 網絡策略
    • Ingress Controller
      • Ingress + Letsencrypt
      • minikube Ingress
      • Traefik Ingress
      • Keepalived-VIP
    • Cloud Provider 擴展
    • Device 插件
  • 服務治理
    • 服務治理
      • 一般準則
      • 滾動升級
      • Helm
      • Operator
      • Service Mesh
      • Linkerd
      • Linkerd2
    • Istio
      • 安裝
      • 流量管理
      • 安全管理
      • 策略管理
      • 度量管理
      • 排錯
      • 社區
    • Devops
      • Draft
      • Jenkins X
      • Spinnaker
      • Kompose
      • Skaffold
      • Argo
      • Flux GitOps
  • 實踐案例
    • 實踐概覽
    • 資源控制
    • 集群高可用
    • 應用高可用
    • 調試
    • 端口映射
    • 端口轉發
    • 用戶管理
    • GPU
    • HugePage
    • 安全
    • 審計
    • 備份恢復
    • 證書輪換
    • 大規模集群
    • 大數據與機器學習
      • Spark
      • Tensorflow
    • Serverless
  • 排錯指南
    • 排錯概覽
    • 集群排錯
    • Pod 排錯
    • 網絡排錯
    • PV 排錯
      • AzureDisk
      • AzureFile
    • Windows 排錯
    • 雲平臺排錯
      • Azure
    • 排錯工具
  • 社區貢獻
    • 開發指南
    • 單元測試和集成測試
    • 社區貢獻
  • 附錄
    • 生態圈
    • 學習資源
    • 國內鏡像
    • 如何貢獻
    • 參考文檔
Powered by GitBook
On this page
  • Azure 負載均衡
  • LoadBalancer Service 一直處於 pending 狀態
  • 負載均衡公網 IP 無法訪問
  • 內網負載均衡 BackendPool 爲空
  • 外網負載均衡均衡 BackendPool 爲空
  • Service 刪除後 Azure 公網 IP 未自動刪除
  • MSI 無法使用
  • Azure ARM API 調用請求過多
  • AKS kubectl logs connection timed out
  • 使用 Virtual Kubelet 後 LoadBalancer Service 無法分配公網 IP
  • Node 的 GPU 數總是 0
  • Azure ServicePrincipal 過期
  • Node 自動重啓
  • AKS Periscope
  • 已知問題及修復版本
  • 參考文檔
  1. 排錯指南
  2. 雲平臺排錯

Azure

Previous雲平臺排錯Next排錯工具

Last updated 1 year ago

Azure 負載均衡

使用 Azure Cloud Provider 後,Kubernetes 會爲 LoadBalancer 類型的 Service 創建 Azure 負載均衡器以及相關的 公網 IP、BackendPool 和 Network Security Group (NSG)。注意目前 Azure Cloud Provider 僅支持 Basic SKU 的負載均衡,並將在 v1.11 中支持 Standard SKU。Basic 與 Standard SKU 負載均衡相比有一定的:

Load Balancer
Basic
Standard

Back-end pool size

up to 100

up to 1,000

Back-end pool boundary

Availability Set

virtual network, region

Back-end pool design

VMs in Availability Set, virtual machine scale set in Availability Set

Any VM instance in the virtual network

HA Ports

Not supported

Available

Diagnostics

Limited, public only

Available

VIP Availability

Not supported

Available

Fast IP Mobility

Not supported

Available

Availability Zones scenarios

Zonal only

Zonal, Zone-redundant, Cross-zone load-balancing

Outbound SNAT algorithm

On-demand

Preallocated

Outbound SNAT front-end selection

Not configurable, multiple candidates

Optional configuration to reduce candidates

Network Security Group

Optional on NIC/subnet

Required

同樣,對應的 Public IP 也是 Basic SKU,與 Standard SKU 相比也有一定的:

Public IP
Basic
Standard

Availability Zones scenarios

Zonal only

Zone-redundant (default), zonal (optional)

Fast IP Mobility

Not supported

Available

VIP Availability

Not supported

Available

Counters

Not supported

Available

Network Security Group

Optional on NIC

Required

在 Kubernetes 中,負載均衡的創建邏輯都在 kube-controller-manager 中,因而排查負載均衡相關的問題時,除了查看 Service 自身的狀態,如

kubectl describe service <service-name>

還需要查看 kube-controller-manager 是否有異常發生:

PODNAME=$(kubectl -n kube-system get pod -l component=kube-controller-manager -o jsonpath='{.items[0].metadata.name}')
kubectl -n kube-system logs $PODNAME --tail 100

LoadBalancer Service 一直處於 pending 狀態

查看 Service kubectl describe service <service-name> 沒有錯誤信息,但 EXTERNAL-IP 一直是 <pending>,說明 Azure Cloud Provider 在創建 LB/NSG/PublicIP 過程中出錯。一般按照前面的步驟查看 kube-controller-manager 可以查到具體失敗的原因,可能的因素包括

  • clientId、clientSecret、tenandId 或 subscriptionId 配置錯誤導致 Azure API 認證失敗:更新所有節點的 /etc/kubernetes/azure.json ,修復錯誤的配置即可恢復服務

  • 配置的客戶端無權管理 LB/NSG/PublicIP/VM:可以爲使用的 clientId 增加授權或創建新的 az ad sp create-for-rbac --role="Contributor" --scopes="/subscriptions/<subscriptionID>/resourceGroups/<resourceGroupName>"

  • Kuberentes v1.8.X 中還有可能出現 Security rule must specify SourceAddressPrefixes, SourceAddressPrefix, or SourceApplicationSecurityGroups 的錯誤,這是由於 Azure Go SDK 的問題導致的,可以通過升級集群到 v1.9.X/v1.10.X 或者將 SourceAddressPrefixes 替換爲多條 SourceAddressPrefix 規則來解決

負載均衡公網 IP 無法訪問

Azure Cloud Provider 會爲負載均衡器創建探測器,只有探測正常的服務纔可以響應用戶的請求。負載均衡公網 IP 無法訪問一般是探測失敗導致的,可能原因有:

  • 後端 VM 本身不正常(可以重啓 VM 恢復)

  • 後端容器未監聽在設置的端口上(可通過配置正確的端口解決)

  • 防火牆或網絡安全組阻止了要訪問的端口(可通過增加安全規則解決)

  • 後端容器不響應(部分或者全部)外部請求時也會導致負載均衡 IP 無法訪問。注意這裏包含部分容器不響應的場景,這是由於 Azure 探測器與 Kubernetes 服務發現機制共同導致的結果:

    • (1)Azure 探測器定期去訪問 service 的端口(即 NodeIP:NodePort)

    • (2)Kubernetes 將其負載均衡到後端容器中

    • (3)當負載均衡到異常容器時,訪問失敗會導致探測失敗,進而 Azure 可能會將 VM 移出負載均衡

內網負載均衡 BackendPool 爲空

外網負載均衡均衡 BackendPool 爲空

在使用不支持 Cloud Provider 的工具(如 kubeadm)部署的集群中,如果未給 Kubelet 配置 --cloud-provider=azure --cloud-config=/etc/kubernetes/cloud-config,那麼 Kubelet 會以 hostname 將其註冊到集群中。此時,查看該 Node 的信息(kubectl get node -o yaml),可以發現其 externalID 與 hostname 相同。此時,kube-controller-manager 也無法將其加入到負載均衡的後端中。

一個簡單的確認方式是查看 Node 的 externalID 和 name 是否不同:

$ kubectl get node -o jsonpath='{.items[*].metadata.name}'
k8s-agentpool1-27347916-0
$ kubectl get node -o jsonpath='{.items[*].spec.externalID}'
/subscriptions/<subscription-id>/resourceGroups/<rg-name>/providers/Microsoft.Compute/virtualMachines/k8s-agentpool1-27347916-0

該問題的解決方法是先刪除 Node kubectl delete node <node-name>,爲 Kubelet 配置 --cloud-provider=azure --cloud-config=/etc/kubernetes/cloud-config,最後再重啓 Kubelet。

Service 刪除後 Azure 公網 IP 未自動刪除

MSI 無法使用

Azure ARM API 調用請求過多

有時 kube-controller-manager 或者 kubelet 會因請求調用過多而導致 Azure ARM API 失敗的情況,比如

"OperationNotAllowed",\r\n    "message": "The server rejected the request because too many requests have been received for this subscription.

一般來說,如果該問題重複出現可以考慮

  • 使用 Azure instance metadata,即爲所有 Node 的 /etc/kubernetes/azure.json 設置 "useInstanceMetadata": true 並重啓 kubelet

  • 爲 kube-controller-manager 增大 --route-reconciliation-period(默認爲 10s),比如在 /etc/kubernetes/manifests/kube-controller-manager.yaml 中設置 --route-reconciliation-period=1m 後 kubelet 會自動重新創建 kube-controller-manager Pod。

AKS kubectl logs connection timed out

$ kubectl --v=8 logs x
I0308 10:32:21.539580   26486 round_trippers.go:417] curl -k -v -XGET  -H "Accept: application/json, */*" -H "User-Agent: kubectl/v1.8.1 (linux/amd64) kubernetes/f38e43b" -H "Authorization: Bearer x" https://x:443/api/v1/namespaces/default/pods/x/log?container=x
I0308 10:34:32.790295   26486 round_trippers.go:436] GET https://X:443/api/v1/namespaces/default/pods/x/log?container=x 500 Internal Server Error in 131250 milliseconds
I0308 10:34:32.790356   26486 round_trippers.go:442] Response Headers:
I0308 10:34:32.790376   26486 round_trippers.go:445]     Content-Type: application/json
I0308 10:34:32.790390   26486 round_trippers.go:445]     Content-Length: 275
I0308 10:34:32.790414   26486 round_trippers.go:445]     Date: Thu, 08 Mar 2018 09:34:32 GMT
I0308 10:34:32.790504   26486 request.go:836] Response Body: {"kind":"Status","apiVersion":"v1","metadata":{},"status":"Failure","message":"Get https://aks-nodepool1-53392281-1:10250/containerLogs/default/x: dial tcp 10.240.0.6:10250: getsockopt: connection timed out","code":500}
I0308 10:34:32.790999   26486 helpers.go:207] server response object: [{
  "metadata": {},
  "status": "Failure",
  "message": "Get https://aks-nodepool1-53392281-1:10250/containerLogs/default/x/x: dial tcp 10.240.0.6:10250: getsockopt: connection timed out",
  "code": 500
}]
F0308 10:34:32.791043   26486 helpers.go:120] Error from server: Get https://aks-nodepool1-53392281-1:10250/containerLogs/default/x/x: dial tcp 10.240.0.6:10250: getsockopt: connection timed out

在 AKS 中,kubectl logs, exec, and attach 等命令需要 Master 與 Nodes 節點之間建立隧道連接。在 kube-system namespace 中可以看到 tunnelfront 和 kube-svc-redirect Pod:

$ kubectl -n kube-system get po -l component=tunnel
NAME                           READY     STATUS    RESTARTS   AGE
tunnelfront-7644cd56b7-l5jmc   1/1       Running   0          2d

$ kubectl -n kube-system get po -l component=kube-svc-redirect
NAME                      READY     STATUS    RESTARTS   AGE
kube-svc-redirect-pq6kf   1/1       Running   0          2d
kube-svc-redirect-x6sq5   1/1       Running   0          2d
kube-svc-redirect-zjl7x   1/1       Running   1          2d

如果它們不是處於 Running 狀態或者 Exec/Logs/PortForward 等命令報 net/http: TLS handshake timeout 錯誤,刪除 tunnelfront Pod,稍等一會就會自動創建新的出來,如:

$ kubectl -n kube-system delete po -l component=tunnel
pod "tunnelfront-7644cd56b7-l5jmc" deleted

使用 Virtual Kubelet 後 LoadBalancer Service 無法分配公網 IP

使用 Virtual Kubelet 後,LoadBalancer Service 可能會一直處於 pending 狀態,無法分配 IP 地址。查看該服務的事件(如 kubectl describe svc)會發現錯誤 CreatingLoadBalancerFailed 4m (x15 over 45m) service-controller Error creating load balancer (will retry): failed to ensure load balancer for service default/nginx: ensure(default/nginx): lb(kubernetes) - failed to ensure host in pool: "instance not found"。這是由於 Virtual Kubelet 創建的虛擬 Node 並不存在於 Azure 雲平臺中,因而無法將其加入到 Azure Load Balancer 的後端中。

解決方法是開啓 ServiceNodeExclusion 特性,即設置 kube-controller-manager --feature-gates=ServiceNodeExclusion=true。開啓後,所有帶有 alpha.service-controller.kubernetes.io/exclude-balancer 標籤的 Node 都不會加入到雲平臺負載均衡的後端中。

注意該特性僅適用於 Kubernetes 1.9 及以上版本。

Node 的 GPU 數總是 0

當在 AKS 集群中運行 GPU 負載時,發現它們無法調度,這可能是由於 Node 容量中的 nvidia.com/gpu 總是0。

解決方法是重新部署 nvidia-gpu 設備插件擴展:

apiVersion: extensions/v1beta1
kind: DaemonSet
metadata:
  labels:
    kubernetes.io/cluster-service: "true"
  name: nvidia-device-plugin
  namespace: kube-system
spec:
  template:
    metadata:
      # Mark this pod as a critical add-on; when enabled, the critical add-on scheduler
      # reserves resources for critical add-on pods so that they can be rescheduled after
      # a failure.  This annotation works in tandem with the toleration below.
      annotations:
        scheduler.alpha.kubernetes.io/critical-pod: ""
      labels:
        name: nvidia-device-plugin-ds
    spec:
      tolerations:
      # Allow this pod to be rescheduled while the node is in "critical add-ons only" mode.
      # This, along with the annotation above marks this pod as a critical add-on.
      - key: CriticalAddonsOnly
        operator: Exists
      containers:
      - image: nvidia/k8s-device-plugin:1.10
        name: nvidia-device-plugin-ctr
        securityContext:
          allowPrivilegeEscalation: false
          capabilities:
            drop: ["ALL"]
        volumeMounts:
          - name: device-plugin
            mountPath: /var/lib/kubelet/device-plugins
      volumes:
        - name: device-plugin
          hostPath:
            path: /var/lib/kubelet/device-plugins
      nodeSelector:
        beta.kubernetes.io/os: linux
        accelerator: nvidia

Azure ServicePrincipal 過期

默認情況下,Service Principal 的過期時間是 1 年,可以通過以下的命令延長過期時間:

az ad sp credential reset --name <clientId> --password <clientSecret> --years <newYears>

Node 自動重啓

AKS Periscope

使用方法:

az extension add --name aks-preview
az aks kollect -g MyResourceGroup -n MyManagedCluster --storage-account MyStorageAccount --sas-token "MySasToken"

已知問題及修復版本

  1. 手動更新 VMSS VM 到最新時 Azure LoadBalancer 後端丟失問題

    • Basic LoadBalancer 修復版本: v1.14.7, v1.15.4, v1.16.0 及更高版本

    • Standard LoadBalancer 修復版本: v1.15.12, v1.16.9, v1.17.5, v1.18.1 及更高版本

  2. Service 未配置 DNS 標籤導致公網 IP 上 DNS 標籤丟失問題

    • 受影響版本:v1.17.0-v1.17.2, v1.16.0-v1.16.6, v1.15.7-v1.15.9, v1.14.10

    • 修復版本:v1.15.10, v1.16.7, v1.17.3, v1.18.0 及更高版本

  3. 路由表併發更新衝突問題

    • 修復版本:v1.15.11, v1.16.8, v1.17.4, v1.18.0 及更高版本

  4. VMSS VM 併發更新衝突問題

    • 修復版本:v1.15.11, v1.16.8, v1.17.4, v1.18.0 及更高版本

  5. VMSS 緩存不一致問題

    • 受影響版本:v1.15.8-v1.15.11, v1.16.5-v1.16.8, v1.17.1-v1.17.4

    • 修復版本:v1.15.12, v1.16.9, v1.17.5, v1.18.0 及更高版本

參考文檔

在創建 Service 時,可以通過 metadata.annotation 來自定義 Azure 負載均衡的行爲,可選的 Annotation 列表請參考 。

當使用內網負載均衡時,從同一個 ILB 的後端 VM 上訪問 ILB VIP 時也會失敗,這是 Azure 的(此時可以訪問 service 的 clusterIP)

該問題的解決方法是使用,保證異常容器自動從服務的後端(endpoints)中刪除。

Kubernetes 1.9.0-1.9.3 中會有這個問題( ),這是由於一個查找負載均衡所屬 AvaibilitySet 的缺陷導致的。

該問題的修復( )將包含到 v1.9.4 和 v1.10 中。

Kubernetes 1.9.0-1.9.3 中會有這個問題():當創建超過 10 個 LoadBalancer Service 後有可能會碰到由於超過 FrontendIPConfiguations Quota(默認爲 10)導致負載均衡無法創建的錯誤。此時雖然負載均衡無法創建,但公網 IP 已經創建成功了,由於 Cloud Provider 的缺陷導致刪除 Service 後公網 IP 卻未刪除。

該問題的修復()將包含到 v1.9.4 和 v1.10 中。

另外,超過 FrontendIPConfiguations Quota 的問題可以參考 增加 Quota 來解決。

配置 "useManagedIdentityExtension": true 後,可以使用 來管理 Azure API 的認證授權。但由於 Cloud Provider 的缺陷( 未定義 useManagedIdentityExtension yaml 標籤導致無法解析該選項。

該問題的修復()將包含在 v1.10 中。

特別是在 Kubernetes 集群創建或者批量增加 Nodes 的時候。從 開始, Azure cloud provider 爲一些列的 Azure 資源(如 VM、VMSS、安全組和路由表等)增加了緩存,大大緩解了這個問題。

kubectl logs 命令報 getsockopt: connection timed out 的錯誤():

爲了保護 AKS 群集,安全更新自動應用於所有的 Linux 節點。 這些更新包括 OS 安全修復項或內核更新,其中的部分更新需要重啓節點才能完成。 AKS 不會自動重新啓動這些 Linux 節點,但你可以參考配置 來自動重啓節點。

除此之外,如果你還想收到節點需要重啓的通知,可以參考 進行配置。

是一個用於排查 AKS 集群問題的調試工具,開源在 <github.com/Azure/aks-periscope>。

問題鏈接: 和

問題鏈接:

問題鏈接:

問題鏈接:

僅包含在 v1.18.0 或更高版本中的性能優化:

問題鏈接:

更多的 AKS 排錯信息可以參考 。

侷限
侷限
Cloud Provider Azure 文檔
預期行爲
健康探針
kubernetes#59746
kubernetes#60060
acs-engine#2151
kubernetes#59747
kubernetes#59083
kubernetes#59255
kubernetes#59340
Azure subscription and service limits, quotas, and constraints
Managed Service Identity (MSI)
kubernetes #60691
kubernetes#60775
v1.9.2 和 v1.10
AKS#232
這裏
kured
Dashboard and notifications on AKS for required worker nodes reboots
AKS Periscope
https://github.com/kubernetes/kubernetes/issues/80365
https://github.com/kubernetes/kubernetes/issues/89336
https://github.com/kubernetes/kubernetes/issues/87127
https://github.com/kubernetes/kubernetes/issues/88151
https://github.com/kubernetes/kubernetes/pull/88094
https://github.com/kubernetes/kubernetes/pull/88699
https://github.com/kubernetes/kubernetes/issues/89025
AKS 常見問題
AKS troubleshooting
Azure subscription and service limits, quotas, and constraints
Virtual Kubelet - Missing Load Balancer IP addresses for services
Troubleshoot Azure Load Balancer
Troubleshooting CustomScriptExtension (CSE) and acs-engine
Setting up azure firewall for analysing outgoing traffic in AKS
Dashboard and notifications on AKS for required worker nodes reboots