前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【重识云原生】第六章容器6.3.8节——kube-proxy

【重识云原生】第六章容器6.3.8节——kube-proxy

作者头像
江中散人_Jun
发布2022-10-04 19:57:13
5630
发布2022-10-04 19:57:13
举报

1 kube-proxy简述

1.1 kube-proxy简介

        kube-proxy是Kubernetes的核心组件,部署在每个Node节点上,它是实现Kubernetes Service的通信与负载均衡机制的重要组件;kube-proxy负责为Pod创建代理服务,从apiserver获取所有server信息,并根据server信息创建代理服务,实现server到Pod的请求路由和转发,从而实现K8s层级的虚拟转发网络。

        在k8s中,提供相同服务的一组pod可以抽象成一个service,通过service提供的统一入口对外提供服务,每个service都有一个虚拟IP地址(VIP)和端口号供客户端访问。kube-proxy存在于各个node节点上,主要用于Service功能的实现,具体来说,就是实现集群内的客户端pod访问service,或者是集群外的主机通过NodePort等方式访问service。在当前版本的k8s中,kube-proxy默认使用的是iptables模式,通过各个node节点上的iptables规则来实现service的负载均衡,但是随着service数量的增大,iptables模式由于线性查找匹配、全量更新等特点,其性能会显著下降。从k8s的1.8版本开始,kube-proxy引入了IPVS模式,IPVS模式与iptables同样基于Netfilter,但是采用的hash表,因此当service数量达到一定规模时,hash查表的速度优势就会显现出来,从而提高service的服务性能。

1.2 kube-proxy与Service关系

        kube-proxy负责为Service提供cluster内部的服务发现和负载均衡,它运行在每个Node计算节点上,负责Pod网络代理, 它会定时从etcd服务获取到service信息来做相应的策略,维护网络规则和四层负载均衡工作。在K8s集群中微服务的负载均衡是由Kube-proxy实现的,它是K8s集群内部的负载均衡器,也是一个分布式代理服务器,在K8s的每个节点上都有一个,这一设计体现了它的伸缩性优势,需要访问服务的节点越多,提供负载均衡能力的Kube-proxy就越多,高可用节点也随之增多。

        service是一组pod的服务抽象,相当于一组pod的LB,负责将请求分发给对应的pod。service会为这个LB提供一个IP,一般称为cluster IP。kube-proxy的作用主要是负责service的实现,具体来说,就是实现了内部从pod到service和外部的从node port向service的访问。

        简单来说: 

  • kube-proxy其实就是管理service的访问入口,包括集群内Pod到Service的访问和集群外访问service。
  • kube-proxy管理sevice的Endpoints,该service对外暴露一个Virtual IP,也成为Cluster IP,集群内通过访问这个Cluster IP:Port就能访问到集群内对应的serivce下的Pod。
  • service是通过Selector选择的一组Pods的服务抽象,其实就是一个微服务,提供了服务的LB和反向代理的能力,而kube-proxy的主要作用就是负责service的实现。
  • service另外一个重要作用是,一个服务后端的Pods可能会随着生存灭亡而发生IP的改变,service的出现,给服务提供了一个固定的IP,而无视后端Endpoint的变化。

        举个例子,比如现在有podA,podB,podC和serviceAB。serviceAB是podA,podB的服务抽象(service)。那么kube-proxy的作用就是可以将pod(不管是podA,podB或者podC)向serviceAB的请求,进行转发到service所代表的一个具体pod(podA或者podB)上。请求的分配方法一是采用轮询方法进行分配。另外,kubernetes还提供了一种在node节点上暴露一个端口,从而提供从外部访问service的方式。比如这里使用这样的一个manifest来创建service:

代码语言:javascript
复制
apiVersion: v1
kind: Service
metadata: 
  labels:  
    name: mysql   
    role: service  
  name: mysql-service
spec:
  ports:  
    - port: 3306  
      targetPort: 3306
      nodePort: 30964  
  type: NodePort  
  selector:  
    mysql-service: "true"

        上面配置的含义是在node上暴露出30964端口。当访问node上的30964端口时,其请求会转发到service对应的cluster IP的3306端口,并进一步转发到pod的3306端口。

        Service, Endpoints与Pod的关系:

        Kube-proxy进程获取每个Service的Endpoints,实现Service的负载均衡功能。

        Service的负载均衡转发规则:

        访问Service的请求,不论是Cluster IP+TargetPort的方式;还是用Node节点IP+NodePort的方式,都被Node节点的Iptables规则重定向到Kube-proxy监听Service服务代理端口。kube-proxy接收到Service的访问请求后,根据负载策略,转发到后端的Pod。

2 工作原理

2.1  kubernetes服务发现

        Kubernetes提供了两种方式进行服务发现,即环境变量和DNS, 简单说明如下:

1)  环境变量

        当你创建一个Pod的时候,kubelet会在该Pod中注入集群内所有Service的相关环境变量。需要注意: 要想一个Pod中注入某个Service的环境变量,则必须Service要先比该Pod创建。这一点,几乎使得这种方式进行服务发现不可用。比如,一个ServiceName为redis-master的Service,对应的ClusterIP:Port为172.16.50.11:6379,则其对应的环境变量为:

代码语言:javascript
复制
REDIS_MASTER_SERVICE_HOST=172.16.50.11
REDIS_MASTER_SERVICE_PORT=6379
REDIS_MASTER_PORT=tcp://172.16.50.11:6379
REDIS_MASTER_PORT_6379_TCP=tcp://172.16.50.11:6379
REDIS_MASTER_PORT_6379_TCP_PROTO=tcp
REDIS_MASTER_PORT_6379_TCP_PORT=6379
REDIS_MASTER_PORT_6379_TCP_ADDR=172.16.50.11

2)  DNS

        这是k8s官方强烈推荐的方式!!!  可以通过cluster add-on方式轻松的创建KubeDNS来对集群内的Service进行服务发现。

2.2 kubernetes发布(暴露)服务

        kubernetes原生的,一个Service的ServiceType决定了其发布服务的方式:

  • ClusterIP:这是k8s默认的ServiceType。通过集群内的ClusterIP在内部发布服务;
  • NodePort:这种方式是常用的,用来对集群外暴露Service,你可以通过访问集群内的每个NodeIP:NodePort的方式,访问到对应Service后端的Endpoint。
  • LoadBalancer: 这也是用来对集群外暴露服务的,不同的是这需要Cloud Provider的支持,比如AWS等。
  • ExternalName:这个也是在集群内发布服务用的,需要借助KubeDNS(version >= 1.7)的支持,就是用KubeDNS将该service和ExternalName做一个Map,KubeDNS返回一个CNAME记录。

2.3 kube-proxy三种代理模式

        kube-proxy当前实现了三种代理模式:userspace, iptables, ipvs。其中userspace mode是v1.0及之前版本的默认模式,从v1.1版本中开始增加了iptables mode,在v1.2版本中正式替代userspace模式成为默认模式。也就是说kubernetes在v1.2版本之前是默认模式, v1.2版本之后默认模式是iptables。

2.3.1 UserSpace

        UserSpace 是让 Kube-Proxy 在用户空间监听一个端口,所有的 Service 都转发到这个端口,然后 Kube-Proxy 在内部应用层对其进行转发。

        Kube-Proxy 会为每个 Service 随机监听一个端口 (Proxy Port),并增加一条 IPtables 规则。

        从客户端到 ClusterIP:Port 的报文都会被重定向到 Proxy Port,Kube-Proxy 收到报文后,通过 Round Robin (轮询) 或者 Session Affinity(会话亲和力,即同一 Client IP 都走同一链路给同一 Pod 服务)分发给对应的 Pod。

        这种方式最大的缺点显然就是 UserSpace 会造成所有报文都走一遍用户态,造成整体性能下降,这种方在 Kubernetes 1.2 以后已经不再使用了。

2.3.2 Iptables

        IPtables 方式完全由 IPtables 来实现,这种方式直接使用 IPtables 来做用户态入口,而真正提供服务的是内核的 Netilter。

        Kube-Proxy 只作为 Controller,这也是目前默认的方式。

        Kube-Proxy 的 IPtables 方式也是支持 Round Robin 和 Session Affinity 特性。

        Kube-Proxy 监听 Kubernetes Master 增加和删除 Service 以及 Endpoint 的消息。对于每一个 Service,Kube Proxy 创建相应的 IPtables 规则,并将发送到 Service Cluster IP 的流量转发到 Service 后端提供服务的 Pod 的相应端口上。

注:         虽然可以通过 Service 的 Cluster IP 和服务端口访问到后端 Pod 提供的服务,但该 Cluster IP 是 Ping 不通的。其原因是 Cluster IP 只是 IPtables 中的规则,并不对应到一个任何网络设备。但IPVS 模式的 Cluster IP 是可以 Ping 通的。

2.3.3 IPVS

        Kubernetes 从 1.8 开始增加了 IPVS 支持,IPVS 相对 IPtables 效率会更高一些。

        使用 IPVS 模式需要在运行 Kube-Proxy 的节点上安装 ipvsadm、ipset 工具包和加载 ip_vs 内核模块。

        当 Kube-Proxy 以 IPVS 代理模式启动时,Kube-Proxy 将验证节点上是否安装了 IPVS 模块,如果未安装,则 Kube-Proxy 将回退到 IPtables 代理模式。

        这种模式,Kube-Proxy 会监视 Kubernetes Service 对象 和 Endpoints,调用 Netlink 接口以相应地创建 IPVS 规则并定期与 Kubernetes Service 对象 和 Endpoints 对象同步 IPVS 规则,以确保 IPVS 状态与期望一致。访问服务时,流量将被重定向到其中一个后端 Pod。

        与 IPtables 类似,IPVS 基于 Netfilter 的 Hook 功能,但使用哈希表作为底层数据结构并在内核空间中工作。这意味着 IPVS 可以更快地重定向流量,并且在同步代理规则时具有更好的性能。此外,IPVS 为负载均衡算法提供了更多选项,例如:rr (轮询调度)、lc (最小连接数)、dh (目标哈希)、sh (源哈希)、sed (最短期望延迟)、nq(不排队调度)等。

注:         IPVS 是 LVS 项目的一部分,是一款运行在 Linux Kernel 当中的 4 层负载均衡器,性能异常优秀。使用调优后的内核,可以轻松处理每秒 10 万次以上的转发请求。

        目前在中大型互联网项目中,IPVS 被广泛的用于承接网站入口处的流量。

参考链接

kube-proxy · Kubernetes指南

kubernetes核心组件kube-proxy - 努力乄小白 - 博客园

kube-proxy三种工作模式

kube-proxy 详解_IT小菜鸟@的博客-CSDN博客_kube-proxy

kubernetes网络 - kube-proxy详解 - 刘达的博客

Kube-Proxy简述

解析从外部访问Kubernetes集群中应用的几种方法_Linux云服务器_云网牛站

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2022-09-24,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 1 kube-proxy简述
    • 1.1 kube-proxy简介
      • 1.2 kube-proxy与Service关系
      • 2 工作原理
        • 2.1  kubernetes服务发现
          • 2.2 kubernetes发布(暴露)服务
            • 2.3 kube-proxy三种代理模式
              • 2.3.1 UserSpace
              • 2.3.2 Iptables
              • 2.3.3 IPVS
          • 参考链接
          相关产品与服务
          负载均衡
          负载均衡(Cloud Load Balancer,CLB)提供安全快捷的流量分发服务,访问流量经由 CLB 可以自动分配到云中的多台后端服务器上,扩展系统的服务能力并消除单点故障。负载均衡支持亿级连接和千万级并发,可轻松应对大流量访问,满足业务需求。
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档