Kubernetes权威指南:从Docker到Kubernetes实践全接触

本系列文章是书籍:Kubernetes权威指南(第四版):从Docker到Kubernetes实践全接触/龚正等 编著. 的学习笔记
第1章 Kubernetes入门
第2章 Kubernetes安装配置指南
第3章 深入掌握Pod
第4章 深入掌握Service
第5章 核心组件运行机制
第6章 深入分析集群安全机制
第7章 网络原理
第8章 共享存储原理
第9章 Kubernetes开发指南
第10章 Kubernetes集群管理
第11章 Trouble Shooting指导
第12章 Kubernetes开发中的新功能



第1章 Kubernetes入门

提示:这里可以添加本文要记录的大概内容:

例如:随着人工智能的不断发展,机器学习这门技术也越来越重要,很多人都开启了学习机器学习,本文就介绍了机器学习的基础内容。


1.1 Kubernetes是什么

定义

首先,Kubernetes是一个全新的基于容器技术的分布式架构领先方案
其次,Kubernetes其实是一个高度自动化的资源控制系统
再次,Kubernetes是一个开放的开发平台
最后,Kubernetes是一个完备的分布式系统支撑平台

总结,Kubernetes是一个全新的基于容器技术的分布式架构解决方案,并且
是一个一站式的完备的分布式系统开发和支撑平台。
自己的理解:k8s是一张大网,一张架构图,能够解决集群(许多容器)管理问题,甚至还可以自动化运维,缩容扩容也很容易

基本知识

1.service
Service是分布式集群架构的核心,是实现了某个具体业务的特定TCP Server进程。相当于把功能的相关组件打包在一起,一个黑匣子,对外只提供端口,连接便可使用。

2.pod
pod可以理解为容器的集合,通常把一组密切相关的服务进程放入同一个Pod中。

service里面包含pod,pod是集群管理的最小组件。给每个Pod都贴上一个标签(Label),可以解决Service与Pod的关联问题。

首先,Pod运行在一个被称为节点(Node)的环境中,这个节点既可以是物理机,也可以是私有云或
者公有云中的一个虚拟机,通常在一个节点上运行几百个Pod;
其次,在每个Pod中都运行着一个特殊的被称为Pause的容器,其他容器则为业务容器。

3.机器划分
在集群管理方面,Kubernetes将集群中的机器划分为一个Master和一些Node。

在Master上运行着集群管理相关的一组进程kubeapiserver、kube-controller-manager和kubescheduler,这些进程实现了整个集群的资源管理、Pod调度、弹性伸缩、安全控制、系统监控和
纠错等管理功能,并且都是自动完成的。
Node作为集群中的工作节点,运行真正的应用程序,在Node上Kubernetes管理的最小运行单元是Pod。在Node上运行着Kubernetes的kubelet、kube-proxy服务进程,这些服务进程负责Pod的创建、启动、监控、重启、销毁,以及实现软件模式的负载均衡器。

运维工作

运维工作总会遇到服务扩容和服务升级这两个难题

服务的扩容涉及资源分配(选择哪个节点进行扩容)、实例部署和启动等环节,在一个复杂的业务系统中,这两个难题基本上靠人工一步步操作才得以解决,费时费力又难以保证实施质量。
在Kubernetes集群中,只需为需要扩容的Service关联的Pod创建一个RC(Replication Controller),服务扩容以至服务升级等令人头疼的问题都迎刃而解。

1.2 为什么要用Kubernetes

1.docker的舵手

当前,Docker这门容器化技术已经被很多公司采用,从单机走向集群已成为必然,Kubernetes作为当前被业界广泛认可和看好的基于Docker的大规模容器化分布式系统解决方案,得到了以谷歌为首的IT巨头们的大力宣传和持续推进。

2.精简开发团队

只需一名架构师负责系统中服务组件的架构设计,几名开发工程师负责业务代码的开发,一名系统兼运维工程师负责Kubernetes的部署和运维,就可以开发复杂系统了

3.拥抱微服务架构

4.可以随时随地将系统整体“搬迁”到公有云上

5.快速扩容/缩容

。。。

1.3 从一个简单的例子开始

运行在Tomcat里的Web App
当我们通过浏览器访问此应用时,就会显示一个表格的页面,数据则来自数据库。此应用需要启动两个容器:Web App容器和MySQL容器,并且Web App容器需要访问MySQL容器。

在Docker时代
在一个宿主机上启动了这两个容器,就需要把MySQL容器的IP地址通过环境变量注入Web App容器里;同时,需要将Web App容器的8080端口映射到宿主机的8080端口,以便在外部访问。

在Kubernetes时代

1.3.1 环境准备

安装Kubernetes和下载相关镜像,然后使用kubeadm快速安装一个Kubernetes集群
注:本书示例中的Docker镜像下载地址为 https://hub.docker.com/u/kubeguide/

1.3.2 启动MySQL服务

首先,为MySQL服务创建一个RC定义文件mysql-rc.yaml
RC(ReplicationController)
replicas=1,表示只能运行一个MySQL Pod实例。当在集群中运行的Pod数量少于replicas时,RC
会根据在spec.template一节中定义的Pod模板来生成一个新的Pod实例

在创建好mysql-rc.yaml文件后,为了将它发布到Kubernetes集群中

Kubernetes根据mysql这个RC的定义自动创建的Pod,此外会发现MySQL Pod对应的容器还多创建了一个来自谷歌的pause容器,这就是Pod的“根容器”

最后,创建一个与之关联的Kubernetes Service—MySQL的定义文件(文件名为mysql-svc.yaml)
运行kubectl命令,创建Service,根据Service的唯一名称,容器可以从环境变量中获取Service对应的Cluster IP地址和端口,从而发起TCP/IP连接请求。

1.3.3 启动Tomcat应用

1.3.4 通过浏览器访问网页

1.4 Kubernetes的基本概念和术语

Kubernetes中的大部分概念如Node、Pod、ReplicationController、Service等都可以被看作一种资源对象,几乎所有资源对象都可以通过Kubernetes提供的kubectl工具(或者API编程调用)执行增、删、改、查等操作并将其保存在etcd中持久化存储。
从这个角度来看,Kubernetes其实是一个高度自动化的资源控制系统,它通过跟踪对比etcd库里保存的“资源期望状态”与当前环境中的“实际资源状态”的差异来实现自动控制和自动纠错的高级功能。

在声明一个Kubernetes资源对象的时候,需要注意一个关键属性:apiVersion。Kubernetes大部分常见
的核心资源对象都归属于v1这个核心API,比如Node、Pod、Service、Endpoints、Namespace、RC、PersistentVolume等。
我们可以采用YAML或JSON格式声明(定义或创建)一个Kubernetes资源对象,每个资源对象都有自己的特定语法格式(可以理解为数据库中一个特定的表)

1.4.1 Master

Kubernetes里的Master指的是集群控制节点,在每个Kubernetes集群里都需要有一个Master来负责整个集群的管理和控制,基本上Kubernetes的所有控制命令都发给它,如果它宕机或者不可用,那么对集
群内容器应用的管理都将失效。

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

  • Kubernetes API Server(kube-apiserver):提供了HTTP Rest接口的关键服务进程,是Kubernetes里所有资源的增、删、改、查等操作的唯一入口,也是集群控制的入口进程。
  • Kubernetes Controller Manager(kube-controller-manager):Kubernetes里所有资源对象的自动化控制中心,可以将其理解为资源对象的“大总管”。
  • Kubernetes Scheduler(kube-scheduler):负责资源调度(Pod调度)的进程,相当于公交公司的“调度室”。
    另外,在Master上通常还需要部署etcd服务,因为Kubernetes里的所有资源对象的数据都被保存在etcd中。

1.4.2 Node

除了Master,Kubernetes集群中的其他机器被称为Node。Node是Kubernetes集群中的工作负载节
点,每个Node都会被Master分配一些工作负载(Docker容器),当某个Node宕机时,其上的工作负载会被Master自动转移到其他节点上。
在每个Node上都运行着以下关键进程。

  • kubelet:负责Pod对应的容器的创建、启停等任务,同时与Master密切协作,实现集群管理的基本功能。
  • kube-proxy:实现Kubernetes Service的通信与负载均衡机制的重要组件。
  • Docker Engine(docker):Docker引擎,负责本机的容器创建和管理工作。

1.4.3 Pod

Pod是Kubernetes最重要的基本概念,每个Pod都有一个特殊的被称为“根容器”的Pause容器。Pause容器对应的镜像属于Kubernetes平台的一部分,除了Pause容器,每个Pod还包含一个或多个紧密相关的用户业务容器。
为什么Kubernetes会设计出一个全新的Pod的概念并且Pod有这样特殊的组成结构?

  • 引入业务无关并且不易死亡的Pause容器作为Pod的根容器,以它的状态代表整个容器组的状态,可以解决难以判断整体容器状态的问题
  • Pod里的多个业务容器共享Pause容器的IP,共享Pause容器挂接的Volume,这样既简化了密切关联的业务容器之间的通信问题,也很好地解决了它们之间的文件共享问题。

Pod其实有两种类型:普通的Pod及静态Pod(Static Pod)。
静态Pod,没被存放在Kubernetes的etcd存储里,而是被存放在某个具体的Node上的一个具体文件中,并且只在此Node上启动、运行。
普通Pod,一旦被创建,就会被放入etcd中存储,随后会被Kubernetes Master调度到某个具体的Node上。

Pod及周边对象
1.Endpoint
Kubernetes为每个Pod都分配了唯一的IP地址,称之为Pod IP。
在Pod里所包含的容器组的定义则在spec一节中声明,包括容器名,镜像,容器端口(containerPort)。。。
Pod的IP加上这里的容器端口(containerPort),组成了一个新的概念—Endpoint,它代表此Pod里的一个服务进程的对外通信地址。
2.Volume
3.Event

1.4.4 Label

Label和Label Selector共同构成了Kubernetes系统中核心的应用模型,使得被管理对象能够被精细地分组管理,同时实现了整个集群的高可用性。

1.4.5 Replication Controller

声明某种Pod的副本数量在任意时刻都符合某个预期值,包括

  • Pod期待的副本数量
  • 用于筛选目标Pod的Label Selector
  • 当Pod的副本数量小于预期数量时,用于创建新Pod的Pod模板(template)

在我们定义了一个RC并将其提交到Kubernetes集群中后,Master上的Controller Manager组件就得到通知,定期巡检系统中当前存活的目标Pod,并确保目标Pod实例的数量刚好等于此RC的期望值,如果有过多的Pod副本在运行,系统就会停掉一些Pod,否则系统会再自动创建一些Pod
在运行时,我们可以通过修改RC的副本数量,来实现Pod的动态缩放(Scaling),这可以通过执行kubectl scale命令来一键完成

通过RC机制,Kubernetes很容易就实现了“滚动升级”(Rolling Update),比如在当前系统中有10个对应的旧版本的Pod,则最佳的系统升级方式是旧版本的Pod每停止一个,就同时创建一个新版本的Pod,在整个升级过程中此消彼长,而运行中的Pod数量始终是10个,几分钟以后,当所有的Pod都已经是新版本时,系统升级完成。

总结:

  • 在大多数情况下,我们通过定义一个RC实现Pod的创建及副本数量的自动控制。
  • 在RC里包括完整的Pod定义模板。
  • RC通过Label Selector机制实现对Pod副本的自动控制。
  • 通过改变RC里的Pod副本数量,可以实现Pod的扩容或缩容。
  • 通过改变RC里Pod模板中的镜像版本,可以实现Pod的滚动升级。

1.4.6 Deployment

Deployment可以把它看作RC的一次升级,让我们可以随时知道当前Pod“部署”的进度。

1.4.7 Horizontal Pod Autoscaler

Pod横向自动扩容(HPA),HPA与之前的RC、Deployment一样,也属于一种Kubernetes资源对象。通过追踪分析指定RC控制的所有目标Pod的负载变化情况,来确定是否需要有针对性地调整目标Pod的副本数量,这是HPA的实现原理

HPA有以下两种方式作为Pod负载的度量指标

  • CPUUtilizationPercentage
  • 应用程序自定义的度量指标,比如服务在每秒内的相应请求数(TPS或QPS)

CPUUtilizationPercentage是一个算术平均值,即目标Pod所有副本自身的CPU利用率的平均值。即目标Pod所有副本自身的CPU利用率的平均值。一个Pod自身的CPU利用率是该Pod当前CPU的使用量除以它的Pod Request的值,比如定义一个Pod的PodRequest为0.4,而当前Pod的CPU使用量为0.2,则它的CPU使用率为50%,这样就可以算出一个RC控制的所有Pod副本的CPU利用率的算术平均值了。如果某一时刻CPUUtilizationPercentage的值超过80%,则意味着当前Pod副本数量很可能不足以支撑接下来更多的请求,需要进行动态扩容,而在请求高峰时段过去后,Pod的CPU利用率又会降下来,此时对应的Pod副本数应该自动减少到一个合理的水平。如果目标Pod没有定义Pod Request的值,则无法使用CPUUtilizationPercentage实现Pod横向自动扩容

1.4.8 StatefulSet

用来管理有状态的集群
先明白一个概念:有状态的集群

  • 每个节点都有固定的身份ID,通过这个ID,集群中的成员可以相互发现并通信
  • 集群的规模是比较固定的,集群规模不能随意变动
  • 集群中的每个节点都是有状态的,通常会持久化数据到永久存储中
  • 如果磁盘损坏,则集群里的某个节点无法正常运行,集群功能受损

如果通过RC或Deployment控制Pod副本数量来实现上述有状态的集群,就会发现第1点是无法满足的,因为Pod的名称是随机产生的,Pod的IP地址也是在运行期才确定且可能有变动的,我们事先无法为每个Pod都确定唯一不变的ID。另外,为了能够在其他节点上恢复某个失败的节点,这种集群中的Pod需要挂接某种共享存储,为了解决这个问题,Kubernetes从1.4版本开始引入了PetSet这个新的资源对象,并且在1.5版本时更名为StatefulSet,StatefulSet从本质上来说,可以看作Deployment/RC的一个特殊变种,它有如下特性。

  • StatefulSet里的每个Pod都有稳定、唯一的网络标识,可以用来发现集群内的其他成员。假设StatefulSet的名称为kafka,那么第1个Pod叫kafka-0,第2个叫kafka-1,以此类推。
  • StatefulSet控制的Pod副本的启停顺序是受控的,操作第n个Pod时,前n-1个Pod已经是运行且准备好的状态
  • StatefulSet里的Pod采用稳定的持久化存储卷,通过PV或PVC来实现,删除Pod时默认不会删除与StatefulSet相关的存储卷(为了保证数据的安全)

1.4.9 Service

1.概述
Service服务也是Kubernetes里的核心资源对象之一,Kubernetes里的每个Service其实就是我们经常提起的微服务架构中的一个微服务,功能就是通过Label Selector来实现Service与其后端Pod副本集群之间的无缝对接的。
2.Kubernetes的服务发现机制
任何分布式系统都会涉及“服务发现”这个基础问题,Kubernetes则采用了直观朴素的思路去解决这个棘手的问题
首先,每个Kubernetes中的Service都有唯一的Cluster IP及唯一的名称,而名称是由开发者自己定义的,部署时也没必要改变,所以完全可以被固定在配置中。接下来的问题就是如何通过Service的名称找
到对应的Cluster IP。Kubernetes通过Add-On增值包引入了DNS系统,把服务名作为DNS域名,这样程序就可以直接使用服务名来建立通信连接了。
3.外部系统访问Service的问题
为了更深入地理解和掌握Kubernetes,我们需要弄明白Kubernetes里的3种IP,这3种IP分别如下。

  • Node IP:Node的IP地址
  • Pod IP:Pod的IP地址
  • Cluster IP:Service的IP地址

1.4.10 Job

1.4.11 Volume

1.4.12 Persistent Volume

1.4.13 Namespace

1.4.14 Annotation

1.4.15 ConfigMap

1


总结

提示:这里对文章进行总结:

例如:以上就是今天要讲的内容,本文仅仅简单介绍了pandas的使用,而pandas提供了大量能使我们快速便捷地处理数据的函数和方法。

Logo

开源、云原生的融合云平台

更多推荐