1 什么是k8s
Kubernetes也称为K8S,其中8是代表中间“ubernete”的8个字符,是Google在2014年开源的一个容器编排引擎,用于自动化容器化应用程序的部署、规划、扩展和管理,它将组成应用程序的容器分组为逻辑单元,以便于管理和发现,用于管理云平台中多个主机上的容器化的应用,Kubernetes 的目标是让部署容器化的应用简单并且高效,很多细节都不需要运维人员去进行复杂的手工配置和处理;
2 k8s能做什么
k8s可以更快的更新新版本,打包应用,更新的时候可以做到不用中断服务,服务器故障不用停机,从开发环境到测试环境到生产环境的迁移极其方便,一个配置文件搞定,一次生成image,到处运行。
通过Kubernetes你可以:
- 快速部署应用
- 快速扩展应用
- 无缝对接新的应用功能
- 节省资源,优化硬件资源的使用
3 学习k8s基础知识
3.1 k8s组成
从系统架构来看,k8s分为2种节点:
- Master 控制节点,做为指挥官;
- Node 工作节点,干活的
3.2 架构图
3.2.1 Master节点
K8S中的Master是集群控制节点,负责整个集群的管理和控制
在Master上运行着以下关键进程:
- kube-apiserver:提供了HTTP Rest接口的关键服务进程,是K8S里所有资源的增删改查等操作的唯一入口,也是集群控制的入口进程
- kube-controller-manager:K8S里所有资源对象的自动化控制中心,集群内各种资源Controller的核心管理者,针对每一种资源都有相应的Controller,保证其下管理的每个Controller所对应的资源始终处于期望状态
- kube-scheduler:负责资源调度(Pod调度)的进程,通过API Server的Watch接口监听新建Pod副本信息,并通过调度算法为该Pod选择一个最合适的Node
- etcd:K8S里的所有资源对象以及状态的数据都被保存在etcd中
3.2.2 Node节点
Node是K8S集群中的工作负载节点,每个Node都会被Master分配一些工作负载,当某个Node宕机时,其上的工作负载会被Master自动转移到其他节点上
在每个Node上都运行着以下关键进程:
- kubelet:负责Pod对应的容器的创建、启停等任务,同时与Master密切协作,实现集群管理的基本功能
- kube-proxy:实现Kubernetes Service的通信与负载均衡机制的重要组件
- Docker Engine:Docker引擎,负责本机的容器创建和管理工作
在默认情况下Kubelet会向Master注册自己,一旦Node被纳入集群管理范围,kubelet进程就会定时向Master汇报自身的信息(例如机器的CPU和内存情况以及有哪些Pod在运行等),这样Master就可以获知每个Node的资源使用情况,并实现高效均衡的资源调度策略。而某个Node在超过指定时间不上报信息时,会被Master判定为失败,Node的状态被标记为不可用,随后Master会触发工作负载转移的自动流程
3.3 Pod
- POD是k8s的最小单位
- POD的IP地址是随机的,删除POD会改变IP
- POD都有一个根容器
- 一个POD内可以由一个或多个容器组成
- 一个POD内的容器共享根容器的网络命名空间
- 一个POD内的网络地址由根容器提供
3.4 Controller
用来管理POD。控制器的种类有很多:
- RC Replication Controller:控制POD有多个副本
- RS ReplicaSet:RC控制的升级版
- Deployment:推荐使用,功能更强大,包含了RS控制器
- DaemonSet:保证所有的Node上有且只有一个Pod在运行
- StatefulSet:有状态的应用,为Pod提供唯一的标识,它可以保证部署和scale的顺序
4.实战
4.1创建pod的过程
- 用户提交创建Pod的请求,可以通过API Server的REST API,也可用Kubectl命令行工具
- API Server处理用户请求,存储Pod数据到etcd
- Schedule通过和API Server的watch机制,查看到新的Pod,尝试为Pod绑定Node
- 过滤主机:调度器用一组规则过滤掉不符合要求的主机,比如Pod指定了所需要的资源,那么就要过滤掉资源不够的主机
- 主机打分:对第一步筛选出的符合要求的主机进行打分,在主机打分阶段,调度器会考虑一些整体优化策略,比如把一个Replication Controller的副本分布到不同的主机上,使用最低负载的主机等
- 选择主机:选择打分最高的主机,进行binding操作,结果存储到etcd中
- Kubelet根据调度结果执行Pod创建操作: 绑定成功后,会启动container,Scheduler会调用API在数据库etcd中创建一个bound pod对象,描述在一个工作节点上绑定运行的所有Pod信息。运行在每个工作节点上的Kubelet也会定期与etcd同步bound pod信息,一旦发现应该在该工作节点上运行的bound pod对象没有更新,则调用Docker API创建并启动Pod内的容器
在这期间,Control Manager同时会根据K8S的mainfiles文件执行RC Pod的数量来保证指定的Pod副本数。而其他的组件,比如Scheduler负责Pod绑定的调度,从而完成整个Pod的创建
5 kubelet、kubectl、kubeadm区别
5.1.kubelet
5.2.kubeadm
5.3.kubectl
6 k8s资源
6.1.名称空间级别(namespace)
6.2.集群级资源:
7 ClusterIP、NodePort、LoadBalance区别
7.1 关系图
7.2 路由图
7.3 service类型
7.3.1 ClusterIp
默认类型,每个Node分配一个集群内部的Ip,这是私有ip,内部可以互相访问,外部无法访问集群内部。 clusterIP主要在每个node节点使用iptables,将发向clusterIP对应端口的数据, 转发到kube-proxy中。然后kube-proxy自己内部实现有负载均衡的方法,并可以查询到这个service下对应pod的地址和端口,进而把数据转发给对应的pod的地址和端口。
7.3.2. NodePort
基于ClusterIp,另外在每个Node上开放一个端口,将service的port映射到每个node的一个指定内部port上,映射的每个node的内部port都一样。将向该端口的流量导入到kube-proxy,然后由kube-proxy进一步导给对应的pod。可以从所有的位置访问这个地址。
7.3.3 LoadBalance
基于NodePort,云服务商在外部创建了一个负载均衡层,会向cloud provider申请映射到service本身的负载均衡,将流量导入到对应Port。要收费的。
LoadBalancer跟nodePort其实是同一种方式。
区别在于LoadBalancer比nodePort多了一步,就是可以调用cloud provider去创建LB来向节点导流。
7.3.4 ExternalName
将外部地址经过集群内部的再一次封装(实际上就是集群DNS服务器将CNAME解析到了外部地址上),实现了集群内部访问即可。要求kube-dns的版本为1.7或以上.
例如你们公司的镜像仓库,最开始是用ip访问,等到后面域名下来了再使用域名访问。你不可能去修改每处的引用。但是可以创建一个ExternalName,首先指向到ip,等后面再指向到域名。所有需要访问仓库的地方,统一访问这个服务即可