1.4.2 集群类

集群(Cluster)表示一个由Master和Node组成的Kubernetes集群。

1.Master

Master指的是集群的控制节点。在每个Kubernetes集群中都需要有一个或一组被称为Master的节点,来负责整个集群的管理和控制。Master通常占据一个独立的服务器(在高可用部署中建议至少使用3台服务器),是整个集群的“大脑”,如果它发生宕机或者不可用,那么对集群内容器应用的管理都将无法实施。

在Master上运行着以下关键进程。

◎ Kubernetes API Server(kube-apiserver):提供HTTP RESTful API接口的主要服务,是Kubernetes里对所有资源进行增、删、改、查等操作的唯一入口,也是集群控制的入口进程。

◎ Kubernetes Controller Manager(kube-controller-manager):Kubernetes里所有资源对象的自动化控制中心,可以将其理解为资源对象的“大总管”。

◎ Kubernetes Scheduler(kube-scheduler):负责资源调度(Pod调度)的进程,相当于公交公司的调度室。

另外,在Master上通常还需要部署etcd服务。

2.Node

Kubernetes集群中除Mater外的其他服务器被称为Node,Node在较早的版本中也被称为Minion。与Master一样,Node可以是一台物理主机,也可以是一台虚拟机。Node是Kubernetes集群中的工作负载节点,每个Node都会被Master分配一些工作负载(Docker容器),当某个Node宕机时,其上的工作负载会被Master自动转移到其他Node上。在每个Node上都运行着以下关键进程。

◎ kubelet:负责Pod对应容器的创建、启停等任务,同时与Master密切协作,实现集群管理的基本功能。

◎ kube-proxy:实现Kubernetes Service的通信与负载均衡机制的服务。

◎ 容器运行时(如Docker):负责本机的容器创建和管理。

Node可以在运行期间动态增加到Kubernetes集群中,前提是在这个Node上已正确安装、配置和启动了上述关键进程。在默认情况下,kubelet会向Master注册自己,这也是Kubernetes推荐的Node管理方式。一旦Node被纳入集群管理范畴,kubelet进程就会定时向Master汇报自身的情报,例如操作系统、主机CPU和内存使用情况,以及当前有哪些Pod在运行等,这样Master就可以获知每个Node的资源使用情况,并实现高效均衡的资源调度策略。而某个Node在超过指定时间不上报信息时,会被Master判定为“失联”,该Node的状态就被标记为不可用(Not Ready),Master随后会触发“工作负载大转移”的自动流程。

我们可以运行以下命令查看在集群中有多少个Node:

img

然后通过kubectl describe node <node_name>命令查看某个Node的详细信息:

img

在以上命令的运行结果中会展示目标Node的如下关键信息。

◎ Node的基本信息:名称、标签、创建时间等。

◎ Node当前的运行状态:Node启动后会做一系列自检工作,比如磁盘空间是否不足(DiskPressure)、内存是否不足(MemoryPressure)、网络是否正常(NetworkUnavailable)、PID资源是否充足(PIDPressure)。在一切正常时才设置Node为Ready状态(Ready=True),表示Node处于健康状态,Master就可以在其上调度新的任务了(如启动Pod)。

◎ Node的主机地址与主机名。

◎ Node上的资源数量:描述Node可用的系统资源,包括CPU、内存数量、最大可调度Pod数量等。

◎ Node可分配的资源量:描述Node当前可用于分配的资源量。

◎ 主机系统信息:包括主机ID、系统UUID、Linux Kernel版本号、操作系统类型与版本、Docker版本号、kubelet与kube-proxy的版本号等。

◎ 当前运行的Pod列表概要信息。

◎ 已分配的资源使用概要信息,例如资源申请的最小、最大允许使用量占系统总量的百分比。

◎ Node相关的Event信息。

如果一个Node存在问题,比如存在安全隐患、硬件资源不足要升级或者计划淘汰,我们就可以给这个Node打一种特殊的标签——污点(Taint),避免新的容器被调度到该Node上。而如果某些Pod可以(短期)容忍(Toleration)某种污点的存在,则可以继续将其调度到该Node上。Taint与Toleration这两个术语属于Kubernetes调度相关的重要术语和概念,在后续章节中会详细讲解。

在集群类里还有一个重要的基础概念——命名空间,它在很多情况下用于实现多租户的资源隔离,典型的一种思路就是给每个租户都分配一个命名空间。命名空间属于Kubernetes集群范畴的资源对象,在一个集群里可以创建多个命名空间,每个命名空间都是相互独立的存在,属于不同命名空间的资源对象从逻辑上相互隔离。在每个Kubernetes集群安装完成且正常运行之后,Master会自动创建两个命名空间,一个是默认的(default)、一个是系统级的(kube-system)。用户创建的资源对象如果没有指定命名空间,则被默认存放在default命名空间中;而系统相关的资源对象如网络组件、DNS组件、监控类组件等,都被安装在kube-system命名空间中。我们可以通过命名空间将集群内部的资源对象“分配”到不同的命名空间中,形成逻辑上分组的不同项目、小组或用户组,便于不同的分组在共享使用整个集群的资源的同时能被分别管理。当给每个租户都创建一个命名空间来实现多租户的资源隔离时,还能结合Kubernetes的资源配额管理,限定不同租户能占用的资源,例如CPU使用量、内存使用量等。

命名空间的定义很简单,如下所示的YAML文件定义了名为development的命名空间:

img

一旦创建了命名空间,我们在创建资源对象时就可以指定这个资源对象属于哪个命名空间。比如在下面的例子中定义了一个名为busybox的Pod,并将其放入development这个命名空间中:

img

此时使用kubectl get命令查看,将无法显示:

img

这是因为如果不加参数,则kubectl get命令将仅显示属于default命名空间的资源对象。

可以在kubectl get命令中加入--namespace参数来操作某个命名空间中的对象:

img