kubernetes service原理剖析

1.相关概念

1.1 Port相关概念

  • port
    这里的port表示:service暴露在cluster ip上的端口,clusterIP:port 是提供给集群内部客户访问service的入口。

  • nodePort
    nodeIP:nodePort 是提供给集群外部客户访问service的入口。

  • targetPort
    targetPort很好理解,targetPort是pod上的端口,从port和nodePort上到来的数据最终经过kube-proxy流入到后端pod的targetPort上进入容器。

总的来说,port和nodePort都是service的端口,前者暴露给集群内客户访问服务,后者暴露给集群外客户访问服务。从这两个端口到来的数据都需要经过反向代理kube-proxy流入后端pod的targetPod,从而到达pod上的容器内。

1.2 ip相关概念

  • Pod IP
    pod的ip,每个Pod启动时,会自动创建一个镜像为gcr.io/google_containers/pause:0.8.0的容器,容器内部与外部的通信经由此容器代理,该容器的IP也可以称为Pod IP。

  • Cluster IP
    Pod IP 地址是实际存在于某个网卡(可以是虚拟设备)上的,但Service Cluster IP就不一样了,没有网络设备为这个地址负责。它是由kube-proxy使用Iptables规则重新定向到其本地端口,再均衡到后端Pod的。当proxy发现一个新的service后,它会在本地节点打开一个任意端口,建相应的iptables规则,重定向服务的IP和port到这个新建的端口,开始接受到达这个服务的连接。

  • 外部IP
    nodeIP,Service对象在Cluster IP range池中分配到的IP只能在内部访问,如果服务作为一个应用程序内部的层次,还是很合适的。如果这个Service作为前端服务,准备为集群外的客户提供业务,我们就需要给这个服务提供公共IP了。指定service的spec.type=NodePort,这个类型的service,系统会给它在集群的各个代理节点上分配一个节点级别的端口,能访问到代理节点的客户端都能访问这个端口,从而访问到服务。

2.kubernetes的kube-proxy的转发规则分析

2.1概要

当service有了port和nodePort之后,就可以对内/外提供服务。那么其具体是通过什么原理来实现的呢?奥妙就在kube-proxy在本地node上创建的iptables规则。kube-proxy是kubernetes中设置转发规则的组件,通过iptables修改报文的流向。

本文所用的kube-proxy版本如下:
这里写图片描述

五个检查点:
这里写图片描述

这里写图片描述

通过“iptables -L -t [iptables表名]”可以看到,kube-proxy只修改了filter和nat表。

2.2 filter表

filter表中Chain:
这里写图片描述

由上图可以看到:

  • kube-proxy只设置了filter表中INPUT chain和OUTPUT chain,增加了KUBE-FIREWALL和KUBE-SERVICES两个规则链。
  • 所有的出报文都要经过KUBE-SERVICES,如果一个Service没有对应的endpoint,则拒绝将报文发出(如图中KUBE-SERVICES链中的那两行所示)
  • 注意在KUBE-FIREWALL中,所有标记了0x8000的包都会被丢弃,标记动作可以发生在其它的表中。

2.3 nat表

nat表中设置的规则比较多(先截取一部分看):
这里写图片描述
先无视其中的calico,单看kube-proxy,由上图可以看到:

  • kube-proxy设置了nat表中PREROUTING链、OUTPUT链、POSTROUTING 链,增加了KUBE-MARKDROP链和KUBE-MARK-MASQ、KUBE-NODEPORTS、KUBE-POSTROUTING、多个KUBE-SEP-XXX链、KUBE-SERVICES、多个KUBE-SVC-XXX链。
  • 在PREROUTING阶段,将所有报文转发到KUBE-SERVICES
  • 在OUTPUT阶段,将所有报文转发到KUBE-SERVICES
  • 在POSTROUTING阶段,将所有报文转发到KUBE-POSTROUTING

先来看KUBE-SERVICES链:
这里写图片描述

可以看到,所有对service的clusterIP的访问都会先转到KUBE-MARK-MASQ链,然后再转到KUBE-SVC-XXX链。

(1)看一下KUBE-MARK-MASQ链做了什么:
这里写图片描述
即,在KUBE-MARK-MASQ链中为包set mark 0x4000, 有此标记的数据包会在KUBE-POSTROUTING链中统一做MASQUERADE
(2)接着包走到KUBE-SVC-XXX链,看一下在KUBE-SVC-XXX链中做了什么:
这里写图片描述
可以看到,每一个SERVICE,假如有多后端endpoint的话,按照一定规则(比如random)将报文提交到了某个的KUBE-SEP-XXX,KUBE-SEP-XXX链做了什么:
这里写图片描述
首先是又走了一下KUBE-MARK-MASQ链set mark 0x4000(之后在KUBE-POSTROUTING链中会做SNAT),最后在KUBE-SEP-XX中完整了最终的DNAT,将目的地址转换成了POD的IP和端口。

参考

1.http://blog.csdn.net/xinghun_4/article/details/50492041
2.http://blog.csdn.net/liukuan73/article/details/54773579

猜你喜欢

转载自blog.csdn.net/liukuan73/article/details/78921456