Kubernetes(K8s)_09_Kubernetes架构
- Kubernetes架构
- 控制平面组件
- API Server
- Etcd
- Scheduler
- Controller
- Node节点组件
- Kubelet
- kube-proxy
- 附加组件
- Pod网络
- Pod通信
Kubernetes架构
Kubernetes架构:去中心化架构,由多个组件构成
1)Kubernetes架构主要由控制平面组件和Node节点组件构成;
2)基于声明性模型运行并实现(不会线性处理任务);
3)Kubernetes架构也由部分附加组件构成;
//如:Kubernetes DNS服务器、Ingress控制器、Heapster和容器网络接口插件等
//控制平面组件和Node节点组件中均包含容器引擎组件(如:Docker和rkt等)
如:控制平面组件和Node节点组件构成Kubernetes
1)组件均为单独进程运行,且均作为Pod来运行(Kubelet除外);
2)组件间只能通过API Server通信(不可直接通信);
3)API Server和组件间的连接大部分是由组件发起的;
控制平面组件
控制平面组件为以下4种(运行在Master节点):
组件名 | 说明 |
API Server (API服务器) | 管理Kubernetes集群的入口 |
Ectd (分布式持久化存储) | 存储Kubernets集群的核心数据 |
Scheduler (调度器) | 调度Pod与各个节点进行绑定 |
Controller (控制器) | 保证各个资源对象达到期望状态 |
1)Master节点上的组件可部署在多台服务器上,且每个组件可有多个;
2)多个Etcd和API Server可同时并行工作;
3)多个Scheduler和Contoler中只有一个在工作,其他处于待命模式;
如:三Master节点的高可用集群
1)通过负载均衡器确保只会连接到健康状态的API Server
2)API Server是无状态的,可同时运行多个;
API Server
API Server:各个组件的通信渠道
1)以RESTful API的形式提供针对集群状态的CURD,并将其存入Etcd;
1)各个组件均通过API Server进行交流,而数据的来源是Etcd;
2)API Server暴露ComponentStatus的API资源;
//显示控制平面组件的状态命令:kubectl get componentstatuses
如:通过JSON文件创建资源的流程
1)API Server需认证发送请求的用户(API Server中一个或多个认证插件完成)
//API Server在有限时间内会轮流调用认证插件,确定该请求的发送者
2)API Server判断认证后的用户是否可资源执行操作
//由API Server中一个或多个认证插件完成
准入控制插件:验证创建、修改和删资源的请求
1)准入控制插件可修改资源信息;
//如:初始化资源定义中漏配的字段,准入控制插件会填写默认值(也可重写)
2)准入控制插件主要为以下4种:
准入控制插件名 | 说明 |
AlwaysPullImages | 强制每次部署Pod时需拉取镜像 (重写Pod的imagePullPolicy为Always) |
ServiceAccount | 未明确定义服务账户的使用的默认账户 |
NamespaceLifecycle | 防止在命名空间中创建正在被删除的资源 (或在不存在的命名空间中创建资源) |
ResourceQuota | 确保指定命名空间中的Pod 只能使用该命名空间已分配的资源 |
DefaulTolerationSeconds | 检测Pod是否设置污点宽容期 若无,则为其设置默认宽容期 |
3)请求需通过所有的准入控制插件的验证才可被执行;
4)当请求通过验证后API Server会将该请求存储到Etcd,并返回响应;
API Server接受到资源变更的请求时,会执行以下流程:
1)启动Scheduler和Controller或其他组件,去监控已部署的资源变更;
2)组件根据集群元数据的变化执行对应操作;
//kubectl工具也可监听资源变更
如:API Server接受资源变更请求的流程
Etcd
Etcd:高可用的分布式持久存储的键值(Key-Value)数据库
1)各个组件通过API Server间接地读取/写入数据到Etcd;
2)Kubernetes中仅由Etcd存储集群状态和元数据;
Kubernetes的数据存储于Etcd的/registry
1)所有的资源类型均代表一个子目录;
2)资源类型子目录下存储各个命名空间下对应类型的资源;
3)资源中存储对应资源的JSON定义格式;
//API Server将资源的完整JSON形式存储在Etcd中
多个Ectd通过RAFT一致性算法保持一致
1)RAFT算法要求集群大部分节点参与才能修改状态(少数服从多数);
2)Etcd通常部署为奇数个(建议5或7个节点,避免脑裂和过度选举);
3)每个连接到Etcd集群的API Server会得到当前Etcd状态(或之前的状态);
Scheduler
Scheduler(调度器):调度Pod到指定Node节点上运行
1)Scheduler通过预测函数检测Node节点是否可用于分配;
2)Scheduler再通过调度算法决定Pod如何分配给各个Node节点;
Scheduler调度Pod的流程:
1)Scheduler通过API Server更新Pod的定义;
2)API Server通过Node节点的Kubelet(该Pod已被调度);
3)目标节点的Kubelet发现Pod被调度到本节点,则会创建并运行Pod的容器;
如:Scheduler调度Pod的流程
默认调度算法:
1)过滤所有Node节点,得出可用于调度Pod的可用节点列表;
2)对可用节点列表进行排序,找出最优节点;
//若多个节点均为最优,则循环分配
预测函数需检测以下要求:
1)Node节点是否能满足Pod对系统资源的需求;
2)Node节点的标签是否符合Pod的节点选择器;
3)Pod需绑定指定的主机端口在Node节点是否已被占用;
5)Node节点是否能满足Pod定义中要求的卷;
4)Pod是否能够容忍Node节点的污点;
//Node节点需满足以上所有要求,才可被记为可用节点
Kubernetes集群中运行多个Scheduler
1)Pod定义中通过schedulerName字段,可指定Scheduler来调度该Pod;
2)未指定的则由默认Scheduler调度(schedulerNamer被设置为default-scheduler);
Controller
Controller(控制器):确保集群的真实状态往API Server定义的期望状态收敛
1)Controller实现具体的资源部署(活跃的Kubernetes组件);
2)Controller之间不会直接通信,且每个Controller均连接到API Server;
3)每个Controller均有一个构造器,内部会创建一个Informer(监听器);
4)所有的Controller均通过API Server操控对于的API对象;
Controller工作流程:
1)Controller均通过API Server监听资源的变更;
2)对比当前指定资源的当前状态和期望状态;
3)若不满足期望状态,则执行对应的操作;
//资源的期望状态记录在资源的spec字段,实际状态记录在status字段
如:提交Deployment清单至API Server后所发生的事件链
Controller分为以下8种:
(1)Replication Controller
1)通过监听机制监听可能影响期望复制集数量或对应Pod数量的变更事件;
2)监听到对应事件后,会重新检查是否达到期望状态以及实际的复制集数量;
3)若没达到要求,则执行对应的操作;
//Replicaset、DaemonSet和Job同理
如:Replication Controller监听资源对象变更
1)Replication Controller会运行额外的实例,但不会运行Pod;
2)Replication Controller通过创建Pod清单,并发送到API Server;
3)再通过Scheduler和Kubelet实现Pod的创建和运行;
(2)Deployment Controller
1)Deployment被修改后,Deplyment控制器都会滚动升级到新版本;
2)通过Deployment定义策略同时扩缩容新、旧RelicaSet(旧Pod被完全代替)
//不会直接创建任何Pod
(3)StatefulSet Controller
1)初始化并管理每个Pod对象的持久卷声明字段;
//其他Controller只管理Pod
(4)Node Controller
1)确保节点对象列表和集群中实际运行的机器列表保持同步;
2)监控每个节点的健康状态,并删除不可达节点的Pod;
(5)Service Controller
1)LoadBalancer类型服务被创建/删除时,从基础设施请求、释放负载均衡器;
(6)Endpoint Controller
1)同时监听Service和其对应的Pod;
如:Replication Controller监听资源对象变更
1)当监听到Service或Pod被添加、修改或删除时,Controller会选择匹配Service的Pod选择器的Pod,将其IP和端口添加到Endpoint资源中;
//删除Service时,对应的Endpoint也会随之被删除
(7)Namespace Controller
1)当删除Namespace时,Controller实现删除该Namespace下的所有资源;
(8)PersistentVolume Controller
1)Controller会为PVC查找最佳匹配项(声明容量大于需求容量的最小PV);
2)原理:保存一份有序的PV列表,对于每种访问模式按照容量升序排列,返回列表的第一个卷;
Node节点组件
Node节点组件为以下4种(运行在Node节点):
组件名 | 说明 |
Kubelet | 负责Master节点下发到该节点的具体任务 并定时向API Server汇报该节点信息 |
kube-proxy (Kubelet代理服务) | Node节点中Pod的代理 |
1)Node节点上的组件需均在同一个节点上运行
Kubelet
Kubelet:负责Master节点下发到该节点的具体任务
1)同时会管理该节点上的Pod和容器,并定时向API Server汇报节点信息;
2)Kubelet一般会从API Server获取Pod清单
3)Kubelet也可基于本地目录下的Pod清单创建/运行Pod
//本地的Pod清单一般用于将控制平面组件以Pod形式运行
如:Kubelet基于API Server和本地文件Pod清单创建Pod
//Kubelet也是运行容器存活探针的组件
Kubelet工作概括:
1)在API Server中创建一个Node资源以注册该节点;
2)持续监控API Server是否分配Pod给该节点(若分配,则创建并运行Pod);
3)通知容器引擎通过指定的容器镜像运行容器;
4)持续监控运行的容器,并向API Server报告其状态、事件和资源消耗;
//当Pod从API Server中删除时,Kubelet会终止容器并告知API Server已终止
kube-proxy
kube-proxy:确保用户的可通过Kubernetes API连接到指定服务
1)本质:将对Service的IP和端口访问转发至后台的特定Pod;
代理模式分为:userspace代理、iptables代理(默认)
(1)userspace代理:通过实际服务器集成接收连接,同时代理给Pod
1)数据包需传递过kube-proxy,且在用户空间处理(对性能影响较大);
2)以轮询模式对连接做负载均衡;
(2)iptables代理:通过iptables规则重定向数据包到一个随机选择的后端Pod
1)数据包不经过kube-proxy,且数据包只会在内核空间处理(性能更好);
2)以随机选择后端Pod对连接做负载均衡;
iptables代理流程:
1)当API Server创建新Service时,会为其分配一个虚拟IP;
2)API Server通知所有Node节点上的kube-proxy,已有一个新Serivce建立;
3)每个kube-proxy会使该Service在其节点变得可寻址(建立iptables规则);
//确保每个目的地为Service的IP和端口对的数据包可被解析
如:iptables代理的流程
附加组件
附加组件:Kubernetes集群中非核心组件,但可加强集群功能的组件
1)附加组件部署方式:提交YAML清单文件至API Server(以Pod方式部署);
常见附加组件:
(1)DNS
1)以Pod形式部署在集群中,且附属于kube-dns服务;
2)Kubernetes集群中所有Pod默认使用集群内部的DNS服务器;
//实现Pod可通过名称查询Service(甚至是无头Service下Pod的IP)
3)kube-dns通过API Server监控机制监听Service和Endpoint的变更;
(2)Ingress Controller
1)Ingress Controller需运行一个反向代理服务器(如:Nginx);
2)Ingress Controller通过API Server监控机制监听Service和Endpoint的变更;
3)Ingress Controller会直接将流量转发到Service的Pod(略过Service的IP);
4)当外部客户端通过Ingress Controller连接时,会记录该客户端的IP;
Pod网络
Pod网络:确保Kubernetes集群中的Pod可相互通信
1)由系统管理员或CNI(Container Network Interface)插件建立
2)集群中每个Pod都拥有一个具有唯一性的IP
3)当Pod向外部发送数据包时,其源IP会被改成其Node节点的IP
如:Pod内的容器相互通信过程
//Kubernetes集群中Pod必须通过非NAT网络进行连接,Pod到节点或节点到Pod之间也不可使用NAT通信
Pod通信
基础容器:存储集群中所有的网络和命名空间
1)功能:其他容器重启后,仍处于与之前相同的网络和Linux命名空间中;
2)Pod中不论运行多少容器,都会运行一个基础容器;
3)基础容器的生命周期和Pod向绑定;
//基础容器在Pod运行期间被关闭,Kubelet会自动重建以及Pod内的其他容器
Pod通信分为:同节点Pod通信、不同节点Pod通信
(1)同节点Pod通信:基于evth-pair技术(虚拟Ethernet接口对)
1)Pod创建容器时会为每个容器创建虚拟Ethernet接口对;
2)同一节点上的所有Pod都会连接到同一个网桥;
虚拟Ethernet接口对:由连接至两端的两块虚拟网卡构成
1)veth为前缀的虚拟网卡保存至节点的命名空间中;
2)eth0命名的虚拟网卡保存至容器中(eth0的IP从网络地址段中获取);
//容器内部的程序默认发送数据到eth0虚拟网卡;
如:同一Node节点的Pod通过evth-pair技术通信
(2)不同节点Pod通信:通过连接不同节点的网桥
1)连接网桥的方式分为:overlay、underlay、三层路由
2)不同节点的网络必须使用非重叠的地址段(防止Pod的IP重复);
如:通过三层路由连接网桥实现不同节点的Pod通信