kubernets nodeport 无法访问

Environment

Os: centos7.1
Kubelet: 1.6.7
Docker: 17.06-ce
Calico: 2.3

K8s Cluster: master, node-1, node-2

Problem

现有 service A, 为了能使外部访问,故将 service type 设为NodePort。端口为 31246
A 所对应的 pod 运行在 node-1 上。

经过测试发现,外部访问 master:31246node-2:31246 时均出现失败,只有通过 node-1:31246 才可正常访问。

Reason

为了安全起见, docker 在 1.13 版本之后,将系统iptables 中 FORWARD 链的默认策略设置为 DROP,并为连接到 docker0 网桥的容器添加了放行规则。这里引用 moby issue#14041 中的描述:

When docker starts, it enables net.ipv4.ip_forward without changing the iptables FORWARD chain default policy to DROP. This means that another machine on the same network as the docker host can add a route to their routing table, and directly address any containers running on that docker host.

For example, if the docker0 subnet is 172.17.0.0/16 (the default subnet), and the docker host’s IP address is 192.168.0.10, from another host on the network run:

   $ ip route add 172.17.0.0/16 via 192.168.0.10
$ nmap 172.17.0.0/16

The above will scan for containers running on the host, and report IP addresses & running services found.

To fix this, docker needs to set the FORWARD policy to DROP when it enables the net.ipv4.ip_forward sysctl parameter.

kubernetes 使用的 cni 插件会因此受影响(cni并不会在 FORWARD 链中生成相应规则),由此导致除 pod 所在 host 以外节点无法转发报文而访问失败。

Solution

如果对安全要求较低,可将 FORWARD 链的默认规则设为 ACCEPT

iptables -P FORWARD ACCEPT

其它方法可参考:

kubernetes issues#40182

你可能感兴趣的:(kubernetes)