Kubernetes概述

Kubernetes简介

       Kubernetes是Google2014年创建的一款开源的容器编排管理工具,是Google10多年大规模容器管理技术Borg的开源版本。它是容器集群管理系统,是一个开源的平台,可以实现容器集群的自动化部署、自动扩缩容、维护等功能。因此其成熟度从其诞生初期就广泛收到业界的关注,并且迅速成为编排工具市场的主流,其社区活跃度非常高,版本迭代速度也很惊人,它的主要作用是对Docker容器做编排工作,当然,Docker只是容器工具的一种引擎,K8S可支持多种容器引擎,但从目前来说Docker容器引擎是具有绝对优势的,容器需要编排,也很容易理解,因为我们最核心要跑业务通常都是LNMT/P的不同形式的扩展,但NMT/P他们的运行是有先后顺序的,也就是或MySQL要先启动,然后是Tomcat或PHP,最后是Nginx,而控制这种顺序就需要有容器编排工具来帮助我们实现,另外,我们的业务希望7x24小时在线,如何保障?靠人是很难做到实时的,但编排工具可以,K8S帮我们实现了很多控制器,这控制器可以帮我们监控容器运行的状态,并自动帮我们重建(在容器时代重启就是重建)容器,并且还可以在容器处理能力不足时,自动根据我们定义的扩展规则,自动创建新Pod(K8S中最小单元,每个Pod中可有一个或多个容器),并且在压力下去后,自动删除Pod等功能。

通过Kubernetes你可以:

  • 快速部署应用
  • 快速扩展应用
  • 无缝对接新的应用功能
  • 节省资源,优化硬件资源的使用

Kubernetes的特点:

  • 可移植:支持公有云、私有云、混合云、多重云(multi-cloud)。
  • 轻量级:消耗的资源非常少。
  • 可扩展:模块化,插件化,可挂载,可组合。
  • 自动化:自动部署,自动重启,自动复制,自动伸缩/扩展。
  • 自我修复:一旦某一个容器崩溃,能够在1秒中左右迅速启动新的容器。
  • 弹性伸缩:可以根据需要,自动对集群中正在运行的容器数量进行调整。
  • 服务发现:服务可以通过自动发现的形式找到它所依赖的服务。
  • 负载均衡:如果一个服务启动了多个容器,能够自动实现请求的负载均衡。
  • 版本回退:如果发现新发布的程序版本有问题,可以立即回退到原来的版本。
  • 存储编排:可以根据容器自身的需求自动创建存储卷。

Borg系统架构图

        BorgMaster是专门去负责请求分发的,可以理解为整个集群的大脑,真正工作的节点是Borglet,为了防止BorgMaster单节点故障,会发现有很多副本,对于高可用集群来说,最好是把集群数保持在1、3、5、7、9的基数,方便以后在推选的时候不会出现同票的结果。BorgMaster接收到请求以后会去做分发,Scheduler接收到请求以后会去把数据写入到Paxos数据库,Paxos数据库去存储,并且Borglet会实时的在Paxos数据库里监听,如果发现有自己的请求,会把这些请求取出来去处理这些任务,达到目的流程。


Docker swarm和Kubernetes的区别

使用Docker swarm的优点及缺点:

优点:

  • 以更快的速度运行:当您使用虚拟环境时,您可能已经意识到它需要很长时间,并且包括启动和启动您要运行的应用程序的繁程序。使用Docker swarm,这不再是一个问题。Docker swarm消除了启动完整虚拟机的需要,使应用程序能够快速再虚拟和软件定义的环境中运行,并有助于DevOps实施。
  • 文档提供了所有信息:Docker团队在文档方便脱颖而出!Docker正在迅速发展,并为整个平台赢得了热烈的掌声。当版本在很短的时候间隔内发布时,某些平台不会维护文档。但是Docker swarm从未与它妥协。如果该信息仅适用于Docker swarm的某些版本,则文档会确保更新所有信息。
  • 提供简单快速的配置:Docker swarm的一个主要优点是它简化了问题。Docker Swarm使用户可以自己配置,将其放入代码中并轻松部署。由于Docker swarm可以在各种环境中使用,因此需求不受应用程序的约束。
  • 确保应用程序是孤立的:Docker swarm注意每个容器与其他容器隔离并拥有自己的资源。可以部署各种容器以在不同堆栈中运行单独的应用程序。除此之外,当每个应用程序在自己的容器上运行时,Docker swarm会清除应用程序删除。如果不再需要该应用程序,则可以删除其容器。它不会在您的主机操作系统上留下任何临时或配置文件。
  • 版本控制和组件重用:使用Docker swarm,您可以跟踪容器的连续版本,检查差异或回滚到先前版本。容器重复使用前面层中的组件,这使得它们显得轻量级。

缺点:

  • Docker依赖于平台:Docker swarm是一个Linux激动人心的平台。虽然Docker支持Windows和Mac OS X,但它利用虚拟机在非Linux平台上运行。设计为在Windows上的Docker容器中运行的应用程序无法在Linux上运行,反之亦然。
  • 不提供存储选项:Docker swarm不提供将容器连接到存储的无障碍方式,这是主要缺点之一。其数据量需要在主机和手动配置上进行大量即兴创建。如果您期望Docker swarm解决存储问题,可能会以高效且用户友好的方式完成。
  • 监控不良Docker swarm提供有关容器的基本信息,如果您正在寻找基本的监控解决方案,那么Stats命令就足够了。如果您正在寻找高级监控,那么Docker swarm永远不是一个选择。虽然有像CAdvisor这样的第三方工具可以提供更多监控,但使用Docker本身实时收集有关容器的更多数据是不可行的。

 

使用Kubernetes的优点及缺点:

优点:

  • 它的速度很快:在不停机的情况下持续部署新功能时,Kubernetes是一个完美的选择。Kubernetes的目标是以恒定的正常运行时间更新应用程序。它的速度通过您每小时可以运送的许多功能来衡量,同时保持可用的服务。
  • 遵循不可变基础架构的原则:以传统方式,如果多个更新出现任何问题,您就没有任何记录显示您部署了多少更新以及发生了哪个错误。在不可变基础结构中,如果您希望更新任何应用程序,则需要使用新标记构建容器映像并进行部署,从而使用旧映像版本终止旧容器。通过这种方式,您将获得一份记录,并了解您所作的事情以及是否有任何错误,您可以轻松回滚到上一个图像。
  • 提供声明性配置:用户可以知道系统应该处于说明状态以避免错误。作为传统工具的源代码控制,单元测试等不能与命令式配置一起使用,但可以与声明性配置一起使用。
  • 大规模部署和更新软件:由于Kubernetes具有不可变的声明性,因此扩展很容易。Kubernetes提供了一些用于扩展目的的有用功能:
    • 水平基础架构扩展:在单个服务器级别执行操作以应用水平扩展。可以毫不费力地添加或分离atest服务器。
    • 自动扩展:根据CPU资源或其他应用程序指标的使用情况,您可以更改正在运行的容器数。
    • 手动扩展:您可以通过命令或界面手动扩展正在运行的容器的数量。
    • 复制控制器:复制控制器确保集群在运行状态下具有指定数量的等效Pod。如果存在太多Pod,则复制控制器可以删除额外的Pod,反之亦然。
  • 处理应用程序的可用性:Kubernetes检查节点和容器的运行状态,并再由于错误导致的盒中崩溃时提供自我修复和自动替换。此外,它在多个Pod之间分配负载,以便在意外流量期间快速平衡资源。
  • 存储卷:在Kubernetes中,数据是在容器之间共享的,但是如果Pod被杀死,则自动删除卷。此外,数据是远程存储的,因此如果将Pod移动到另一个节点,数据将一直保留,直到用户删除它。

缺点:

  • 迁移进程需要时间:当创建一个新进程时,您必须等待应用程序启动,然后用户才能使用它。如果您要迁移到Kubernetes,则需要对代码库进行修改,以提高启动流程的效率,这样用户就不会有不好的体验。
  • 迁移到无状态需要做很多工作:如果您的应用程序是集群的或无状态的,那么将不会配置额外的Pod,并且必须重新处理应用程序中的配置。
  • 安装过程非常单调乏味:如果不适用Azure、谷歌或Amazon等云提供商,就很难在集群上设置Kubernetes

 

以下用图标的方式来体现不同之处:

  Docker Swarm  Kubernetes
 开发者  Docker公司  谷歌
 发布年份  2013  2014
 公司使用  Bugsnag、Bluestem Brands、Hammerhead、Code Picnic、Dial once等。  Asana、Buffer、CircleCI、Evernote、Harvest、Intel、Starbucks、Shopify等
 Controoller  Manager  Master
 Storage  Volumes  Persistent and Epherma
 公共云服务提供商  Google、Azure、AWS、OTC  Azure
 兼容性  不那么广泛和可定制  更广泛和高度可定制
 安装  易于设置  需要时间安装
 容差率  低容错性  高容错性
 大集群  对于强集群状态考虑速度  在不考虑速度的情况下,即使在大型集群中也提供容器部署和扩展
 负载均衡(Loading Balancing)  当容器中的Pod定义为服务时,提供负载均衡  通过集群中的任何节点提供自动的内部负载平衡
 部署单位  Task  Pod
 Port  Published Port Endpoint
 社区  活跃的用户群,定期更新各种应用程序的映像  获得开源社区和谷歌、亚马逊、微软和IBM等大公司的大力支持
 弱点  没有供应商的认证计划,大多数组织需要商业认证版本。 倾向于开发人员而不是中央IT
 优势  主要由可以决定产品方向的单一供应商控制 明确的市场领导者,最高的采用率
 Slave  Worker Nodes
 容器设置  功能由Docker API提供并受其限制  客户端API和YAML,在Kubernetes中是唯一的
 可扩展性  即使在大型容器中也可以快速部署容器  以牺牲速度为代价为集群状态提供强有力的保证

Kubernetes组件说明

一个Kubernetes集群主要是由控制节点(master)、工作节点(node)构成,每个节点上都会安装不同的组件。如下图:

 

 master:集群的控制平面,负责集群的决策(管理)

  • kube-apiserver:API服务器是Kubernetes控制面的前端,资源操作的唯一入口,接收用户输入的命令,提供认证、授权、API注册和发现等机制。
  • kube-scheduler(决策者):负责集群资源调度的决策,按照预定的调度策略将Pod调度到响应的node节点上。
  • kube-controller-manager(调度者):运行控制器进程的控制平面组件,负责维护集群的状态和资源的调度,比如程序部署安排、故障检测、自动扩展、滚动更新。
  • cloud-controller-manager:云控制器管理器是指嵌入特定云的控制逻辑的控制平面组件。
  • Etcd:兼具一致性和高可用性的键值数据库,可以作为保存Kubernetes所有集群数据的后台数据库。负责存储集群中各种资源对象的信息。

node:集群的数据平面,负责为容器提供运行环境(执行)

  • kubelet(节点管理者):一个在集群中每个节点(node)上运行的代理。它保证容器(containers)都运行在Pod中,负责维护容器的生命周期,即通过控制docker,来创建、更新、销毁容器。
  • kube-proxy(通信入口):kube-proxy是集群中每个节点上运行的网络代理,负责提供集群内部的服务发现和负载均衡。
  • Docker:负责节点上容器的各种操作。

Etcd组件说明

Etcd的官方将它定位成一个可信赖的分布式键值存储服务,它能够为整个分布式集群存储一些关键数据,协助分布式集群的正常运转。以下是版本区别图:

 

        推荐在Kubernetes集群中使用Etcd v3版,v2版本已在Kubernetes v1.11中弃用。v2版会把所有的数据写入到内存中,v3版会引入一个本地的卷的持久化操作,也就意味着关机后并不会造成数据损坏,会从我们的本地磁盘进行恢复,理论上我们需要选择v3版,因为这样不会造成数据丢失,但需要注意一下,v1.11版包括之前的版本是不支持v3版的,那我们现在已经安装的是v1.15.1的最新稳定版了,所以不需要考虑这个问题。万一集群是非常古老的,使用的是v1.11版本的,那就需要注意要做数据备份操作了。

 

Etcd内部架构图

 

  它采用的是HTTP Server的形式,也就意味着这里依然采用httpd协议构建的服务,还有一种也采用的httpd协议,那就是Kubernetes,Kubernetes也是采用httpd协议,进行的C/S结构的开发。为什么要这么做呢?因为我们的httpd协议天生支持很多的一种操作方式,比如put、git等等,包括授权、认证。所以没有必要再去采用我们标准的tcp协议开发一系列的认证流程,所以我们直接采用httpd协议即可。

  Raft是做一些读写信息的工作,所有的信息都被存在这里,并且为了防止这些信息出现损坏的话,它还有一个叫WAL,这是一个预写日志,也就是说如果你想对里面的数据进行更改的话,它会让你先生成一个日志,它先进行存储一下,并且会定时的对这些日志做一次完整的备份,也就是完整+临时。比如我先备份一个大版本,如果有一些临时的修改,会创建1个子版本、2个子版本,到达一定时间以后还会进行一次备份,把它们转换成一个大版本,然后在重复此步骤,那这样有什么好处呢?首先我们不可能进行随时的完整备份,因为消耗的数据量太大,那为什么还要一定时间内进行完整备份呢?是因为防止这里的增量备份太多,我们在还原的时候太费事、太费时,所以采用了这么一种方案,并且它还会实时的把我们这些数据写入到我们的本地磁盘中进行持久化设置,这就是我们Etcd架构的说明。


kube-proxy组件说明

kubelet会跟我们的CRI(Container容器、Runtime运行环境、interface接口)进行交互,简白来说这就是我们的docker的表现形式,kubelet会跟docker交互,去操作docker创建对应的容器,也就是kubelet会维护我们Pod的生命周期。


kube-proxy组件说明

  负载的工作就是通过我们kube-proxy去完成的,也就意味着怎么去实现我们的Pod与Pod之间的访问,包括负载均衡,那就需要借助到我们的kube-proxy,它的默认操作对象是操作防火墙,去实现Pod的映射,当然我们新版本中还支持IPVS映射,也就是我们的LVS组件。


其他插件说明

  • CoreDNS:可以为集群中的SVC创建一个域名IP的对应关系解析,也就意味着我们以后在集群中访问我们一些其他的一些Pod的时候,我完全不需要通过Pod的IP地址,通过什么呢?通过CoreDNS提供一个B/S结构的访问体系。
  • Ingress Controller:我们的官方Kubernetes集群只能实现一个四层代理,Ingress可以实现七层代理,也就是可以根据我们的主机名,根据我们的域名地址负载均衡。
  • Federation:它给我们提供了一个可以跨集群中心多K8S的统一管理的功能。
  • Prometheus:提供了一个K8S集群的监控能力。
  • ELK:提供了K8S集群日志统一分析介入平台。

Kubernetes的工作原理

Kubernetes的工作原理具体如下:

  1. 运维人员向API Server发出创建Pod请求,告诉它我想干什么,我的期望是什么。
  2. API Server响应请求,并通过一系列认证授权,把请求存储到Etcd。
  3. 并通知Controller-manager,它会通过API Server读取Etcd,然后按照所预设的模板去创建Pod,并将Pod数据写入Etcd。
  4. 然后Controller-manager会通过API Server去找Scheduler为新创建的Pod选择最适合的node节点。Scheduler会通过预算策略在所有的node节点中挑选最优的。
  5. node节点中还剩多少资源是通过汇报给API Server存储在Etcd里面的,API Server会调用一个方法找到Etcd里所有的node节点的剩余资源,再对比Pod所需要的资源,在所有node节点中查找哪些node节点符合要求,
  6. 如果都符合,预算策略就交给优选策略处理,优选策略再通过CPU的负载、内存的剩余量等因素选择最合适的node节点,并把Pod调度到这个node节点上运行。
  7. Controller-manager会通过API Server通知kubelet去创建Pod,然后通过kube-proxy中的Service对外提供服务接口。