当前位置: 首页 > 科技观察

5分钟带你了解K8S必要的架构概念,以及网络模型

时间:2023-03-19 14:57:44 科技观察

目录K8S,他们会被K8S里面的概念搞糊涂,望而却步;而且很多文章介绍的时候都太专业了。今天老顾就来帮大家梳理一下。谈话不深入。目的是帮助大家更好地理解各种概念的由来。架构图5分钟让你了解K8S必要的架构概念,以及网络模型(1)上图中,有两种Node节点,一种是Master,一种是Work。顾名思义,WorkNode是用来工作的,也就是实际承担服务的机器节点。例如服务A部署到K8S后,其运行环境在WorkNode节点上。那么为什么要使用主节点呢?小伙伴可以认为是用来分配服务给哪个工作节点节点的;可以理解为一个大管家,它会知道现有工作节点的资源运行状态,并决定哪些服务要安排在工作节点上。WorkNode节点上有两个重要的组件,一个是Pod,一个是Container;Pod是K8S的最小单元,里面可以有多个Container。容器是服务/组件运行的环境。一般一个Pod只有一个业务服务Container,其他Container都是系统需要的容器(其实就是一些流程组件,比如网络组件,Volume组件等)。所以一般可以理解为我们的服务在Pod中。以上简单介绍了K8S的基本架构和小伙伴对核心点的基本使用。明白这一点就够了。当然,具体的Master和Work节点需要深入了解。什么是组件以及组件之间的发布过程?继续往下看。在MasterNode组件中,用户一般使用kubectl命令和dashboard控制台来操作k8s。所有的操作都是通过APIServer组件进行的,需要持久化的都存储在etcd中。Scheduler和ControllerManager组件一直在订阅APIServer中的更改。整体流程如果用户需要创建服务A的三个pod,整体流程:1)通过Kubectl提交创建RC的请求,通过APIServer将请求写入etcd2)此时ControllerManager通过APIServer监听资源变化的接口监听这个RC事件。经过分析,发现当前集群中没有对应的Pod实例,于是根据RC中的Pod模板定义生成一个Pod对象,通过APIServer写入etcd3)接下来,这个事件被Scheduler发现时,它立即执行一个复杂的调度过程,为新的Pod选择一个WorkNode,并通过APIServer将结果写入etcd。4)随后,运行在目标WorkNode上的Kubelet进程通过APIServer监听“新生”的Pod,并根据其定义启动Pod。5)用户的需求是3个pod;那么3个吊舱已经启动了吗?它由控制器管理器监控和管理,这将确保资源满足用户的需求。etcd用于持久化存储集群中的所有资源对象,如Node、Service、Pod、RC、Namespace等;APIServer提供了API来封装etcd的操作。这些API基本上是集群中资源对象的增删改查和监控资源变化的接口。APIServer为资源对象提供了唯一的操作入口,所有其他组件都必须通过它提供的API来操作资源数据。通过对相关资源数据的“全量查询”+“变化监控”,这些组件可以“实时”完成相关业务功能。ControllerManager集群内部管理控制中心的主要目的是自动化Kubernetes集群的故障检测和恢复,比如根据RC的定义完成Pod的复制或移除,确保Pod实例数量符合RC副本的定义;根据Service和Pod的管理关系完成服务的Endpoints对象的创建和更新;其他任务如节点发现、管理和状态监控、死容器占用的磁盘空间、清理本地缓存的镜像文件等也由ControllerManager完成。Scheduler集群中的调度器负责集群节点中Pod的调度和分配。WorkNode组件上图右边是WorkNode组件,整体流程1)kubelet监听到ApiServer的变化后,如果有worknode节点需要创建pod;会通知ContainerRuntime组件2)ContainerRuntime是管理节点的Pod组件,当启动一个pod时,如果本地没有image,会从dockerhub拉取image,启动容器pod3)kubelet会通过相关的信息到ApiServerKubelet负责创建、修改、监控、删除等全生命周期管理,Kubelet定期将Node的状态信息“报告”给APIServer。Pod管理本质上是负责ContainerRuntime组件的kube-proxy,它实现了Serviceproxy和softwaremodeloadbalancer。这是因为pod的网络IP经常变化。对于这个网络知识,老谷会在下一篇文章介绍Pod发布,里面介绍了K8S架构的整体流程。下面老谷从pod开始,一步步介绍K8S的其他概念。我们先编辑yaml,定义一个pod对象apiVersion:v1#指定api版本,这个值必须在kubectlapiversion中kind:Pod#指定资源创建的角色/类型metadata:#metadata/attributeofresourcename:mc-user#resource名称在同一个命名空间中必须是唯一的。spec:#specificationoftheresourcecontent指定资源容器的内容:#Containerdefinition-name:mc-user#容器image的名称:rainbow/mc-user:1.0.RELEASE#Containerimage我们通过kubectl命令来创建这个podkubectlapply-fmc-user-pod.yaml我们的mc-user:1.0.RELEASE镜像是一个web应用,端口8080;但是我们发现pod启动后,我们无法通过pod的ip地址访问到这个web服务怎么访问pod呢?在反向代理解决访问pod的问题之前,先来看看我们之前是如何部署网站的。要从外网访问我们的内部网站,我们一般会在中间部署一个nginx。反向代理我们的网络服务。根据这个思路,在K8S系统中也有反向代理的概念。NodePort服务在K8S中,我们可以使用NodePort类型的服务来实现反向代理。K8S中有很多服务,其中NodePortService提供了反向代理的实现,使得外部网络可以访问内部的pod了。实现过程:1)Pod需要打上Label标签2)外部流量请求发送到NodePortService,通过Selector进行路由,3)NodePortService根据路由转发到后端PodLabel标签从上面的流程来看,Service也起到了负载均衡的作用;后端Pod可以有多个,可以同时标记同一个Label,Service会被路由转发到其中一个Pod。ServiceType也可以是LoadBalancer,ClusterIPLoadBalancer:这个是部署到云端时(比如阿里云)需要用到的也是反向代理+负载均衡的作用,用于外部访问内部K8S。ClusterIP:这个Service是在K8S集群内部用作反向代理的Label和Selector。上图中,有2个pod定义了Label为app:nginx;1个pod定义了应用程序:apache;然后服务筛选器的选择器应用程序:nginx,仅路由到nginxpod。服务发布我们写一个NodePort服务发布文件apiVersion:v1kind:Servicemetadata:name:mc-userspec:ports:-name:http#通信协议port:8080#这里的端口对应clusterIP,即ip:8080,用于内部使用权。targetPort:8080#端口必须对应容器暴露的端口nodePort:31001#节点会开放这个端口,这个端口是给外部调用的selector:app:mc-user#这里的selector必须选择容器类型的标签:NodePort#这个表示NodePort类型的端口范围nodePort:30000~32767上面是NodePortService的yaml文件,我们还需要修改之前一个Pod的yaml文件apiVersion:v1#指定api版本,这个值必须是inkubectlapiversionkind:Pod#指定资源创建的角色/类型metadata:#Metadata/资源的属性name:mc-user#资源名称在同一个命名空间中必须唯一labels:#标签定义app:mc-user#Labelvaluespec:#specificationoftheresourcecontent指定资源容器的内容:#Containerdefinition-name:mc-user#容器image的名称:rainbow/mc-user:1.0.RELEASE#Containerimage我们可以使用kubectl命令分别执行pod和service的yaml文件谎言;这样就可以直接通过外网访问了。http://localhost:31001别忘了端口是nodePort定义的端口。总结今天老谷介绍了K8S的基本概念和架构流程;核心是小伙伴们需要了解Pod、Service、Labels、Selector这几个组件为什么会这样?他们解决了什么问题?后续老谷会继续介绍其他K8S组件概念,希望能帮助小伙伴们理解,降低K8S的学习难度;谢谢你!!!