本文介绍Kubernetes(K8S)。
1. kubernetes介绍
本章节主要介绍应用程序在服务器上部署方式演变以及kubernetes的概念、组件和工作原理。
1.1 应用部署方式演变
在部署应用程序的方式上,主要经历了三个时代:
传统部署:互联网早期,会直接将应用程序部署在物理机上
优点:简单,不需要其他技术的参与。
缺点:不能为应用程序定义资源使用边界,很难合理地分配计算资源,而且程序之间容易产生影响。简单地说,一个操作系统上的资源是有限的,而这些应用程序是共享这些资源的,如果没有边界限制,假如某个应用程序发生了内存泄露,此时必然后干扰其他内存,也就有可能干扰其他应用程序。
虚拟化部署:在一台物理机上运行多个虚拟机,每个虚拟机都是独立的一个环境
为了解决传统部署的缺点,本质上应该就是一台物理机部署一个应用程序,但是这样会造成成本增加以及资源浪费。因此,为了折衷,采用虚拟化部署。在一台物理主机上虚拟化(Hypervisor)多个系统,即多台虚拟机,每台虚拟机都类似于一个物理机。这样可在一定程度上解决了应用程序之间的影响,即解决了边界问题。
优点:程序环境不会相互产生影响,提供了一定的安全性。
缺点:增加了虚拟操作系统,浪费了部分资源。简单地说,就是本身物理机存在了操作系统,此时仍然虚拟出操作系统,这是对资源的浪费。或者说,虚拟机连硬件也模拟,存在一定的资源浪费。
容器化部署:与虚拟化类似,但是共享了操作系统
容器,就是常见的Docker技术,仅虚拟软件环境,对硬件不需要模拟,也无需模拟操作系统,即共享了操作系统(Container Runtime)。
优点:
- 可以保证每个容器拥有自己的文件系统、CPU、内存、进程空间等;
- 运行应用程序锁需要的资源都被容器包装,并和底层基础架构解耦;
- 容器化的应用程序可以跨云服务商、跨Linux操作系统发行版进行部署;
1.2 容器化部署需要考虑的问题
容器化部署相较于上面两种部署方式存在一定的优点,那么也需要考虑一些问题,比如说:
- 一个容器故障停机了,怎么样让另一个容器立刻启动去替补停机的容器;
- 当并发访问量变大的时候,怎么样做到横向扩展容器数量;
这些容器管理的问题统称为容器编排问题,为了解决这些容器编排问题,就产生了一些容器编排的软件:
- Swarm:Docker自己的容器编排工具;
- Mesos:Apache的一个资源统一管控的工具,需要和Marathon结合使用;
- Kubernetes:Google开源的容器编排工具;
2019年的市场占有率如下所示,K8S还是一家独大的。
1.3 kubernetes简介
kubernetes是一个全新的基于容器技术的分布式架构领先方案,是谷歌Borg系统的一个开源版本,于2014年9月发布第一个版本,2015年7月发布第一个正式版本。https://kubernetes.io/。
kubernetes的本质是一组服务器集群,它可以在集群的每个节点上运行特定的程序,来对节点中的容器进行管理。它的目标就是实现资源管理的自动化,主要提供了如下的主要功能:
- 自我修复:一旦某个容器崩溃,能够在1秒左右迅速启动新的容器
- 弹性伸缩:可以根据需要,自动对集群中正在运行的容器数量进行调整
- 服务发现:服务可以通过自动发现的形式找到它所依赖的服务
- 负载均衡:如果一个服务启动了多个容器,能够自动实现请求的负载均衡
- 版本回退:如果发现新发布的程序版本有问题,可以立即回退到原来的版本
- 存储编排:可以根据容器自身的需求自动创建存储卷。
个人感觉和Nginx有一点类似,Nginx用于各个服务管理,并且自身也可以作为静态的资源服务器。而kubernetes是k8s集群,在集群的每个节点上都安装特定的程序,通过这些程序来管理节点上的容器,以及节点之间联动。
如下图所示,蓝框就是若干个kubernetes节点,构成了集群。每个集群节点都运行了多个容器,kubernetes就是通过在节点上安装程序来对节点内部的容器进行管理,以及节点之间的容器综合管理。
1.4 kubernetes组件
一个kubernetes集群主要是由控制节点(master)、工作节点(node)构成,每个节点上都会安装不同的组件。
1.4.1 控制节点(master)
控制节点是集群的控制平面,负责集群的决策。控制节点就是控制管理的。包含四个组件:
- ApiServer:资源操作的唯一入口,接收用户输入的命令,提供认证、授权、API注册和发现等机制
- Scheduler:负责集群资源调度,按照预定的调度策略将Pod调度到相应的node节点上
- ControllerManager:负责维护集群的状态,比如程序部署安排、故障检测、自动扩展、滚动更新等
- Etcd:负责存储集群中各种资源对象的信息(注意,这里的Etcd是默认的具体的服务,可以用MySQL,这里相当于某个数据库,可以手动配置。)
通过上面的图可以看出,kuberctl是客户端访问的入口,而ApiServer则是整个集群接收控制指令的入口。而Scheduler负责调度资源,即计算决定由哪个工作节点来执行任务。ControllerManager则是保存集群的状态,安排具体的节点来工作【注意,这里的安排指的是通知,并不是决定哪个节点工作】。Etcd是用于存储节点的信息,比如这个节点的某个容器在运行,另一个节点的某个容器在等候,有点像数据库(或者是消息队列)。
1.4.2 工作节点(node)
工作节点是集群的数据平面,负责为容器提供运行环境。包含是三个组件:
- Kuberlet:负责维护容器的生命周期,即通过控制docker,来创建、更新、销毁容器
- KubeProxy:负责提供集群内部的服务发现和负载均衡
- Docker:负责节点上容器的各种操作
Kuberlet相当于工作节点接收控制节点命令的负责人,接收完之后,并控制Docker来执行。KuberProxy即代理,通过它来访问具体的程序(docker容器)。
1.4.3 组件调用流程
以部署一个nginx服务来说明kubernetes系统各个组件调用关系:
- 首先要明确,一旦kubernetes环境启动之后,master和node都会将自身的信息存储到etcd数据库中;方便知道哪些控制节点和工作节点是正常工作的。为后续的计算调用做准备。
- 一个nginx服务的安装请求首先会被发送到master节点的ApiServer组件。
- ApiServer组件会调用Scheduler组件来决定到底应该把这个服务安装到哪个node节点上。在此时,它会从Etcd数据库中读取各个node节点的信息,然后按照一定的算法进行选择,并将结果告知ApiServer。
- ApiServer调用ControllerManager取调用这个node节点安装nginx服务。
- 工作节点中的Kuberlet接收到指令后,回通知Docker,然后由Docker来启动一个nginx的pod。【pod是kubernetes的最小操作单元,容器必须跑在pod中,个人认为,k8s只能通过某个东西来管理容器,即pod】
- 至此,一个nginx服务就运行了,如果需要访问nginx(即获取服务),就需要通过KubeProxy来对pod产生访问的代理。这样,外界用户就可以访问集群中的nginx服务了。
通过上面的步骤,可以看到,kubernetes主要提供了两个功能:
- 对集群的控制,比如安装某项服务,通过ApiServer来接收指令即可。而具体是哪个工作节点安装,则由内部决策来控制;
- 提供访问服务的接口KuberProxy,通过暴露出KuberProxy,来访问pod,并对外提供服务。
1.5 kubernetes概念
- Master:集群控制节点,每个集群需要至少一个master节点负责集群的管控。
- Node:工作负载节点,由master分配容器到这些node工作节点上,然后node节点上的docker负责容器的运行。
- Pod:kubernetes的最小控制单元,容器都是运行在pod中的,一个pod中可以有1个或者多个容器。k8s通过控制Pod来控制容器,进而控制程序。
- Controller:控制器,通过它来实现对pod的管理,比如启动pod、停止pod、伸缩pod的数量等。k8s中有很多种控制器。
- Service:pod对外服务的统一入口,可以维护同一类的多个pod。
- Label:标签,用于对pod进行分类,同一类pod会拥有相同的标签。
- NameSpace:命名空间,用来隔离pod的运行环境。即pod之间是可以相互访问的,如果不想访问,只能隔离起来,类似局域网、VLAN。
如下图所示,紫色就是Pod,每个Pod都运行着一个Tomcat服务器,那么Pod怎么对外提供服务呢?即通过Service,在Service中可以实现负载均衡。
2. 集群环境搭建
本节介绍如何搭建kubernetes的集群环境。
2.1 环境规划
2.1.1 集群类型
kubernetes集群大体上分为两类:一主多从和多主多从。
- 一主多从:一台Master节点和多台Node节点,搭建简单,但是有单机故障风险,适合用于测试环境。
- 多主多从:多台Master节点和多台Node节点,搭建麻烦,安全性高,适合用于生产环境。
为了简单起见,本文搭建一主两从类型的集群。
2.1.2 安装方式
kubernetes有多重部署方式,目前主流的方式有kubeadm、minikube、二进制包。
- minikube:一个用于快速搭建单节点kubernetes的工具
- kubeadm:一个用于快速搭建kubernetes集群的工具
- 二进制包:从官网下载每个组件的二进制包,依次去安装,此方式对于理解kubernetes组件更加有效
由于现在需要安装kubernetes的集群环境,但是又不想过于麻烦,所以选择使用kubeadm方式。
2.1.2 主机规划
2.2 环境搭建
2.3 服务部署
3. 资源管理
4. 备注
参考B站《黑马程序员》。