k8s网络系列学习笔记之一-----Service简介

从今天开始,打算整理一下k8s网络相关的知识和内容,这块的内容较多,将分多个章节进行学习、记录和分析,有纰漏的地方还希望读者指正。本文不会逐个介绍Service的基本功能,这里主要介绍一些跟网络相关的内容关心的内容。

前言

在早期运维时代,我们都是在物理机上部署程序,一般会选择一台主机,把要部署的程序安装到这台主机上,但是一般部署到这台机器后,我们一般认为这个进程存在与这台机器上这个状态是恒定的。当然这个进程有可能会挂掉,机器也有可能会重启,我们需要能够自动拉起相应的进程,拉起后它仍然在这台机器上。但是在程序挂或者机器重启的过程中,我们访问这个进程就会出错,会造成一段时间的服务不可用。
在微服务架构中,我们一般会把服务注册到一个注册中心,如果服务挂了,就会从注册中心摘掉。所以一般会通过部署多个服务进程,来保证服务整体的可用性,实现不间断的服务能力。

Pod简介

Kubernetes Pod是Kubernetes的一个最小部署单元,它由一个或者多个容器组成(这里一般指Docker容器),这里我们在物理机时代部署一个进程类似,但是在Kubernetes中,一般认为Pod是一个临时的实体,而不是永久性实体,Pod是有生命周期的,它们可以被创建,也可以被销毁,是一个临时实体,不是一个持久性的实体,每个Pod成功部署后,会有一个唯一的UID标识,一旦销毁后(不管什么原因),它就不能被恢复了。

所以一般我们会通过Deployment或者ReplicationController来管理Pod,实现Pod动态的创建和销毁,当一个Pod被销毁或者Pod所在的主机宕机之后,会自动重新调度创建出一个Pod,这个Pod与之前的Pod的名字可以相同,但是UID是不同的,而且它们的IP也会不同,那么当通过Deployment或者ReplicationController管理的一组Pod向其他的Pod提供服务时,如果保留自己呢?

当然这里也可以基于前面提到的微服务架构体系来实现,但是Kubernetes有自己的一套解决方案,那就是通过Service来提供统一的访问入口。

Service简介

Kubernetes Service与微服务类似,它提供了一套一组Pod的抽象,可以让其他的Pod(或者物理进程)访问到底层的一组Pod,实现负载均衡和高可用服务能力。

Kubernetes Service通常通过Label Selector来实现与底层的Pod的关联,并且会进行实时的关联。Service会基于Endpoints API实时检测到底层Pod的变化,并进行更新,与微服务的原理类似,唯一不同的是访问的方式不太一致。

  • 一般的微服务需要实现一个富SDK,在SDK中实现对多个backend访问的高可用和负载均衡的能力,所以微服务体系在开发层面来讲,要做到语言无关性需要额外做出很多工作;
  • k8s service一般提供了基于VIP代理的方式访问Service,首先访问到vip和对应的端口,再由Service重定向到管理的Pod中,保持了API的一致性;

kube-proxy代理模式

K8S Service的这种服务能力是在kube-proxy中的代理来实现的,kube-proxy在 Kubernetes v1.0 版本,代理完全在 userspace,在 Kubernetes v1.1 版本,新增了 iptables 代理,但并不是默认的运行模式。 从 Kubernetes v1.2 起,默认就是 iptables 代理,发展到v1.8版本开始引入ipvs模式,并在Kubernetes 1.11进入GA,在Kubernetes1.12成为kube-proxy的默认代理模式。

  • userspace
    这种模式,kube-proxy 会监视 Kubernetes master 对 Service 对象和 Endpoints 对象的添加和移除。 对每个 Service,它会在本地 Node 上打开一个端口(随机选择)。 任何连接到“代理端口”的请求,都会被代理到 Service 的backend Pods 中的某个上面(如 Endpoints 所报告的一样)。 使用哪个 backend Pod,是基于 Service 的 SessionAffinity 来确定的。 最后,它安装 iptables 规则,捕获到达该 Service 的 clusterIP(是虚拟 IP)和 Port 的请求,并重定向到代理端口,代理端口再代理请求到 backend Pod。

网络返回的结果是,任何到达 Service 的 IP:Port 的请求,都会被代理到一个合适的 backend,不需要客户端知道关于 Kubernetes、Service、或 Pod 的任何信息。

默认的策略是,通过 round-robin 算法来选择 backend Pod。 实现基于客户端 IP 的会话亲和性,可以通过设置 service.spec.sessionAffinity 的值为 "ClientIP" (默认值为 "None")。

services-userspace-overview.jpg
  • iptables
    这种模式,kube-proxy 会监视 Kubernetes master 对 Service 对象和 Endpoints 对象的添加和移除。 对每个 Service,它会安装 iptables 规则,从而捕获到达该 ServiceclusterIP(虚拟 IP)和端口的请求,进而将请求重定向到 Service 的一组 backend 中的某个上面。 对于每个 Endpoints 对象,它也会安装 iptables 规则,这个规则会选择一个 backend Pod

默认的策略是,随机选择一个 backend。 实现基于客户端 IP 的会话亲和性,可以将 service.spec.sessionAffinity 的值设置为 "ClientIP" (默认值为 "None")。

和 userspace 代理类似,网络返回的结果是,任何到达 Service 的 IP:Port 的请求,都会被代理到一个合适的 backend,不需要客户端知道关于 Kubernetes、Service、或 Pod 的任何信息。 这应该比 userspace 代理更快、更可靠。然而,不像 userspace 代理,如果初始选择的 Pod 没有响应,iptables 代理不能自动地重试另一个 Pod,所以它需要依赖 readiness probes

services-iptables-overview.jpg
  • ipvs
    这种模式,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模式假定在运行kube-proxy之前在节点上都已经安装了IPVS内核模块。当kube-proxy以ipvs代理模式启动时,kube-proxy将验证节点上是否安装了IPVS模块,如果未安装,则kube-proxy将回退到iptables代理模式。

service-ipvs-overview.png

K8S中的Pod信息

在K8s中有几个不同的port申明。

  • 在Pod中就会有定义
    pod.spec.containers[].ports,这个定义描述了pods的容器暴漏的端口,其实即使我们不在Pod中申明的暴漏的端口号,你的容器依然后占用相应的端口号,这里的端口号的申明另有意义。
  • 在Service中的port、targetPort、nodePort
    service中通过service.spec.ports列表配置了一个服务的端口以及代理的Pod的目的端口。
    NodePort可以让我们可以通过集群外访问到主机IP和对应的端口号,也可以在集群内访问到服务的ClusterIP和端口号,最终被Pod的targetPort接受。

NodePort:该字段让服务在集群外部可见,通过暴漏节点上IP和定义的NodePort,服务必须是NodePort类型;

Port:通过指定的端口在集群内部暴漏服务的端口号;

targetPod:描述了Service映射到Pod的端口号,缺省不指定这个字段,那么它会与Port字段相同,当Port与targetPod不同时可以在这里指定。与此同时,这个字段还提供了更高的灵活性,它是一个字符串类型的,我们除了指定一个端口号以外,还可以指定前面我们提到的Pod申明暴漏的端口的名字,通过这种方式,我们可以不要求代理的Pod侦听的相同的端口号。譬如如果我们有两个版本的程序发布在K8S中,它们可以有不同的端口号,而对外仍然保持统一的服务,不影响外部应用的访问。

总结

本次希望逐步分析K8S网络相关的专题,所以没有完整介绍Service的概念,主要介绍了Service网络相同的基本知识,并把它与微服务进行了简单的对比。

从对比中,我们可以看出Service的独特之处在于它是基于代理的模式,实现了负载均衡和反向代理功能,这种服务的好处在于整个服务对外只需要暴漏API,这样不需要考虑高可用性、负载均衡等,可以通过自己熟悉的任何语言来访问服务。ServiceMesh在这方面做的更彻底,对外也是只暴漏原生的API,而把微服务的几乎所有特性,包括路由格则、服务发现和负载均衡、断路器、超时重试、错误注入、安全等都封装在底层。

后续的几个章节,会接下来会逐步记录学习Service的相关的笔记内容。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 203,937评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,503评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,712评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,668评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,677评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,601评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,975评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,637评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,881评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,621评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,710评论 1 329
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,387评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,971评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,947评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,189评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,805评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,449评论 2 342

推荐阅读更多精彩内容