调试 pod 之间的网络连接
查看用于调试 pod 之间的连接问题的选项和策略。
检查集群组件和联网 pod 的运行状况
执行以下步骤以检查组件的运行状况。 如果集群组件不是最新的或未处于正常状态,那么可能会发生网络问题。
-
检查集群主节点和工作程序节点是否在受支持的版本上运行并且处于正常状态。 如果集群主节点或工作程序未运行受支持的版本,请 进行任何必要的更新 以使其运行受支持的版本。 如果任何组件的状态不是
Normal
或Ready
,请查看 群集主控健康状态、 群集状态、工作节点状态,或 故障排除Critical
或NotReady
工作节点的步骤,以了解更多信息。 请确保已解决任何相关问题,然后再继续。要检查集群主版本和运行状况:
ibmcloud oc cluster get -c <cluster-id>
要检查工作程序节点版本和运行状况:
ibmcloud oc workers -c <cluster-id>
-
对于每个工作程序节点,请验证 Calico 和集群 DNS pod 是否存在并以正常状态运行。
-
运行命令以获取集群 pod 的详细信息。
oc get pods -A -o wide | grep -e calico -e dns-default
-
在输出中,确保集群包含以下 pod。 确保每个 pod 的状态为
Running
,并且 pod 的重新启动次数不会过多。- 每个工作程序节点正好有一个
calico-node
pod。 - 每个集群至少有一个
calico-typha
pod。 较大的集群可能有多个集群。 - 每个集群正好有一个
calico-kube-controllers
pod。 - 每个节点一个
dns-default
pod。 但是,如果某些节点附加了标签,它们可能没有dns-default
pod。 这是正常现象,不会造成网络问题。
示例输出
NAMESPACE NAME READY STATUS RESTARTS AGE IP NODE NOMINATED READINESS GATES calico-system calico-kube-controllers-1a1a1a1 1/1 Running 0 37m 172.17.61.195 10.245.0.5 <none> <none> calico-system calico-node-1a1a1a1 1/1 Running 0 37m 10.245.0.5 10.245.0.5 <none> <none> calico-system calico-node-1a1a1a1 1/1 Running 0 37m 10.245.0.4 10.245.0.4 <none> <none> calico-system calico-typha-1a1a1a1 1/1 Running 0 37m 10.245.0.5 10.245.0.5 <none> <none> openshift-dns dns-default-1a1a1a1 2/2 Running 0 33m 172.17.36.144 10.245.0.4 <none> <none> openshift-dns dns-default-1a1a1a1 2/2 Running 0 33m 172.17.61.210 10.245.0.5 <none> <none>
- 每个工作程序节点正好有一个
-
如果列出的任何 pod 不存在或处于不正常状态,请浏览先前步骤中包含的集群和工作程序节点故障诊断文档。 在继续之前,请确保解决此步骤中 pod 的任何问题。
-
使用测试 pod 进行调试
要确定 pod 上网络问题的原因,可以在每个工作程序节点上创建测试 pod。 然后,您可以运行测试并观察 pod 中的联网活动,这可能会揭示问题的根源。
设置 pod
-
为测试 pod 创建新的特权名称空间。 创建新的名称空间可防止现有名称空间中的任何定制策略或配置影响测试 pod。 在此示例中,新名称空间称为
pod-network-test
。创建名称空间。
oc create ns pod-network-test
-
为新的特权命名空间添加标签。
oc label namespace pod-network-test --overwrite=true \ pod-security.kubernetes.io/enforce=privileged \ pod-security.kubernetes.io/enforce-version=latest \ pod-security.kubernetes.io/audit=privileged \ pod-security.kubernetes.io/audit-version=latest \ pod-security.kubernetes.io/warn=privileged \ pod-security.kubernetes.io/warn-version=latest \ security.openshift.io/scc.podSecurityLabelSync="false"
-
运行该命令以允许名称空间运行具有特权安全上下文的 pod。
oc adm policy add-scc-to-group privileged system:serviceaccounts:pod-network-test
-
创建并应用以下守护进程集,在每个节点上创建一个测试 pod。
apiVersion: apps/v1 kind: DaemonSet metadata: labels: name: webserver-test app: webserver-test name: webserver-test spec: selector: matchLabels: name: webserver-test template: metadata: labels: name: webserver-test app: webserver-test spec: tolerations: - operator: "Exists" containers: - name: webserver securityContext: privileged: true image: us.icr.io/armada-master/network-alpine:latest env: - name: ENABLE_ECHO_SERVER value: "true" - name: POD_NAME valueFrom: fieldRef: fieldPath: metadata.name restartPolicy: Always terminationGracePeriodSeconds: 1 ```
-
应用 daemonset 以在工作程序节点上部署测试 pod。
oc apply --namespace pod-network-test -f <daemonset-file>
- 列出命名空间中的所有 pod,验证 pod 是否成功启动。
oc get pods --namespace pod-network-test -o wide
在 pod 中运行测试
运行 curl
,ping
和 nc
命令以测试每个 pod 的网络连接,并运行 dig
命令以测试集群 DNS。 查看每个输出,然后参阅 确定问题 以查找结果可能意味着什么。
-
列出测试 pod 并记下每个 pod 的名称和 IP。
oc get pods --namespace pod-network-test -o wide
示例输出
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES webserver-test-1a1a1 1/1 Running 0 68s 172.17.36.169 10.245.0.4 <none> <none> webserver-test-1a1a1 1/1 Running 0 68s 172.17.61.240 10.245.0.5 <none> <none>
-
运行
exec
命令登录到一个Pod。kubectl exec -it --namespace pod-network-test <pod_name> -- sh
-
在 pod 上运行
curl
命令并记下输出。 请指定您未登录的播客的IP地址。 这将测试不同节点上的 pod 之间的网络连接。curl <pod_ip>:8080
成功输出的示例。
Hostname: webserver-test-t546j Pod Information: node name: env var NODE_NAME not set pod name: webserver-test-t546j pod namespace: env var POD_NAMESPACE not set pod IP: env var POD_IP not set Connection Information: remote address: 172.17.36.169 remote port: 56042 local address: 172.17.61.240 local port: 8080
-
在 pod 上运行
ping
命令并记下输出。 请使用exec
命令指定您未登录的播客的IP地址。 这将测试不同节点上的 pod 之间的网络连接。ping -c 5 <pod_ip>
成功输出的示例。
PING 172.30.248.201 (172.30.248.201) 56(84) bytes of data. 64 bytes from 172.30.248.201: icmp_seq=1 ttl=62 time=0.473 ms 64 bytes from 172.30.248.201: icmp_seq=2 ttl=62 time=0.449 ms 64 bytes from 172.30.248.201: icmp_seq=3 ttl=62 time=0.381 ms 64 bytes from 172.30.248.201: icmp_seq=4 ttl=62 time=0.438 ms 64 bytes from 172.30.248.201: icmp_seq=5 ttl=62 time=0.348 ms --- 172.30.248.201 ping statistics --- 5 packets transmitted, 5 received, 0% packet loss, time 4086ms rtt min/avg/max/mdev = 0.348/0.417/0.473/0.046 ms
-
在 pod 上运行
nc
命令并记下输出。 请使用exec
命令指定您未登录的播客的IP地址。 这将测试不同节点上的 pod 之间的网络连接。nc -vzw 5 <pod_ip> 8080
成功输出的示例。
nc -vzw 5 172.17.61.240 8080 172.17.61.240 (172.17.61.240:8080) open
-
运行
dig
命令以测试 DNS。dig +short kubernetes.default.svc.cluster.local
示例输出
172.21.0.1
dig +short ibm.com
示例输出
23.50.74.64
-
运行
curl
命令,测试与服务器的完整TCP或 HTTPS 连接。 此示例通过检索集群的版本信息来测试 pod 与集群主节点之间的连接。 成功检索集群版本指示正常连接。curl -k https://kubernetes.default.svc.cluster.local/version
示例输出
{ "major": "1", "minor": "25", "gitVersion": "v1.25.14+bcb9a60", "gitCommit": "3bdfba0be09da2bfdef3b63e421e6a023bbb08e6", "gitTreeState": "clean", "buildDate": "2023-10-30T21:33:07Z", "goVersion": "go1.19.13 X:strictfipsruntime", "compiler": "gc", "platform": "linux/amd64" }
-
退出 pod。
exit
-
对其余 Pod 重复先前步骤。
确定问题
查看先前部分的输出,以帮助查找 pod 联网问题的原因。 本部分列出了可从先前部分中识别的一些常见原因。
-
如果这些命令在测试 pod 上正常运行,但在缺省名称空间中的应用程序 pod 中仍存在联网问题,那么可能存在专门与应用程序相关的问题。
- 您可能具有限制网络流量的 Calico 或 Kubernetes 网络安全策略。 如果将网络策略应用于 pod,那么 将删除该策略未特别允许的所有流量。 有关联网策略的更多信息,请参阅 Kubernetes 文档。
- 如果您正在使用 Istio 或 Red Hat OpenShift Service Mesh,那么可能存在用于删除或阻止 pod 之间的流量的服务配置问题。 有关更多信息,请参阅 Istio 和 Red Hat OpenShift Service Mesh的故障诊断文档。
- 此问题可能与应用程序中的错误相关,而不是与集群相关,并且可能需要您自己的独立故障诊断。
-
如果针对某些 pod 的
curl
,ping
或nc
命令失败,请标识这些 pod 所在的工作程序节点。 如果问题仅存在于某些工作程序节点上,请 更换这些工作程序节点 或查看有关 工作程序节点故障诊断 的其他信息。 -
如果从
dig
命令进行的 DNS 查找失败,请参阅 Red Hat DNS 故障诊断信息。
如果您仍无法解决 pod 联网问题,请 打开支持案例,并包含问题的详细描述,您尝试解决该问题的方式,您运行的测试类型以及 pod 和工作程序节点的 相关日志。 有关打开支持案例以及要包含哪些信息的更多信息,请参阅 常规调试指南。