kubernetes(理论知识)

1.kubernetes 简介

kubernetes,简称K8s,是用8代替8个字符“ubernete”而成的缩写。是 Google 开源的一个容器编排引擎,用于管理云平台中多个主机上的容器化的应用。它支持自动化部署、大规模可伸缩、应用容器化管理。在生产环境中部署一个应用程序时,通常要部署该应用的多个实例以便对应用请求进行负载均衡。

在 Kubernetes 中,我们可以创建多个容器,每个容器里面运行一个应用实例,然后通过内置的负载均衡策略,实现对这一组应用实例的管理、发现、访问,而这些细节都不需要运维人员去进行复杂的手工配置和处理。

传统的应用部署方式是通过插件或脚本来安装应用。这样做的缺点是应用的运行、配置、管理、所有生存周期将与当前操作系统绑定,这样做并不利于应用的升级更新、回滚等操作,当然也可以通过创建虚拟机的方式来实现某些功能,但是虚拟机非常重,并不利于可移植性。

新的方式是通过部署容器方式实现,每个容器之间互相隔离,每个容器有自己的文件系统 ,容器之间进程不会相互影响,能区分计算资源。相对于虚拟机,容器能快速部署,由于容器与底层设施、机器文件系统解耦的,所以它能在不同云、不同版本操作系统间进行迁移。

容器占用资源少、部署快,每个应用可以被打包成一个容器镜像,每个应用与容器间成一对一关系也使容器有更大优势,使用容器可以在build或release 的阶段,为应用创建容器镜像,因为每个应用不需要与其余的应用堆栈组合,也不依赖于生产环境基础结构,这使得从研发到测试、生产能提供一致环境。类似地,容器比虚拟机轻量、更“透明”,这更便于监控和管理。

2. kubernetes 的特点

  • 自动装箱: 基于资源依赖及其约束能够自动完成容器的部署且不影响其可用性
  • 自我修复: 一旦容器崩了,可以自动启动一个新的容器替代,从而实现自我修复的目的
  • 自动实现水平扩展:一个容器不够,再启动一个,可以不断的进行扩展,只要物理平台的资源能够支撑
  • 自动进行服务发现和负载均衡:通过KubeDNS(或CoreDNS)为系统内置了服务发现功能,为每个service配置DNS名称,service通过iptables或ipvs内建了负载均衡机制
  • 自动发布和回滚:自动发布和回滚,支持多种发布方式
  • 密钥和配置管理:容器化应用程序的最大问题在于配置容器内的应用程序比较困难。基于镜像启动一个容器后,如果期望容器中的应用程序换一个配置该怎么办呢?如果我们定义一个 entrypoint 的脚本,而这个脚本可以接受用户传入的变量参数,把变量的值转换为容器内的应用程序可读取的配置,从而能完成容器化应用程序的配置。之所以这么麻烦是因为早期的应用程序不是面向云原生而开发的,所以那些应用程序要通过读取配置文件来获取配置,而云原生开发的应用程序可以基于环境变量来获取配置。这种配置方式使得一个镜像能满足用户在不同环境下运行同一个镜像为不同配置的容器的许球球。但是在容器编排工具当中,这种配置方式会存在一些问题,比如配置信息保存到哪里?如果我们用编排平台让容器启动自动化了,但每次启动容器时我们还要手工去传递环境变量的值,这是一个非常麻烦的事,所以我们需要一个外部的组件保存这些配置信息于外部,当镜像启动为容器时,只需要让镜像去加载外部的配置中心的配置信息,就能完成应用程序的配置。
  • 存储编排:把存储卷实现动态供给,当容器要存储卷时,根据容器自身的需求创建能够满足其需要的存储卷
  • 批处理:除了管理服务型应用之外,Kubernetes 还支持批处理作业及CI(持续集成)

3. kubernetes 集群架构

kubernetes 就是一个组合多台主机的资源整合成一个大的资源池,并统一对外进行计算、存储等能力的集群。
在这里插入图片描述

3.1 master

  • API Server:负责接收并处理请求
  • Scheduler:调度容器创建的请求
  • Controller Manager:确保后端节点(node)上的控制器(Controller)处于健康状态
  • Controller:确保已创建的容器处于健康状态
  • etcd:etcd是 Kubernetes 提供默认的存储系统,保存所有集群数据,使用时需要为etcd数据提供备份计划

3.2 nodes

  • Kubelet:与master通信的集群代理
  • docker:运行容器
  • kube-proxy:kube-proxy通过在主机上维护网络规则并执行连接转发来实现Kubernetes服务抽象

4. kubernetes 专业术语

4.1 pod

  • pod是 kubernetes 中最小调度逻辑单元
  • pod可以理解为是容器的外壳,它为容器做了一层抽象的封装
  • pod内部主要是用来放容器的
  • pod的特点是可以将多个容器加入到同一个网络名称空间中
  • 一个pod中可以包含多个容器(实际生产中不会放多个容器)
  • 同一个pod中的不同容器可以共享存储卷
  • 一个pod上无论是有一个容器还是有多个容器,一旦将次pod调度到某node上运行时,这一个pod内部的所有容器只能运行在同一个node上

pod分类

  • 自主式pod:自我手动管理的pod,创建以后仍然需要提交给 apiserver ,由 apiserver 接收以后借助于调度器将其调度至指定的node节点,由node启动此pod,如果pod出现故障,需要重启容器则有 kubelet 来完成,如果 node 节点故障了,那么此pod将会消失。其无法实现全局调度,所以不推荐使用此种pod
  • 控制器管理的pod

pod控制类型

  • ReplicationController:副本控制器。当启动一个pod是,这个pod如果不够用可以再启动一个副本,而后由控制器来管理同一类pod的各种副本与对象。一旦副本少了就会自动增加。采取多退少补的规则,精确符合我们所定义的期望
  • ReplicaSet:由一个名叫 Deployment 的声明式更新的控制器来管理
  • Deployment:管理无状态应用,建构在ReplicaSet之上的
    滚动更新
    声明式配置–>支持动态运行时修改
  • DaemonSet:如果需要在每个node上运行一个副本的时候可以用 Daemonset
  • Job:执行一次性任务,执行成功后就退出
  • CronJob:周期性Job
  • StatefulSet:管理有状态应用

Deployment滚动更新策略:
在这里插入图片描述

4.2 node

  • node 是k8s集群中的工作节点,负责运行由 master 指派的各种任务。而最核心的任务就是以pod形式运行容器
  • node 可以是任何形式的计算设备,只要此设备上能够有传统意义上的 CPU、内存、存储空间,并且能装上k8s的集群代理程序,它都可以作为整个k8s集群一个成员

4.3 标签(Label)和标签选择器(Label Selector)

当大量的pod运行在一个集群当中时,如何实现分类管理?比如想删除某一类pod,这么多的pod,我们肯定不能通过pod的名称来识别容器,因为pod随时都会被创建和删除,当一个pod发生故障被删除后,重新生成的pod的名称和被删除的pod肯定不一样,只不过其内部运行的程序是一样的,所以我们不能通过pod的名称来识别。同时我们有可能要将一类pod归为一组,比如创建4个 nginx 的pod,期望使用一个控制器对其进行统一管理,删除一个控制器就把这4个pod都删了,控制器还要保证这4个pod都处于运行状态,缺一个要补一个,多一个要多杀一个,精确符合我们期望的4个pod才行。

为了能够实现pod识别,需要在pod至上附加一些元数据,类似 Dockerfile 中的 label 标签的方式,比如在创建pod时为其附加一个名为 app 的 key,然后将其值设为 nginx,那么当我们在批量进行pod调度管理时,可以检查pod中是否有 app 这个 key,且其值是否为 nginx,通过此种方法来识别pod是否是我们想要控制的pod。

Label(标签)是 Kubernetes 系统中另外一个核心概念。一个 Label 是 一个key=value 的键值对,其中 key 与 value 由用户自己指定。Label可以被附加到各种资源对象上,例如 Node、Pod、Service、RC 等,一个资源对 象可以定义任意数量的 Label,同一个 Label也可以被添加到任意数量的 资源对象上。Label通常在资源对象定义时确定,也可以在对象创建后 动态添加或者删除。

Label 相当于我们熟悉的“标签”。给某个资源对象定义一个 Label, 就相当于给它打了一个标签,随后可以通过 Label Selector(标签选择 器)查询和筛选拥有某些 Label 的资源对象,Kubernetes 通过这种方式实现了类似SQL的简单又通用的对象查询机制。

Label Selecto r可以被类比为SQL语句中的where查询条件,例如name=redis-slave 这个 Label Selector 作用于Pod时,可以被类比为 select * from pod where pod’s name =‘redis-slave’这样的语句。

5. kubernetes 核心组件

5.1 HPA

Deployment 还支持耳机控制器 HPA(HorizontalPodAutoscaler),水平pod自动伸缩控制器。

一般情况下我们可以确保一个node上有2个pod在运行,万一用户访问流量增加,2个pod不足以承载这么多访问量怎么办?此时我们就应该增加pod资源,那么到底应该增加几个呢?

HPA 控制器可以自动监控pod、自动进行扩展。

5.2 service(服务发现)

Kubernetes Pod 是有生命周期的,它们可以被创建,也可以被销毁,然而一旦被销毁生命就永远结束。如果pod所在的节点宕机了,那么此pod将应该要在其他的节点上重建,而重建玩的pod与原来的pod已经不是同一个pod了,只是两者都是运行的同一个服务而已。且每个容器都有其ip地址,重建的pod中的容器ip地址与之前的pod容器的ip地址是不一样的,如此一来就会存在一个问题,客户端如何访问这些pod中的容器呢?

为了尽可能的降低客户端与pod间协调的复杂度,k8s为每一组同类服务的pod和其客户端之间添加了一个中间层,这个中间层是固定的,这个中间层就叫 service。

Service 通过 label-selector 关联Pod。

service 只要不被删除,其地址与名称皆是固定的,当客户端需要在其配置文件中写上访问某个服务时,它不再需要自动发现,只需要在配置文件中写明 service 的名称即可,而这个 service 是个调度器,其不但能够提供一个稳定的访问入口,还可以做反向代理,当 service 接收到客户端的请求后,会将其代理到后端的pod之上,一旦pod宕机了会立即新建一个pod,这个新建的pod会立即被 service 关联上,作为 service 后端的可用pod之一。

客户端程序访问服务都是通过IP+端口号或者主机名的方式来实现的。而 service 关联后端的pod不是靠他的IP和主机名,而是靠pod的标签选择器,只要创建的pod的 label 是统一的,无论IP地址和主机如何改变,其都能被service 所识别。如此一来,只要pod属于标签选择器,只要其在 service 的管理范围之内,则其就会被关联到 service 中,当这个动态的pod关联到 service中之后,再进行动态的探测此pod的IP地址、端口,再将其作为自己后端可调度的可用服务器主机对象。因此,客户端的请求发送到 service,然后由 service 代理到后端真实的pod中的容器进行响应。

service 不是一个程序,也不是一个组件,它只是一个 iptables 的 dnat 规则。service 作为k8s的对象,有其自身的名称,而 service 的名称相当于服务的名称,而这个名称可以被解析。

service代理模式

  • iptables模式
    客户端IP请求时,直接请求本地内核service ip,根据iptables的规则直接将请求转发到到各pod上,因为使用iptable NAT来完成转发,也存在不可忽视的性能损耗。另外,如果集群中存在上万的Service/Endpoint,那么Node上的iptables rules将会非常庞大,性能还会再打折扣。
  • ipvs模式
    客户端IP请求时到达内核空间时,根据ipvs的规则直接分发到各pod上。kube-proxy会监视Kubernetes Service对象和Endpoints,调用netlink接口以相应地创建ipvs规则并定期与Kubernetes Service对象和Endpoints对象同步ipvs规则,以确保ipvs状态与期望一致。访问服务时,流量将被重定向到其中一个后端Pod。

在这里插入图片描述

5.3 AddOns 附件

dns pod
装完k8s后第一件事就是需要在k8s集群上部署一个 dns pod ,以确保各 service 的名称能够被解析。可以动态改变,包括动态创建、动态删除、动态修改。

把 service 的名称改了,dns pod 会自动触发,将 dns 解析记录中的名称也给改掉,假如我们手动把 service 的ip地址改了,改完以后自动触发,将dns服务中的解析记录给改掉。如此一来,客户端去访问pod资源的时候可以直接访问 service 的名称,然后由集群中专用的dns服务来负责解析。

这种pod是k8s自身的服务需要用到的pod,所以我们把它称为基础性的系统架构级的pod对象,而且她们也被称为集群附件。

6. kubernetes 网络模型

6.1 节点网络

各节点自身的网络,例如:master 与 node 之间的通信:此地址配置于 k8s 集群构建之前,它并不能由 K8s管理,管理员需要在集群创建之前手动确定其地址配置及管理方式。

6.2 pod网络

它是一个虚拟网络,用于为 各 Pod对象 设定 IP地址等网络参数,其地址配置于 Pod 中 Container 的网络接口上。

6.3 service 网络

它是专门用于 Service 资源对象的网络,它也是一个虚拟的网络。Service 的 IP 地址,并不配置于 任何 主机 或 Container 的网络接口之上,而是 通过 Node 上的 “kube-proxy” 配置为 “iptables” 或 “ipvs” 规则,从而将发往此 “service” 的所有流量通过规则调度至其后端的各“Pod对象”之上!
在这里插入图片描述
k8s的三种网络模型分属于三个网段。

通信的类型

  • 容器间通信: 同一个 pod 内多个容器间通过 LO 网卡完成通信
  • pod 与 pod 通信: 要求必须是 pod_ip 与 pod_ip 通信,不能经过任何的转发
  • pod 与 svc 通信: pod_ip 通过 iptable 或者 lvs 规则到 cluster_ip,lvs 不能代替 iptable 比如不能做 nat
  • svc 与集群外部通信: 通过 NodePort 或 LoadBalancer 的 svc,或 Ingress 来实现

6.4 CNI 插件

为了使容器之间的通信更加方便,Google 和 CoreOS 主导制定了一个容器网络标准CNI(Conteinre Network Interface) 。
CNI可允许K8S配置任何CNI插件。
官方文档:https://kubernetes.io/docs/concepts/cluster-administration/addons/
常见的插件

  • Flannel
    Flannel是目前使用最为普遍的方案,提供了多种网络backend,它支持多种数据路径,也适合于overlay/underlay等多种场景。对于overlay的数据包封装,可以使用用户态的UDP,内核态的Vxlan(性能相对较好),甚至在集群规模不大,且处于同一个二层域时可以采用host-gw的方式修改主机路由表
    参考地址: https://github.com/coreos/flannel
  • Calico
    主要是采用了修改主机路由,节点之间采用BGP的协议去进行路由的同步。但是现实中的网络并不总是支持BGP路由的,因此Calico也支持内核中的IPIP模式,使用overlay的方式来传输数据,Calico是Kubernetes生态系统中另一种流行的网络选择,它提供收费的技术支持。虽然Flannel被公认为是最简单的选择,但Calico以其性能、灵活性而闻名。Calico的功能更为全面,更为复杂。它不仅提供主机和pod之间的网络连接,还涉及网络安全和管理。Calico CNI插件在CNI框架内封装了Calico的功能。Calico不使用overlay网络。
    参考地址:https://github.com/projectcalico/cni-plugin
  • Weave Nets
    Weave是由Weaveworks提供的一种插件,它提供的模式是在集群中的节点之间创建网状的overlay网络。
    为了创建网络,Weave依赖于网络中每台主机上安装的路由组件。然后,这些路由器交换拓扑信息,以维护可用网络环境的最新视图。当需要将流量发送到位于不同节点上的pod时,Weave路由组件会自动决定是通过“快速数据路径”发送,还是回退到“sleeve”分组转发的方法。
    与Calico一样,Weave也为Kubernetes集群提供网络策略功能。设置Weave时,网络策略会自动安装和配置,因此除了添加网络规则之外,用户无需进行其他配置。一个其他网络方案都没有、Weave独有的功能,是对整个网络的简单加密。虽然这会增加相当多的网络开销,但Weave可以使用NaCl加密(http://nacl.cr.yp.to)来为sleeve流量自动加密所有路由流量,而对于快速数据路径流量,因为它需要加密内核中的VXLAN流量,Weave会使用IPsec ESP来加密快速数据路径流量。
    对于那些寻求功能丰富的网络、同时希望不要增加大量复杂性或管理难度的人来说,Weave是一个很好的选择。它设置起来相对容易,提供了许多内置和自动配置的功能,并且可以在其他解决方案可能出现故障的场景下提供智能路由。网状拓扑结构确实会限制可以合理容纳的网络的大小,不过对于大多数用户来说,这也不是一个大问题。此外,Weave也提供收费的技术支持,可以为企业用户提供故障排除等等技术服务。

6.5 策略控制(Network Policy)

Network Policy)是Kubernetes提供的基于策略的网络控制,用于隔离应用并提高安全性。它使用Kubernetes中常用的标签选择器模拟传统的分段网络,并通过策略控制它们之间的东西流量以及与外部交流的南北流量。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值