Pod 到 Pod 通信不适用于 k8s 中的 Python 套接字

Pod-to-pod communication doens't work with Python socket in k8s

问题

在我们的项目中,我们需要两个 pods 作为服务器-客户端通过 Python socket 库进行通信。这两个容器都是使用 docker build 在本地构建的,通过 yaml 文件上的 imagePullPolicy: IfNotPresent 和 k8s 集群的同一节点上的 运行 在本地拉取(我是 运行ning kubernetes vanilla ,如果这很重要的话)。

当我们

时,沟通效果很好

服务端和客户端都部署在K8s中时通信失败。 kubectl logs client -f returns :

Traceback (most recent call last):
  File "client.py", line 7, in <module>
    client_socket.connect((IP_Server,PORT_Server))
TimeoutError: [Errno 110] Connection timed out

我怀疑客户端脚本在集群上部署时发出的请求有问题,但我找不到问题所在。

代码

server.py

import socket

IP = "0.0.0.0"
PORT = 1234

server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
server_socket.bind((IP, PORT))
server_socket.listen()

...

server.yaml

apiVersion: v1
kind: Service
metadata:
  name: server
  labels:
    app: server
spec:
  ports:
    - port: 1234
      targetPort: 1234
      protocol: TCP
  selector:
    app: server
---
apiVersion: v1
kind: Pod
metadata:
  name: server
  labels:
    app: server
spec:
  containers:
  - name: server
    image: server:latest
    imagePullPolicy: IfNotPresent
    ports:
    - containerPort: 1234

client.py

import socket

IP_Server = # the IP of the server service, obtained from "kubectl get svc" 
PORT_Server = 1234

client_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
client_socket.connect((IP_Server,PORT_Server)) # fails here

...

client.yaml

apiVersion: v1
kind: Pod
metadata:
  name: client
  labels:
    app: client
spec:
  containers:
  - name: client
    image: client:latest
    imagePullPolicy: IfNotPresent

默认 设置中 - 不应该有任何东西阻止您在 2 pods 之间进行连接。但是,您不应依赖 IP 地址在集群内进行通信。尝试使用服务名称:

$ kubectl get svc
NAME         TYPE        CLUSTER-IP    EXTERNAL-IP   PORT(S)   AGE
kubernetes   ClusterIP   10.96.0.1     <none>        443/TCP   10m
server       ClusterIP   10.98.48.92   <none>        80/TCP    9m39s

server 通常应该对同一命名空间内的所有 pods 运行 可用。

您解析服务器 IP 地址的方式可能有问题,但服务器创建的“服务”应该可以通过 DNS 隐式访问(例如 server:1234),如here,所以也许您可以改用它?

万一以后有人来这里,我找到了一个对我有用的解决方案,方法是执行

iptables -P INPUT ACCEPT
iptables -P FORWARD ACCEPT
iptables -P OUTPUT ACCEPT
iptables -F

然后删除所有 coredns pods.

参考:https://github.com/kubernetes/kubernetes/issues/86762#issuecomment-836338017