背景
这是在HWL负责网校云业务线测试时,给同事分享的基础概念文档。
目录:
一
.
Docker
核心概念
二
. Kubernetes
是什么及架构
三
. Kubernetes
核心概念
四
. Deployment
部署
Pod
操作
一、Docker
核心概念
1、
为什么是Docker
虚拟机:
基础设施(
Infrastructure)。服务器,或者是云主机。
主操作系统(Host Operating System
)。服务器上运行的操作系统
虚拟机管理系统(
Hypervisor)。利用
Hypervisor,可以在主操作系统之上运行多个不同的从操作系统。
从操作系统(
Guest Operating System)。假设你需要运行
3个相互隔离的应用,则需要使用
Hypervisor启动
3个从操作系统,也就是
3个虚拟机。这些虚拟机都非常大,也许有
700MB,这就意味着它们将占用
2.1GB的磁盘空间。更糟糕的是,它们还会消耗很多
CPU和内存。
各种依赖。每一个从操作系统都需要安装许多依赖。
应用。安装依赖之后,就可以在各个从操作系统分别运行应用了,这样各个应用就是相互隔离的。
Docker
:
Docker
守护进程(Docker Daemon
)。Docker
守护进程取代了Hypervisor
,它是运行在操作系统之上的后台进程,负责管理Docker
容器。
各种依赖。对于
Docker,应用的所有依赖都打包在
Docker镜像中,
Docker容器是基于
Docker镜像创建的。
应用。应用的源代码与它的依赖都打包在
Docker镜像中,不同的应用需要不同的
Docker镜像。不同的应用运行在不同的
Docker容器中,它们是相互隔离的。
对比虚拟机与
Docker
Docker守护进程可以直接与主操作系统进行通信,为各个
Docker容器分配资源;它还可以将容器与主操作系统隔离,并将各个容器互相隔离。虚拟机启动需要数分钟,而
Docker容器可以在数毫秒内启动。由于没有臃肿的从操作系统,
Docker可以节省大量的磁盘空间以及其他系统资源。
2、
Docker
架构
Docker使用客户端
– 服务器(
C/S)架构,使用远程
API管理和创建
Docker 容器。
Docker 客户端与
Docker 守护进程通信,后者负责构建、运行和分发
Docker容器。
Docker客户端和守护进程可以在同一系统上运行,也可以将
Docker客户端连接到远程
Docker守护进程。
Docker客户端和守护进程使用
REST API,通过
UNIX套接字或网络接口进行通信。
Client
客户端通过命令行或其他工具与守护进程通信,客户端会将这些命令发送给守护进程,然后执行这些命令。命令使用
Docker API,
Docker客户端可以与多个守护进程通信。
Docker daemon
Docker守护进程(
docker daemon)监听
Docker API请求并管理
Docker对象,如镜像,容器,网络和卷。守护程序还可以与其他守护程序通信以管理
Docker服务。
Docker Host
Docker Host是物理机或虚拟机,用于执行
Docker守护进程的仓库。
Docker Registry
Docker仓库用于存储
Docker镜像,可以是
Docker Hub这种公共仓库,也可以是个人搭建的私有仓库。使用
docker pull或
docker run命令时,将从配置的仓库中提取所需的镜像。使用
docker push命令时,镜像将被推送到配置的仓库。
Docker Image
Docker 镜像可以看作是一个特殊的文件系统,除了提供容器运行时所需的程序、库、资源、配置等文件外,还包含了一些为运行时准备的一些配置参数(如匿名卷、环境变量、用户等)。
镜像可以用来创建
Docker 容器,一个镜像可以创建很多容器。
Docker 提供了一个很简单的机制来创建镜像或者更新现有的镜像,用户甚至可以直接从其他人那里下载一个已经做好的镜像来直接使用。
Docker Container
Docker 利用容器来运行应用。容器是从镜像创建的运行实例。它可以被启动、开始、停止、删除。每个容器都是相互隔离的、保证安全的平台。
可以把容器看做是一个简易版的
Linux 环境(包括
root用户权限、进程空间、用户空间和网络空间等)和运行在其中的应用程序。
3、Docker CLI
4、Dockerfile
5、Docker Compose
Compose 是用于定义和运行多容器
Docker 应用程序的工具。通过
Compose,您可以使用
YML 文件来配置应用程序需要的所有服务。然后,使用一个命令,就可以从
YML 文件配置中创建并启动所有服务。
6、Docker Swarm
集群管理
Swarm是
Docker 引擎内置(原生)的集群管理和编排工具,它将
Docker 主机池转变为单个虚拟
Docker 主机。
Docker Swarm 适用于简单和快速开发至关重要的环境,而
Kubernetes 适合大中型集群运行复杂应用程序的环境。
两者不是竞争对手,各有利弊,因需选择。
二、Kubernetes
是什么及架构
1、k8s
是什么
先来一张
Kubernetes官网的截图,可以看到,官方对
Kubernetes的定义:
Kubernetes(
k8s)是一个自动化部署、扩展和管理容器化应用程序的开源系统。
Kubernetes
这个单词是希腊语,它的中文翻译是
“
舵手
”
或者
“
飞行员
”
。在一些常见的资料中也会看到
“ks”
这个词,也就是
“k8s”
,它是通过将
8
个字母
“ubernete ”
替换为
“8”
而导致的一个缩写。
Kubernetes
为什么要用
“
舵手
”
来命名呢?
这是一艘载着一堆集装箱的轮船,轮船在大海上运着集装箱奔波,把集装箱送到它们该去的地方。
Container
这个英文单词也有另外的一个意思就是
“
集装箱
”
。
Kubernetes
也就借着这个寓意,希望成为运送集装箱的一个轮船,来帮助我们管理这些集装箱,也就是管理这些容器。
这个就是为什么会选用
Kubernetes
这个词来代表这个项目的原因。更具体一点地来说:
Kubernetes
是一个自动化的容器编排平台,它负责应用的部署、应用的弹性以及应用的管理。
2、k8s
能做什么
2.1
调度
Kubernetes
可以把用户提交的容器放到
Kubernetes
管理的集群的某一台节点上去。
Kubernetes
的调度器是执行这项能力的组件,它会观察正在被调度的这个容器的大小、规格。
比如,容器所需要的
CPU
以及它所需要的内存,然后在集群中找一台相对比较空闲的机器来进行一次放置的操作。
2.2
自动修复
Kubernetes
有节点健康检查的功能,它会监测这个集群中所有的宿主机,当宿主机本身出现故障,或者软件出现故障的时候,这个节点健康检查会自动对它进行发现。
接下来
Kubernetes
会把运行在这些失败节点上的容器进行自动迁移,迁移到一个正在健康运行的宿主机上,来完成集群内容器的自动恢复。
2.3
水平伸缩
Kubernetes
有业务负载检查的能力,它会监测业务上所承担的负载,如果这个业务本身的
CPU
利用率或内存占用过高,或者响应时间过长,它可以对这个业务进行一次扩容。
比如,下面的例子中,黄颜色的过度忙碌,
Kubernetes
就可以把黄颜色负载从一份变为三份。接下来,它就可以通过负载均衡把原来打到第一个黄颜色上的负载平均分到三个黄颜色的负载上去,以此来提高响应速度。
3、k8s
的架构
Kubernetes
架构是一个比较典型的二层架构和
server-client
架构。
Master
作为中央管控节点,与
Node
建立连接。
所有
UI
的、
clients
、
user
侧的组件,只会和
Master
进行连接,把希望的状态或者想执行的命令下发给
Master
,
Master
会把这些命令或者状态下发给相应的节点,进行最终的执行。
Kubernetes
的
Master
包含四个主要的组件:
API Server
、
Controller
、
Scheduler
以及
etcd
。
API Server
:提供了资源操作的唯一入口,并提供认证、授权、访问控制、
API注册和发现等机制。
Kubernetes
中所有的组件都会和
API Server
进行连接,组件与组件之间一般不进行独立的连接,都依赖于
API Server
进行消息的传送;
Controller
:控制器,它
负责维护集群的状态,比如故障检测、自动扩展、滚动更新等。
上面的
2
个例子,第
1
个自动对容器进行修复、第
2
个自动水平扩张,都是由
Controller
完成的;
Scheduler
:是调度器,
负责资源的调度,按照预定的调度策略将
Pod
调度到相应的机器上。
例如上面的例子,把用户提交的
pod
,依据它对
CPU
、
memory
请求的大小,找一台合适的节点,进行放置;
etcd
:是一个分布式的存储系统,保存了整个集群的状态,比如
Pod、
Service等对象信息。
API Server
中所需要的原信息都被放置在
etcd
中,
etcd
本身是一个高可用系统,通过
etcd
保证整个
Kubernetes
的
Master
组件的高可用性。
Kubernetes
的
Node
是真正运行业务负载的,每个业务负载会以
Pod
的形式运行。一个
Pod
中运行的一个或者多个容器。
kubelet
:
Master在
Node节点上的
Agent,是
真正去运行
Pod
的组件,
也是
Node
上最关键的组件,负责本
Node节点上
Pod的创建、修改、监控、删除等生命周期管理,同时
Kubelet定时
“
上报
”
本
Node
的状态信息到
API
Server
。
它通过
API Server
接收到所需要
Pod
运行的状态。然后提交到
Container Runtime
组件中。
Container Runtime
:容器运行时。
负责镜像管理以及
Pod
和容器的真正运行(
CRI
),
可以理解为类似
JVM
Storage Plugin
或者
Network Plugin
:对存储跟网络进行管理
在
OS
上去创建容器所需要运行的环境,最终把容器或者
Pod
运行起来,也需要对存储跟网络进行管理。
Kubernetes
并不会直接进行网络存储的操作,他们会靠
Storage Plugin
或者
Network Plugin
来进行操作。用户自己或者云厂商都会去写相应的
Storage Plugin
或者
Network Plugin
,去完成存储操作或网络操作。
Kube-proxy
:
负责为Service
提供cluster
内部的服务发现和负载均衡,
完成
service
组网
在
Kubernetes
自己的环境中,也会有
Kubernetes
的
Network
,它是为了提供
Service network
来进行搭网组网的。真正完成
service
组网的组件是
Kube-proxy
,它是利用了
iptable
的能力来进行组建
Kubernetes
的
Network
,就是
cluster network
。
组件间的通信
步骤说明:
1.
通过
UI
或者
CLI
提交
1
个
Pod
给
Kubernetes
进行部署,这个
Pod
请求首先会提交给
API Server
,下一步
API Server
会把这个信息写入到存储系统
etcd
,之后
Scheduler
会通过
API Server
的
watch
机制得到这个信息:有
1
个
Pod
需要被调度。
2. Scheduler
会根据
node
集群的内存状态进行
1
次调度决策,在完成这次调度之后,它会向
API Server
报告:
“OK
!这个
Pod
需要被调度到
XX
节点上。
”
API Server
接收后,会把这次的操作结果再次写到
etcd
中。
3. API Server
通知相应的节点进行这个
Pod
真正的执行启动。相应节点的
kubelet
会得到通知,然后
kubelet
会去调
Container runtime
来真正去启动配置这个容器和这个容器的运行环境,去调度
Storage Plugin
来去配置存储,
network Plugin
去配置网络。
三、Kubernetes
核心概念
第一个概念:
Pod
Pod
是
Kubernetes
的最小调度以及资源单元。可以通过
Kubernetes
的
Pod API
生产一个
Pod
,让
Kubernetes
对这个
Pod
进行调度,也就是把它放在某一个
Kubernetes
管理的节点上运行起来。
一个
Pod
简单来说是对一组容器的抽象,它里面会包含一个或多个容器
。
比如下图,它包含了两个容器,每个容器可以指定它所需要资源大小
当然,在这个
Pod
中也可以包含一些其他所需要的资源:比如说我们所看到的
Volume
卷这个存储资源。
第二个概念:Volume
管理
Kubernetes
存储,用来声明在
Pod
中的容器可以访问的文件目录,一个卷可以被挂载在
Pod
中一个或者多个容器的指定路径下面。
而
Volume
本身是一个抽象的概念,一个
Volume
可以去支持多种的后端的存储。
Kubernetes
的
Volume
支持很多存储插件,可以支持本地的存储和分布式的存储,比如像
ceph
,
GlusterFS
;也可以支持云存储,比如阿里云上的云盘、
AWS
上的云盘、
Google
上的云盘等等。
第三个概念:Deployment
Deployment
是在
Pod
上更为上层的一个抽象,它可以定义一组
Pod
的副本数目、以及
Pod
的版本。一般用
Deployment
来做应用的真正的管理,而
Pod
是组成
Deployment
最小的单元。
Kubernetes
通过
Controller
(控制器)维护
Deployment
中
Pod
的数目,
Controller
也会去帮助
Deployment
自动恢复失败的
Pod
。
比如,可以定义一个
Deployment
,这个
Deployment
里面需要
2
个
Pod
,当
1
个
Pod
失败的时候,控制器就会监测到,再去新生成
1
个
Pod
,把
Deployment
中的
Pod
数目从
1
个恢复到
2
个。通过控制器,也可以完成发布策略,比如进行滚动升级、重新生成的升级或者进行版本回滚。
第四个概念:Service
Service
:
提供
1
个或者多个
Pod
实例的稳定访问地址
比如,一个
Deployment
可能有
2
个甚至更多个完全相同的
Pod
。对于外部的用户来讲,访问哪个
Pod
都是一样的,所以希望做一次负载均衡,在做负载均衡的同时,只需要访问某一个固定的
VIP
,也就是
Virtual IP
地址,而不需要得知每一个具体的
Pod
的
IP
地址。
如果
1
个
Pod
失败了,可能会换成另外一个新的。提供了多个具体的
Pod
地址,对外部用户来说,要不停地去更新
Pod
地址。当这个
Pod
再失败重启之后,如果有一个抽象,把所有
Pod
的访问能力抽象成
1
个第三方的
IP
地址,实现这个的
Kubernetes
的抽象就叫
Service
。
实现
Service
有多种入口方式:
第五个概念:Namespace
Namespace
:用来做一个集群内部的逻辑隔离,包括鉴权、资源管理等。
Kubernetes
的每个资源,比如
Pod
、
Deployment
、
Service
都属于一个
Namespace
,同一个
Namespace
中的资源需要命名的唯一性,不同的
Namespace
中的资源可以重名。
K8S
的
API
Kubernetes API
是由
HTTP+JSON
组成的:用户访问的方式是
HTTP
,访问
API
中
content
的内容是
JSON
格式的。
用
Kubectl
命令、
Kubernetes UI
或者
Curl
,直接与
Kubernetes
交互都是使用
HTTP + JSON
的形式。
如下图,对于这个
Pod
类型的资源,它的
HTTP
访问的路径就是
API
,
apiVesion: V1,
之后是相应的
Namespaces
,以及
Pods
资源,最终是
Podname
,也就是
Pod
的名字。
当提交一个
Pod
,或者
get
一个
Pod
的时候,它的
content
内容都是用
JSON
或者是
YAML
表达的。上图中
YAML
的例子,在这个
YAML
文件中,对
Pod
资源的描述分为几个部分。
第一个部分,一般是
API
的
version
。比如在这个例子中是
V1
,它也会描述我在操作哪个资源;
kind
如果是
pod
,在
Metadata
中,就写上这个
Pod
的名字;比如
nginx
。也会给
pod
打一些
label
,在
Metadata
中,有时候也会去写
annotation
,也就是对资源的额外的一些用户层次的描述。
比较重要的一个部分叫
Spec
,
Spec
也就是希望
Pod
达到的一个预期的状态。比如
pod
内部需要有哪些
container
被运行;这里是一个
name
为
nginx
的
container
,它的
image
是什么?它暴露的
port
是什么?
当从
Kubernetes API
中去获取这个资源的时候,一般在
Spec
下面会有一个
status
字段
,它表达了这个资源当前的状态;比如一个
Pod
的状态可能是正在被调度、或者是已经
running
、或者是已经被
terminates
(被执行完毕)。
Label
是一个比较有意思的
metadata
,可以是一组
KeyValue
的集合。
如下图,第一个
pod
中,
label
就可能是一个
color
等于
red
,即它的颜色是红颜色。当然也可以加其他
label
,比如说
size: big
就是大小,定义为大的,它可以是一组
label
。
这些
label
是可以被
selector
(选择器)所查询的。就好比
sql
类型的
select
语句。
通过
label
,
kubernetes
的
API
层就可以对这些资源进行筛选。
例如,
Deployment
可能代表一组
Pod
,是一组
Pod
的抽象,一组
Pod
就是通过
label selector
来表达的。当然
Service
对应的一组
Pod
来对它们进行统一的访问,这个描述也是通过
label selector
来选取的一组
Pod
。
四、Depolyment
部署pod
操作
屏幕。。。