第一章 kubernetes简介


kubernetes简介


kubernetes 的本质是一组服务集群,每个节点上运行特定的程序,来对节点中的容器进行管理,主要的功能如下 :

  • 自我修改 :一旦某个容器崩溃,能够在1秒左右迅速启动新的容器
  • 弹性伸缩 :可以根据需要,自动对集群中正在运行的容器数量进行调整
  • 服务发现 :服务可以通过自动发现的形式找到它对依赖的服务
  • 负载均衡 :如果一个服务启动了多个容器,能够自动实现请求的负载均衡
  • 版本回退 : 如果发现新发布的程序版本有问题,可以立即回退到原来的版本
  • 存储编排 :可以根据容器自身的需求启动创建存储卷

1.1、kubernetes组件


主要有控制节点(Master)、工作节点(node)构成,每个节点上安装不同的组件

1.1.1、master 节点

**集群控制平面,负责集群的决策(管理) **

  • ApiServer : 资源操作的唯一入口,接收用户输入的命名,提供认证,授权,API注册和发现等机制
  • Scheduler : 负责集群资源调度,按照预定的调度策略将 Pod 调度到相应的 node节点上
  • ControllerManager : 负责维护集群的状态,比如程序部署安排,故障监测,自动扩展,滚动更新
  • Etcd :负责存储集群中各种资源对象信息(键值对数据库)
1.1.2、node 节点

集群的数据平面,负责为容器提供运行环境

  • Kubelet : 负责维护容器的生命周期,即通过控制 docker 来创建,更新,销毁容器
  • KubeProxy : 提供集群内容的服务发现和负载均衡(pod与pod之间的访问),通过操作防火墙实现端口映射,将路由规则写入至 IPtables、IPVS实现服务映射
  • Docker : 负责节点容器的各种操作
1.1.3、其他组件

  • CoreDNS : 可以为集群中的 SVC创建一个域名IP的对应关系解析
  • DashBoard :给K8S集群提供一个 B/S 结构访问体系
  • Ingress Controller :官方只能实现 四 层代理,InGress 可以实现 7层代理
  • Fedetation : 提供一个可以跨集群中心多 K8S统一管理的功能
  • Prometheus : 提供 K8S集群的监控能力
  • ELK : 提供K8S集群日志统一分析介入平台
1.1.4、组件关系举例说明

  • 环境启动后,masterh和node都会将自身的信息存储到 ETCD数据库中
  • 一个nginx服务的安装请求会首先发送到 master 节点的 apiServer组件
  • apiServer 组件会调用 Schedule组件来决定到底应该将服务安装到哪个 Node节点上
  • apiServer调用 controller-manager去调度Node节点安装nginx服务
  • Kubelet 接收到指令后,会通知docker,然后由 docker来启动 一个nginx 的pod
  • 如果需要访问Nginx,需要通过kube-proxy来对 pod 产生访问代理。

1.2、kubernetes概念


1.2.1、术语介绍

  • Pod : 最小控制单元,容器运行在Pod中,一个Pod 中可以有1个或多个容器
  • Controller : 控制器,通过它来实现对 Pod的管理,比如启动 Pod、停止Pod、伸缩Pod的数量
  • Service : Pod 对外服务的统一入口,下面可以维护同一类的的多个Pod
  • Label : 标签,用于对Pod进行分类,同一个Pod会拥有相同的标签
  • NameSpace : 命令空间,用于隔离Pod的运行环境
1.2.2、网络通信模式

  • 同Pod内多个容器的通信 : 公共Pause网络栈进行通信,共享同一个网络命令空间,共享同一个linux协议栈
  • Pod之间的通信 : Overlay Network
  • Flanneld 是针对 K8S 设计的网络规划服务,主要功能为让集群中,不同节点主机创建的 Docker容器都具集群唯一的虚拟IP地址 。而且它能在这些 IP地址间建立一个 覆盖网络(Overlay Network),通过这个覆盖网络,将数据包传递到目标容器内
  • Pod与Service之间的通信 - 各节点的 IPtables规则(当前通过LVS进行转发)
  • Pod 到外网 :查找路由表,转发数据到宿主机网卡,宿主机网卡完成路由选择后,由 IPtabes执行 Masquerade,将源IP更改为宿主网卡IP,然后向外 网服务器发送请求。
1.2.3、通信方式 :

  • 同服务器上的两个 Pod 通信 : 走Docker0 的网桥进行通信
  • 不同服务器上的 Pod 通信 : 通过Flannel 进行通信
  • 将各个 Flannel可分配的 IP网段资源注册到 ETCD 中
  • Fannel监控 ETCD中每个 Pod实际地址,并在内存中建立 Pod节点路由表

第二章 集群环境搭建


2.1、集群类型


  • 集群大体分成两类 : 一主多从,和多主多从

2.2、安装方式


  • minikube :快速搭建单节点kubernetes工具
  • kubeadm : 快速搭建kubernetes集群工具
  • 二进制包 :官网下载,依次安装,有利于理解

2.3、环境初始化


作用

IP地址

配置

Master

192.168.80.121

2C / 4G

Node1

192.168.80.122

2C / 4G

Node2

192.168.80.123

2C / 4G

  1. 检查操作系统的软件版本
# 三台服务器
[root@linux123 ~]# cat /etc/redhat-release 
CentOS Linux release 7.6.1810 (Core)
  1. 主机名解析
[root@linux121 ~]# cat /etc/hosts
localhost6.localdomain6
192.168.80.121 linux121
192.168.80.122 linux122
192.168.80.123 linux123
  1. 时间同步
# 三台服务器

# 启动chronyd服务
[root@linux121 ~]$ systemctl start chronyd
# 设置chronyd服务开机自启
[root@linux121 ~]$ systemctl enable chronyd
# chronyd 服务启动稍后等几分钟,就可时候用date命令验证时间了
[root@linux121 ~]$ date
  1. 禁用 iptables 和 firewalld服务
    docker 和 kubernetes 在运行时会产生大量的 iptables规则,为了不让系统规则跟他们混淆,直接关闭系统规则
# 1、关闭防火墙
[root@linux121 ~]# systemctl stop firewalld
[root@linux121 ~]# systemctl disbale firewalld

# 2、关闭iptables服务
[root@linux121 ~]# systemctl stop iptables
[root@linux121 ~]# systemctl disbale iptables
  1. 禁用Selinux
    selinux 是linux系统下一个安全服务,如果不关闭它,在安装集群会产生各种奇葩问题
# 编辑 /etc/selinux/config 文件,修改selinux 的值为 disabled
# 注意修改完成后,需要重启 linux服务
SELINUX = disabled
  1. 禁用 swap分区
# 编辑分区配置文件 /etc/fstab,注释掉swap分区一行
# 注意修改完成后,需要重启 linux服务

# /dev/mapper/centos-swap swap            swap  defults 0 0
  1. 修改linux的内核参数
# 修改linux的内核参数,添加网桥过滤和地址转发功能
# 编辑 /etc/sysctl.d/kubernetes.conf 文件,添加如下配置
net.bridge.bridge-nf-call-ip6tables=1
net.bridge.bridge-nf-call-iptables=1
net.ipv4.ip_forward=1

# 重载加载配置
[root@linux121 ~]# sysctl -p

# 加载网桥过滤模块
[root@linux121 ~]# modprobe br_netfilter

# 查看网桥过滤模块是否加载成功
[root@linux121 ~]# lsmod | br_netfilter
  1. 配置 ipvs 功能
    在 kubernetes 中 service有两种代理模型,一种基于 iptables, 一种基于ipvs的,两者比较,ipvs的性能明显高一些,但如果要使用需要手动载入 ipvs模块
# 1 安装 ipset 和 ipvsadm
[root@linux121 ~]# yum install ipset ipvsadmin -y

# 2 添加需要加载的模块写入脚本文件
[root@linux121 ~]# cat <<EOF> /etc/sysconfig/modules/ipvs.modules

#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_sh
modprobe -- nf_conntrack_ipv4
EOF

# 3、为脚本文件添加执行权限
[root@linux121 ~]# chmod +x /etc/sysconfig/modules/ipvs.modules

# 4、执行脚本文件
[root@linux121 ~]# /bin/bash /etc/sysconfig/modules/ipvs.modules

# 5、查看对应的模块是否加载成功
[root@linux121 ~]# lsmod | grep -e ip_vs -e nf_conntrack_ipv4
  1. 重启服务器
    上面步骤完成后,需要重启 linux系统
[root@linux121 ~]# reboot

可能出现的问题

# master节点分类的 CPU最小为2个
# swap 空间没关闭
# 需要调整一个参数

[root@linux121 ~]# kubeadm init --kubernetes-version=v1.17.4 --pod-network-cidr=10.224.0.0/16 --service-cidr=10.96.0.0/12 --apiserver-advertise-address=192.168.80.121
W0828 06:20:32.438991    8797 validation.go:28] Cannot validate kube-proxy config - no validator is available
W0828 06:20:32.439077    8797 validation.go:28] Cannot validate kubelet config - no validator is available
[init] Using Kubernetes version: v1.17.4
[preflight] Running pre-flight checks
	[WARNING IsDockerSystemdCheck]: detected "cgroupfs" as the Docker cgroup driver. The recommended driver is "systemd". Please follow the guide at https://kubernetes.io/docs/setup/cri/
	[WARNING SystemVerification]: this Docker version is not on the list of validated versions: 20.10.17. Latest validated version: 19.03
error execution phase preflight: [preflight] Some fatal errors occurred:
	[ERROR FileContent--proc-sys-net-bridge-bridge-nf-call-iptables]: /proc/sys/net/bridge/bridge-nf-call-iptables contents are not set to 1
	[ERROR Swap]: running with swap on is not supported. Please disable swap


[root@linux121 ~]# echo "1" >/proc/sys/net/bridge/bridge-nf-call-iptables

2.4、Docker 安装


# 集群全部服务器

#0、切换镜像源
wget https://morrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo -o /etc/yum.repos.d/docker-ce.repo

# 查看当前镜像源中支持的docker版本
yum list docker-ce --showduplicates

# 1、yum 包更新到最新
yum update
# 2、安装需要的软件包
yum install -y yum-utils device-mapper-persistent-data lvm2
 
# 3、设置yum源,设置镜像仓库
yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo

# 阿里云镜像
yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo

# 4、安装docker及相关的包,出现输入的界面都按 y
# docker-ce 社区版
yum install -y docker-ce docker-ce-cli containerd.io

# 5、启动docker
systemctl start docker

# 6、查看docker版本、验证是否验证成功
docker -v

# 7、设置开机自启
systemctl enable docker 

# 8、查看哪些服务设置了开机自启 【STATE状态为 enable】
systemctl list-unit-files

2.5、安装 kubernetes 组件


安装 kubernetes组件

# 切换国内镜像源
# 编辑 /etc/yum.repos.d/kubernetes.repo 添加如下配置
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64/
enabled=1
gpgcheck=0
repo_gpgcheck=0
gpgkey=https://mirrors.aliyun.com/kubernetes/yum/doc/yum-key.gpg https://mirrors.aliyun.com/kubernetes/yum/doc/rpm-package-key.gpg


# 安装kubeadm、kubelet 和 kubectl [集群全部服务器均安装]
[root@linux121 ~]$ yum install --setopt=obsoletes=0 kubeadm-1.17.4-0 kubelet-1.17.4-0 kubectl-1.17.4-0 -y


# 配置kubelet的cgroup 
# 编辑 /etc/sysconfig/kubelet, 添加下面配置
KUBELET_CGROUP_APGS="--cgroup-driver=systemd"
KUBE_PROXY_MODE="ipvs"     # 调整代理模式


# 设置kubelet开机自启
[root@linux121 ~]# systemctl enable kubelet

2.6、准备集群镜像


# 安装kubernetes集群前,需要准备好集群镜像,镜像可以通过命令查看
[root@linux121 ~]# kubeadm config images list


# 第二种方式,下载镜像
# 此镜像在kubernetes的仓库中,由于网络原因无法连接,下面提供一种替代方案

images=(
	kube-apiserver:v1.17.4
	kube-controller-manager:v1.17.4
	kube-scheduler:v1.17.4
	kube-proxy:v1.17.4
	pause:3.1
	etcd:3.4.3-0
	coredns:1.6.5
)

for imageName in ${images[@]} : do
	docker pull registry.cn-hangzhou.aliyuncs.com/google_containers/$imageName
	docker tag registry.cn-hangzhou.aliyuncs.com/google_containers/$imageName k8s.gcr.io/$imageName
	docker rmi registry.cn-hangzhou.aliyuncs.com/google_containers/$imageName
done

2.7、集群初始化


  • 对集群进行初始化,并将node节点加入到集群中

Master节点

# 创建集群 (将下载好的镜像进行安装)
[root@linux121 ~]# kubeadm init \
	--kubernetes-version=v1.17.4 \
	--pod-network-cidr=10.224.0.0/16 \
	--service-cidr=10.96.0.0/12 \
	--apiserver-advertise-address=192.168.109.100

# kubernetes-version=v1.17.4 版本信息
# pod-network-cidr=10.224.0.0/16 pod网络
# server-cidr=10.96.0.0/12  service网络
# apiserver-advertise-address=192.168.109.100  master节点地址

# 创建必要文件(执行kubectl的一些依赖文件,初始化成功信息中会有提示自行此操作)
[root@linux121 ~]# mkdir -p $HOME/.kube
[root@linux121 ~]# sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
[root@linux121 ~]# sudo chown $(id -u):$(id -g) $HOME/.kube/config

node节点执行

# 将node节点加入集群【192.168.109.100 为主节点】
# 前面的操作完成后 ,会有对这一步的提示

			
[root@linux121 ~]# kubeadm join 192.168.80.121:6443 --token 4x0k8r.zzdqfnuo1kqv0a55 \
>     --discovery-token-ca-cert-hash sha256:e4d16c161369d3d2e4d5b0b45d201dacdd436f26da8c56e87a72b7711e913358


[root@linux122 ~]# kubeadm join 192.168.80.121:6443 --token 4x0k8r.zzdqfnuo1kqv0a55 \
>     --discovery-token-ca-cert-hash sha256:e4d16c161369d3d2e4d5b0b45d201dacdd436f26da8c56e87a72b7711e913358

[root@linux123 ~]# kubeadm join 192.168.80.121:6443 --token 4x0k8r.zzdqfnuo1kqv0a55 \
>     --discovery-token-ca-cert-hash sha256:e4d16c161369d3d2e4d5b0b45d201dacdd436f26da8c56e87a72b7711e913358
# 查看集群状态 此时的集群状态为 notready,这是因为还没配置网络插件
[root@linux121 ~]# kubectl get nodes

2.8、安装网络插件


支持很多网络插件,比如 flannel、calico、canal等,任选一种即可,本次选择 flannel

下列操作只需要在 Master 节点操作即可,插件使用的是 DaemonSet 的控制器,它会在每个节点上运行

# 获取 fannel 的配置文件
[root@linux121 ~]# wget https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml

# 修改 kube-flannel.yml 文件中 quay.io 仓库为 quay-mirror.qiniu.com

# 使用配置文件启动 fannel
[root@linux121 ~]# kubectl appy -f kube-flannel.yml

# 查看集群状态
[root@linux121 ~]# kubectl get nodes

至此搭建完成

2.9、服务部署测试


集群环境测试

# 部署nginx
[root@linux121 ~]# kubectl create deployment nginx --image=niginx:1.14-alpine

# 暴漏端口
[root@linux121 ~]# kubectl expose deployment nginx --port=80 --type=NodePort

# 查看服务器状态
[root@linux121 ~]# kubectl get pods,svc

第三章 YAML语言


3.1、资源管理

语法 :

  • 大小写敏感
  • 缩进表示层级关系
  • 缩进只允许使用空格,不允许使用tab(只对低版本生效)
  • 缩进空格数量不重要,主要左对齐即可
  • 、# 号表示注释

支持数据类型

  • 纯量 :单个的,不可区分的 (值、字符串、布尔、整数、浮点、Null、时间、日期)
  • 对象 :键值对的集合,又称为映射(Mapping)/ 哈希(hash)/字典(dictinary)
  • 数组 :一组按次序排列的值,又称为序列(sequence)/ 列表(list
    注意 :冒号后面 + 空格

3.2、资源管理方式

声明式对象配置 : 通过apply命令和配置文件去操作kubernetes资源

  • 命令式对象该管理 :直接使用命令操作 kubernetes 资源 - (简单、无审计跟踪)
kubectl run nginx-pod --image=nginx:1.17.1 --port=80
  • 命令式对象配置 : 通过命令配置和配置文件去操作kubernetes资源 - (配置文件多,操作麻烦)
kubectl create/patch -f nginx-pod.yaml
  • 声明式对象配置 : 通过apply命令和配置文件去操作kubernetes资源 - (支持目录操作,意外情况下,调试困难)
# 只用于创建和更新功能,没有则创建,有则更新
kubectl apply -f nginx-pod.yaml

3.3、命令式对象管理


kubectl 为集群命令行工具,能够对集群进行管理。

# 语法
kubectl   [command]   [type]   [name]   [flags]

comand : 指定要对资源的操作 , 例如 create 、get 、delete

type : 指定资源类型 ,例如 deployment 、pod 、service

name :指定资源名称、名称大小敏感

flags : 指定额外的可选参数

# 查看所有pod
kubectl get pod

# 查看某个pod
kubectl get pod pod_name

# 查看某个pod,以yaml格式展示
kubectl get pod pod_name -o yaml

3.4、K8S常用命令


基本命令

命令

翻译

命令作用

create

创建

创建资源

edit

编辑

编辑资源

get

获取

获取资源

patch

更新

更新资源

delete

删除

删除资源

explain

解释

展示资源

# 查看pod调度节点及 pod_ip, -n 指定命名空间
kubectl -n pod_name_space get pod -o wide

# 查看完整的 yaml
kubectl -n pod_name_space get pod pod_name -o yaml

# 查看pod的明细信息及事件
kubectl -n pod_name_space describe pods pod_name


# 查看Pod 或 Pod内容器的日志
kubectl log myapp-pod -c testcontainer

运行和调试

命令

翻译

命令作用

run

运行

在集群张运行一个指定的镜像,默认使用pod控制器

expose

暴露

暴露资源为Service

describe

描述

显示资源内部信息

logs

日志

输出容器在Pod中的日志

attach

缠绕

进入运行中的容器

exec

执行

执行容器中的一个命令

cp

复制

在Pod内外复制文件

rollout

首次展示

管理资源的发布

scale

规模

扩(缩)容Pod的数量

autoscale

自动调整

自动调整Pod的数量

# 进入Pod内的容器
kubectl -n <namesapace> exec <pod_name> -c <container_name> -ti /bin/sh

# 查看 pod 内容器日志,显示标准或者错误输出日志
kubectl -n <namesapace> logs -f <pod_name> -c <container_name>

# 查看日志信息
kubectl -n <namesapace> logs -f --tail=100 <pod_name> -c <container_name>

高级命令&其他命令

命令

翻译

命令作用

apply

应用更新

更新

label

标签

标签

cluster-info

集群信息

显示集群信息

version

版本

显示当前Server 和 Client 的版本

# 更新pod版本
kubectl apply -f demo-pod.yaml

3.5、服务资源清单


集群级别

资源名称

缩写

资源作用

nodes

no

集群组成部分

namespaces

ns

隔离Pod

Pod资源控制器

资源名称

缩写

作用

replicationcontrollers

rc

pod控制器

replicasets

rs

pod控制器

deployments

deploy

pod控制器

daemonsets

ds

pod控制器

jobs

pod控制器

cronjobs

cj

pod控制器

horizontalpodautoscalers

hpa

pod控制器

statefulsets

sts

pod控制器

服务资源

资源名称

缩写

作用

services

svc

统一pod对外出口

ingress

ing

统一pod对外出口

存储资源

资源名称

缩写

作用

volumeattachments

存储

persistentvolumes

pv

存储

persistentvolumeclaims

pvc

存储

配置资源

资源名称

缩写

作用

congigmaps

cm

配置

secrets

配置

# 创建namespace
kubectl create namespace dev

# 获取namespace
kubectl get ns

# 在此namespace下创建并运行一个nginx的pod
# run 默认为使用pod控制器
kubectl run pod --image=nginx -n dev

# 查看新创建的pod -n 指定命名空间
kubectl get pod -n dev

# 查看pod创建过程
kubectl describe pods [pod名/id] -n dev

# 删除指定pod
kubectl delete pod pod-253434543453-pcw7x

3.6、命令式对象配置


创建一个nginxpod.yaml

apiVersion : v1
kind : Namespace 
metadata :
	name : dev


# 两端内容需要用 --- 进行分割	
---


apiVersion : v1
kind : Pod
metadata :
	name : nginxpod
	namespace : dev
spec :
	containers :
	- name : nginx-containers
	  image : nginx:1.17.1

执行 create命令,创建资源:

# 文件执行命令
kubectl create -f nginxpod.yaml

# 执行get命令,查看资源
kubectl get -f nginxpod.yaml

# 执行 delete 命令,删除资源
kubectl delete -f nginxpod.yaml

3.7、声明式对象配置


仅用于新增更新

kubectl apply -f nginxpod.yaml
  • 如果资源不存在,就创建, 相当于 kubectl create
  • 如果资源存在,则更新,相当于 kubectl patch

node节点需要执行命令,需要将master节点配置文件拷贝到 node 节点

scp -r HOME./kube  node1:HOME/

第四章 实战入门


4.1、应用命名空间


Namespace : 多套环境的资源隔离,或多个租户的资源隔离, 不同namesapce的pod不能互相访问

集合kubernetes配额机制,限定不同租户能够占用的资源,例如CPU、内存等

系统空间

  • default : 所有未指定 namespace的对象都会被分配到 default命名空间
  • kube-node-lease :集群节点之间的心跳维护,v1.13开始引入
  • kube-public : 此命名空间下的资源可以被所有人访问(包括未认证用户)
  • kube-system :所有有kubernetes 系统创建的资源都处于此空间

配置方式

首先准备一个 yaml 文件 :ns-dev.yaml

apiVersion : v1
kind : Namespace 
metadata :
	name : dev

创建 : kubectl create -f ns-dev.yaml

删除 :kubectl delete -f ns-dev.yaml

4.2、Pod 运行


定义 : 对容器的封装,可以 包含一个或多个容器

集群启动后,这个组件也都是以 Pod 的方式运行的。(每个节点上多有一组组件)

创建并运行

# 命令格式 : kubectl run (pod控制器名称) [参数]
# --image  指定Pod的镜像
# --port  指定暴露端口
# --namespace  指定namespace
kubectl run nginx --image=nginx:1.17.1 --port=80 --namespace dev

查看Pod信息

# 查看Pod 基本信息
kubectl get pods -n dev

# 查看Pod 详细信息
kubectl get pods -n dev -o wide

# 查看Pod详细信息
kubectl describe pod nginx-23r34345323443f -n dev

Pod访问

# 查看Pod 详细信息(端口)
kubectl get pods -n dev -o wide

curl 10.224.10.80 80

配置操作

创建一个pod-nginx.yaml 内容如下 :

apiVersion : v1
kind : Pod 
metadata :
	name : nginx
	namespace : dev
spac :
	containers :
	- image : nginx : 1.17.1
	  name : pod
	  ports :
	  - name : nginx-port
	    containerPort : 80
	    protocol : TCP

4.3、Label 标签


定义 : 用来区分和选择Pod的标识

  • 会以 key/value 键值对的形式附加到各种对象上。如Node、Pod、Service
  • 一个资源可以定义任一数量的Label , 同一个 Label 可以被添加到任一数量的资源对象行
  • Label 通常在资源定义是确认,当然也可以对对象创建后进行添加或删除

可以通过Label 实现资源的多维度分组,方便的进行资源分配,调度,位置,部署等管理工作

版本标签 : “version” : “release” , “version” : “stable”
环境标签 :“environment” : “dev” , “environment” : “test” , “environment” : “pro”
架构标签 :“tier” : “frontend” , “tier” : “backend”

标签完成后,需要使用 Label Selector , 即 :

  • Label :用于给某个资源对象定义标签
  • Label Selector : 用于查询和筛选拥有某些标签的资源对象

当前有两种 Label Selector

  • 基于等式的 Label Selector
    name = slave : 选择所有包含 Label 中 key =“name” , value = “slave” 的对象
    env != production : 选择所有包含 Label 中的key=“env” 且 value不等于"production" 的对象
  • 基于 集合的Label Selector
    name in (master,slave) : 选择所有包含 Label 中的 key =“name” 且 value =“master” 或 “slave” 的对象
    name not in (frontend): 选择所有包含Label 中 key =“name” 且 value 不等于 frontend 的对象

可以使用多个标签

  • name = slave , env != production
  • name not in (frontend), env != production
# 为node资源打标签
kubectl label node k8s-slave1 component=mysql


# 为 pod资源打标签
kubectl label pod nginx-pod version=1.0 -n dev

# 为pod更新标签
kubectl label pod nginx-pod version=2.0 -n dev --overwrite

# 查看标签
kubectl get pod nginx-pod  -n dev --show-labels

# 筛选标签
kubectl get pod nginx-pod  -n dev -1 version=2.0 --show-labels
kubectl get pod nginx-pod  -n dev -1 version!=2.0 --show-labels

# 删除标签( 标签后面 加一个  -  代表去除)
kubectl label pod nginx-pod version- -n dev

4.4、Deployment控制器


  • 定义 :用户 Pod 管理,确保 pod 资源符合预期的效果,当 pod 出现故障时,会尝试进行重建Pod

命令操作

# 命令格式 : kubectl run deployment名称 [参数]
# --image 指定 pod的镜像
# --port 指定端口
# --replicas 指定创建pod数量
# --namespace 指定namespace
kubectl run nginx --image=nginx:1.17.1 --port=80 --replicas=3 -n dev

# 查看创建 pod
kubectl get pods -n dev

# 查看deployment的信息
kubectl get deploy -n dev

# UP-TO-DATE : 成功升级的副本数量
# AVAILABLE : 可用副本的数量

# 查看deployment 详细信息
kubectl describe deploy nginx -n dev

# 删除
kubectl delete deploy nginx -n dev

配置文件信息

apiVersion : app/v1
kind : Deployment
metadata :
	name : nginx
	namespace : dev
	
spac :
	replicas : 3  # 副本数量
	selector : # 标签选择器
		matchLabels :
			run : nginx  # 选择标签(与pod名称对应)
			
	template :    # Pod 模板区
		metadata :
		labels :
			run : nginx # 设置标签
	spac :
		containers :
		- image : nginx : 1.17.1
	  		name : pod
             ports :
             	- containerPort : 80
             	  protocol : TCP

4.5、Service


  • 定义 :可以看作一组同类Pod对外的访问接口,借助 Service,应用可以方便地实现服务发现和负载均衡
  • 每个 Pod 都会分配一个独立的 Pod IP ,然后依然存在两个问题
  • Pod IP 会随着Pod的重建产生变化
  • Pod IP 仅仅是集群内可见的虚拟 IP,外部无法访问

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XHIg7mJe-1660605598025)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211106211145762.png)]

操作一 : 创建集群内部可访问的 Service

# 暴扣(expose) Service [暴露 deploy管理的名字为 nginx 的pod]
kubectl expose deploy nginx --name=svc-nginx1 --type=ClusterIP --port=80 --target-port=80 -n dev

# 查看Service
kubectl get svc svc-nginx -n dev -o wide

操作二 : 创建集群外部也可访问的 Service

# 上面创建的 Service 的 type类型为 ClusterIP, 这个 ip地址只用集群内部访问
# 如果需要创建外部也可以访问的 Service, 需要修改 type 为 NodePort
kubectl expose deploy nginx --name=svc-nginx2 --type=NodePort --port=80 target-port=80 -n dev

# 此时查看,会发现出现 NodePort 类型的 Service,而且有一对 Port(80:31928/TC)
kubectl get svc sev-nginx-1 -n dev -o wide

# 删除 Service
kubectl delete svc svc-nginx2 -n dev

配置方式

apiVersion : v1
kind : Service
metadata :
	name : svc-nginx
	namespace : dev
	
spac :
	clusterIP : 10.109.179.231
	ports :
	- port : 80
	  protocol : TCP
	  targetPort : 80
	selector :
	   run : nginx  #  有标签 run : nginx 
	   type : ClusterIP

创建 : kubectl create -f svc-nginx.yaml

删除 : kubectl delete -f svc-nginx.yaml

第五章 Pod详解


5.1、Pod 结构


Pod内容器的组成

  • 用户自定义容器
  • 根容器 ( Pause容器 )
  1. 可以以它依赖,评估整个 Pod 的健康状态
  2. 可以在根容器上设置 IP 地址,其他容器都此 IP (Pod IP) , 以实现 Pod 内部网络通信
    Pod 内部通信,Pod之间的通信采用虚拟化二层网络技术来实现,当前环境是 Flannel

5.2、Pod 定义


全配置样例 : kubectl explain pod.spec.container.lifecycle

# 查看全部 pod可配置参数
[root@linux123 ~]# kubectl explain pod


apiVersion: v1  #版本号
kind: Pod #资源类型


metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    key2: value2
  annotations: <map[string]string> #资源注解,与label不同在于他不能用于挑选资源对象,仅用于为对象提供“元数据”。
    key1: value1
    key2: value2
    


spec: <Object> #必选,pod中容器的详细定义

  containers: <[]Object> -required- #pod中的容器列表,可以有多个容器
  - name: <string> -required- #容器名称
    image: <string> -required- #容器的镜像名称
    
    
    resources : # 资源
    	limits : # 资源限制(上限)
    		cpu :"2" # cpu限制
    		memory : "10Gi" # 内存限制
    	requests : # 资源限制(下线)
        	cpu :"2" # cpu限制
    		memory : "10Gi" # 内存限制
    	
    	
    
    imagePullPolicy: <string> (Always, Never, IfNotPresent) #获取镜像的策略,
    # Alawys表示下载镜像 
    # IfnotPresent表示优先使用本地镜像,否则下载镜像
    # Nerver表示仅使用本地镜像,如果是lastest默认为Always
    # 否则默认为IfNotPresent
    
    command: <[]string> #容器的启动命令列表,如不指定,使用打包时使用的启动命令,需要指定bash shell,对应Dockerfile的ENTRYPOINT,定义command后,只会运行command下的命令(优先执行与其他子字段下的command)
    args: <[]string> #容器的启动命令参数列表,向command中传参数,对应Dockerfile的CMD
    
    workingDir: <string> #容器的工作目录
    ports: <[]Object> #需要暴露的端口列表
    - name: <string> #端口号名称
      containerPort: <integer> -required- #容器所在pod的IP地址上暴露的端口
      hostPort: <integer> #容器所在节点暴露的端口,默认与Container相同
      hostIP: <string> #绑定host主机IP地址对应外部端口(调度节点不确定)
      protocol: <string> #端口协议,支持TCP和UDP,默认TCP
    volumeMounts: <[]Object> #挂载到容器内部的存储卷配置
    - name: #引用pod定义的共享存储卷的名称,需用volumes[]部分定义的的卷名
      mountPath: <string> -required- #存储卷在容器内mount的绝对路径  
      
    # 环境变量   
    env: <[]Object>
      name: <string> -required-
      value: <string>
      valueFrom: <Object>
      
    # 存活探针
    livenessProbe: <Object> #容器存活状态探测
      exec: <Object> # 执行用户自定义命令
        command: <[]string>
      httpGet: <Object> #指定要执行的http请求
        host: <string> #Pod的IP地址
        httpHeaders: <string> 
        path: <string> #表示向哪个url发起请求
        port: <string> -required- #指定端口
      tcpSocket: <Object> #指定涉及TCP端口的操作。 尚不支持TCP挂钩
        host: <string> #Pod的IP地址
        port: <string> -required- #指定端口
      initialDelaySeconds: <integer> #在容器启动后多少秒进行探测,默认容器启动就探测(主进程需要启动时间)
      failureThreshold: <integer> #探测器探测的最小连续故障次数,到达此次数即视为失败,默认3,最小1
      successThreshold: <integer>
      periodSeconds: <integer> #执行探测的频率(单位s),默认10s,最下1s
      timeoutSeconds: <integer> #探测超时的秒数,默认1s
      
    
    # 就绪性探针
    readinessProbe: <Object> #就绪状态探测,子字段和livenessProbe一样
    
    # 钩子函数挂入点
    lifecycle: <Object>
      postStart: <Object> #在容器创建后立即执行的
        exec: <Object>    # 允许在容器内执行一条命令
        httpGet: <Object>    # 在当前容器中向某url发起http请求
        tcpSocket: <Object>   # 在当前容器尝试访问指定的Socket
      preStop: <Object> #在容器终止后立即执行的
      
      
  volumes: <[]Object>
    emptyDir: {}
    hostPath: <Object>
      path: <string> -required-
      type: <string> #DirectoryOrCreate:宿主机目录不存在就创建;Directory:宿主机目录必须存在;FileOrCreate:宿主机文件不存在就创建;File:宿主机文件必须存在;Socket:;CharDevice:BlockDevice:;默认为空
    nfs: <Object>
      path: <string> -required-
      readOnly: <boolean> #默认false
      server: <string> -required- #NFS server地址
    persistentVolumeClaim: <Object>
      claimName: <string> -required-
      readOnly: <boolean>
      
  nodeName: <string> #通过节点名称选择指定的部署主机
  
  nodeSelector: <map|string|string> #标签选择器,通过标签指定部署的节点(标签:key: value)
  restartPolicy: <string> #pod内容器重启策略,Always:总是重启、OnFailure:只有状态错误才重启、Never:从来不重启,默认总是重启
  
  hostNetwork: <boolean> #是否使用主机的网络命名空间
  hostPID: <boolean>
  hostIPC: <boolean>
  serviceAccountName: <string> #指定创建的serviceaccount名称
  
  
status: <Object>

说明 :

  • containers <[]object> 容器列表,用于定义容器的详细信息
  • nodeName 根据nodeName的值将pod调度到指定的Node节点上
  • nodeSelector <map[]> 根据NodeSelector 中定义的信息选择该 Pod调度到包含这些标签的节点
  • hostNetwork 是否使用主机网络模式,默认为 false,如果设置Ftue,表示使用宿主机网络
  • volumes <[] Object> 存储卷,用于定义pod 上面挂载的存储信息
  • restartPolicy 重启策略,表示Pod在遇到故障的时候的处理策略
5.2.1、Pod健康检查机制

LivenessProbe探针 :

  • 用于判断容器是否存活,及Pod是否为running状态,如果LivenessProbe 探针探测到容器不健康,则 kubelet 将kill 掉容器,并根据容器重启策略是否重启,如果一个容器不包含 LivenessProbe 探针,则kubelet 认为容器的 livenessProbe探针返回值永远为成功
# 存活探针
    livenessProbe:   #容器存活状态探测
        httpGet: <Object> #指定要执行的http请求
            host: <string> #Pod的IP地址
            path: <string> #表示向哪个url发起请求
            port: <string> -required- #指定端口
            scheme :HTTP
       initialDelaySeconds : 10   # 容器启动后第一次执行探测最小等待时间
       periodSeconds : 10    # 执行探测的频率
       timeoutSeconds : 2    # 探测超时时间

ReadlineProbe 探针 :

  • 可用性探针,用于判断容器是否正常提供服务,即容器的 Ready 是否为 true ,是否可以接受请求 , 如果 ReadinessProbe 探测失败,则容器的 Ready 将为 False , endpoint controller 控制器量将此 pod 的 Endpoint 从对应的 service 的 Endpoint列表中移除,不再将任何请求调度到 pod 上,直到下次探测成功 (剔除此pod不参与接受请求不会将流量转发给此 pod)
  • ExecAction : 在容器内执行指令。如果命令返回码为0,则认为诊断成功
  • TCPSocketAction :对制定端口上的容器IP地址进行TCP监测,如果端口开放,则诊断成功
  • HttpGetAction : 指定的端口路径和路径上的容器 IP 地址执行 Http get请求,如果响应码大于等于200且小400,则判断为成功。

5.3、Pod的生命周期


Pod 创建过程

  • 运行初始化容器(init container)过程
  • 运行主容器(main container)过程
  • 容器启动后钩子(post start)、容器终止前钩子(pre stop)
  • 容器的存活性探测(liveness probe)、就绪性探测(readness probe)
  • pod 终止过程

Pod 运行状态(相位)

  • 挂起(pending):apiserver 已经创建pod资源,但它尚未被调度完成
  • 运行中(Running):Pod已经被调度到某个节点,容器都已经被 k8s创建完成
  • 成功(successed): pod中所有容器已经成功终止,并且不会被重启
  • 失败(failed): 所有容器都已经终止,但至少有一个容器终止失败,即容器返回了非0状态的退出
  • 未知(unknow):apiserver 服务正常获取到pod对象的状态信息,通常由网络通信导致

Pod 重启策略

  • Always : 容器失败时,自动启动容器,默认策略
  • OnFailure : 容器终止运行,且退出码不为0时重启
  • Never : 不论状态如何,都不重启容器

阶梯型重启延迟时长 : 10S 20S 40S 80S 120S 240S 300S

注 :在Pod层级

5.4、Pod 调度


调度规则

  • 自动调度 :运行在哪个节点上由 scheduler 经过一些列算法得出
  • 定向调度 : NodeName、NodeSelector
  • 亲和性调度 :NodeAffinity 、PodAffinity、PodAntiAffinity
  • NodeAffinity (node亲和性):以node为目标,解决pod可以调度到那些node的问题
  • PodAffinity (pod亲和性):以pod为目标,解决pod可以和那些已存在的pod部署在同一个拓扑域中
  • PodAntiAffinity (pod亲和性):以pod为目标,解决pod不能和那些已存在pod部署在同一拓扑中
  • 污点容忍 :Taints、Toleration
# node亲和性 - 定向调度

apiVersion: v1  #版本号
kind: Pod #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    key2: value2

spec: <Object> #必选,pod中容器的详细定义

  containers: <[]Object> -required- #pod中的容器列表,可以有多个容器
  - name: <string> -required- #容器名称
    image: <string> -required- #容器的镜像名称
    
    
  nodeName : node1    # 指定调度到node1节点
# node1 节点打标签
[root@linux123 ~]# kubectl label node1 nodeenv=pro



# node亲和性 - 定向调度

apiVersion: v1  #版本号
kind: Pod #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    key2: value2

spec: <Object> #必选,pod中容器的详细定义

  containers: <[]Object> -required- #pod中的容器列表,可以有多个容器
  - name: <string> -required- #容器名称
    image: <string> -required- #容器的镜像名称
    
    
  nodeSelector :   # 指定调度到具有 nodeenv=pro 标签的节点上
  	nodeenv : pro
# 亲和性调度 - 硬限制

apiVersion: v1  #版本号
kind: Pod #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    key2: value2

spec: <Object> #必选,pod中容器的详细定义

  containers: <[]Object> -required- #pod中的容器列表,可以有多个容器
  - name: <string> -required- #容器名称
    image: <string> -required- #容器的镜像名称
    
    
  affinity : # 亲和性设置
  	NodeAffinity : # 设置node亲和性
  		requiredDuringSchedulingIgnoredDuringExecution : # 硬限制
  			nodeSelectorTerms:
  			- matchExpressions : # 匹配 env的值在 ["xxx" , "yyy"]中的标签 (或的关系)
  				-key : nodeenv
  				 operator : In
  				 values : ["xxx" , "yyy"]
# 亲和性调度 - 软限制

apiVersion: v1  #版本号
kind: Pod #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    key2: value2

spec: <Object> #必选,pod中容器的详细定义

  containers: <[]Object> -required- #pod中的容器列表,可以有多个容器
  - name: <string> -required- #容器名称
    image: <string> -required- #容器的镜像名称
    
    
  affinity : # 亲和性设置
  	NodeAffinity : # 设置node亲和性
  		preferredDuringSchedulingIgnoredDuringExecution : # 软限制
  		   -weighe : 1
  			prefernece:
  			- matchExpressions : # 匹配 env的值在 ["xxx" , "yyy"]中的标签 (或的关系)
  				-key : nodeenv
  				 operator : In
  				 values : ["xxx" , "yyy"]

第六章 Pod 控制器详解


6.1、Pod控制器介绍


  • ReplicationController : 原始控制器,目前已经被 ReplicaSet 取代
  • ReplicaSet :保证指定数量的Pod运行,并支持Pod数量变更,镜像版本变更
  • Deployment : 通过控制 ReplicaSet 来控制Pod,并支持滚动升级,版本回退
  • Horzontal Pod Autoscaler : 根据集群负载自动调整 Pod数量,实现削峰填谷
  • DaemonSet : 在集群中指定 Node上运行一个副本,一般用于守护进程类的任务(日志收集、节点监控)
  • Job : 它创建出来的Pod只要完成就立即退出,用于执行一次性任务
  • CronJob : 它创建的 Pod 会周期性执行,用于执行周期性任务
  • StatefulSet : 管理有状态的应用

6.2、ReplicaSet(RS)


  • 特性说明 :保证一定数量的Pod能够正常运行,持续监听Pod状态,一旦Pod发生故障,就会重启或重建,同时支持 Pod数量的扩缩容 和镜像版本升级。(扩容,另启 n 个pod)

RS配置清单

apiVersion: v1  #版本号
kind: ReplicaSet #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: <map[string]string> #标签列表
    key1: value1
    
spec: <Object> #必选,pod中容器的详细定义
  replicas : 3 # 副本数量
  selector : # 选择器,通过它指定该控制器管理那些 pod
  	 matchLabels :  # Labels配置规则
  	 	app : nginx-pod
  	 matchExpressions :  # Expressions 匹配规则
  	 	-{key : app ,operator : In , values :{nginx-pod}}
  	 	
  template : # 模板,当副本数量不足时,会根据下面模板信息创建 Pod副本
  	metadata :
  		labels :
  			app : nginx-pod  # 与上面的匹配规则名称对应
  	spec :
  		containers :
  		- name :nginx
  		  image : nginx:1.17.1
  		  ports :
  		  -containerPort : 80

命令调整pod数量

# 直接编辑 yaml文件
kubectl edit rs [rs容器名称] -n dev

# 命令调整容量
# 使用 scale 命令实现扩容缩容,后面 --replicas=n 直接指定目标数量即可
kubectl scale rs pc-replicaset --replicas=2 -n dev

镜像版本的升级,降级

# 直接编辑 yaml文件
kubectl edit rs [rs容器名称] -n dev

# 修改 image信息即可


# 命令调整容量
# 使用 set image rs rs名称  容器=镜像版本 -n namespace

kubectl set image rs pc-replicaset nginx=nginx:1.17.1 -n dev

6.3、Deployment (deploy)


通过管理 ReplicaSet 来管理集群

  • 支持 ReplicaSet所有功能
  • 支持发布的停止、继续
  • 支持版本滚动升级和版本回退
apiVersion: v1  #版本号
kind: Deployment #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: 
  	controller : deploy
    
spec: <Object> #必选,pod中容器的详细定义
  replicas : 3 # 副本数量
  revisionHistoryLimit : 3 # 保存历史版本,默认是 10
  paused : false # 部署暂停,默认关闭
  progressDeadlineSeconds ; 600  # 部署超时时间(s),默认600
  strategy : # 策略
  	type : RollingUpdate # 滚动更新策略(两种策略 : 滚动更新、重建更新)
  		maxSurge : 30% # 最大额外可以存在的副本数,可以为百分比,也可以为数值
  		maxUnavailable : 30%  # 最大不可用Pod 的最大值,可以为百分比,也可以为数值
  selector : # 选择器,通过它指定该控制器管理那些 pod
  	 matchLabels :  # Labels配置规则
  	 	app : nginx-pod
  	 matchExpressions :  # Expressions 匹配规则
  	 	-{key : app ,operator : In , values :{nginx-pod}}
  	 	
  template : # 模板,当副本数量不足是,会根据下面模板信息创建 Pod副本
  	metadata :
  		labels :
  			app : nginx-pod
  	spec :
  		containers :
  		- name :nginx
  		  image : nginx:1.17.1
  		  ports :
  		  -containerPort : 80
6.3.1、扩缩容

# 命令调整容量
# 使用 scale 命令实现扩容缩容,后面 --replicas=n 直接指定目标数量即可
kubectl scale deploy pc-deployment --replicas=5 -n dev

kubectl get pod -n dev

# 编辑 yaml文件
kubectl deploy pc-deployment -n dev

镜像更新

  • 重建更新 : 一次性删除全部老版本的Pod
  • 滚动更新(默认):滚动发布形式进行更新 (strategy) - 先删老版本,再启动新版本

strategy : 指定新 pod 替换旧 pod的策略

  • type : 指定策略类型
  • Recreate : 创建新的 Pod 之前先杀死所有已经存在的 Pod
  • RollingUpdate : 滚动更新,杀死一部分,再启动新的、在更新过程中,存在两种pod
  • rollingUpdate : 当 type 为 RollingUpdate 时生效,用于为 RollingUpdate 设置参数
  • maxSurge : 25% # 最大额外可以存在的副本数,可以为百分比,也可以为数值
  • maxUnavailable : 25% # 最大不可用Pod 的最大值,可以为百分比,也可以为数值

重建更新

  • 编辑 pc-deployment.yaml , 在spec 节点系添加更新策略
spec :
	strategy : # 策略
		type : Recreate # 重建更新策略

滚动更新 (默认)

spec :
	strategy : # 策略
		type : rollingUpdate # 滚动更新策略
		rollinngUpdate :
			maxUnavailable : 25%  # 最大可存在 Pod 占比
			maxSurge : 25%   # 最大不可用 Pod 占比

创建deploy 进行验证

# 更新镜像
kubectl set image deployment pc-deployment nginx=nginx:1.17.2 -n dev

# 观察升级过程
kubectl get pods -n dev -w
6.3.2、版本回退

支持版本升级过程中暂停,继续功能,以及版本回退

kubectl rollout : 版本升级相关功能,支持下面选项

  • status 显示当前升级状态
  • history 显示升级历史记录
  • pause 暂停版本升级过程
  • resume 继续已经暂停的版本升级过程
  • restart 启动版本升级过程
  • undo 回滚到上一级版本(可以使用 --to-revison 回滚到指定版本)
# 查看当前升级版本状态
kubectl rollout status deploy pc-deployment -n dev

# 查看升级历史记录
Kubectl rollout history deploy pc-deployment -n dev

# 版本回滚
# 直接使用 --to-version=1 回滚到1版本,如果省略这个选项,就是回退到上一个版本
kubectl rollout undo deployment pc-deployment --to-revision=1 -n dev

金丝雀发布 - 同时存在新旧两个版本

# 连续执行两个命令  先发布,后暂停 (先创建新的,再暂停老的)
[root@linux123 ~]# kubectl set image deploy pc-deployment nginx=nginx:1.17.4 -n dev && kubectl rollout pause deployment pc-deployment -n dev


# 继续发布
[root@linux123 ~]# kubectl rollout resume deploy pc-deployment -n dev

6.4、Horizontal Pod Autoscaler (HPA)


  • HPA 可用获取每个pod利用率,然后和 HPA中定义的指标进行对比,从而实现Pod 数据的调整。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LjtGMoZS-1660605598027)(D:\software\typora\typor安装位置\笔记\图片\HPA.png)]

6.5、DaemonSet (DS)


  • DaemonSet 类型控制器可保证集群中每一台(或指定)节点上都运行一个副本,适用于日志收集,节点监控等场景。也就是说,如果一个 Pod 提供的功能是节点级别的 (每个节点都需要且只需要一个)。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3IUMgheM-1660605598028)(D:\software\typora\typor安装位置\笔记\图片\微信截图_20211225205236.png)]

控制器特点

  • 每当向集群添加一个节点时,指定的 Pod副本也将添加到该节点
  • 当节点从集群中移除时,Pod 也就被垃圾回收了
# pc-daemonset.yaml

apiVersion: v1  #版本号
kind: DaemonSet #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间

    
spec: <Object> #必选,pod中容器的详细定义
  selector : # 选择器,通过它指定该控制器管理那些 pod
  	 matchLabels :  # Labels配置规则
  	 	app : nginx-pod
  	 	
  template : # 模板,当副本数量不足是,会根据下面模板信息创建 Pod副本
  	metadata :
  		labels :
  			app : nginx-pod
  	spec :
  		containers :
  		- name :nginx
  		  image : nginx:1.17.1
# 发布完成后,每个节点都会有一个 Pod
[root@linux123 ~]# kubectl create -f pc-deployment.yaml

6.6、Job 控制器


负责批量处理(一次要处理指定数量任务)短暂的一次性任务

  • 当 job 创建的Pod执行成功结束时,job将记录成功结束 pod 数量
  • 当成功结束的Pod 达到指定的数量时,job将完成执行
apiVersion: v1  #版本号
kind: job #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: 
  	controller : job
    
spec: <Object> #必选,pod中容器的详细定义
  completions : 1  # 指定job需要成功运行 Pods 的次数,默认 1
  parallelism : 1  # 指定job在任一时刻应该并发运行 Pod的数量,默认 1
  activeDeadlineSeconds : 30 # 指定 job 可运行的时间期限,超过世界还未结束,系统将尝试进行终止
  backoffLimit : 6  # 执行 job失败后,可重试的次数,默认 6
  manualSelector : true  # 是否可以使用 Selector选择器选择Pod,默认false
  
  
  selector : # 选择器,通过它指定该控制器管理那些 pod
  	 matchLabels :  # Labels配置规则
  	 	app : nginx-pod
  	 matchExpressions :  # Expressions 匹配规则
  	 	-{key : app ,operator : In , values :{nginx-pod}}
  	 	
  template :
  	metadata :
  		labels :
  			app : nginx-pod
  	spec :
  		restartPolicy : Never # 重启策略只能设置为 Never 或者OnFailure
  		containers :
  		- name :nginx
  		  image : nginx:1.17.1
  		  ports :
  		  -containerPort : 80
apiVersion: v1  #版本号
kind: job #资源类型

metadata: <Object> #元数据
  name: pc-job
  namespace: dev #pod所属命名空间
    
spec: <Object> #必选,pod中容器的详细定义
  completions : 1  # 指定job需要成功运行 Pods 的次数,默认 1
  parallelism : 1  # 指定job在任一时刻应该并发运行 Pod的数量,默认 1
  activeDeadlineSeconds : 30 # 指定 job 可运行的时间期限,超过世界还未结束,系统将尝试进行终止
  backoffLimit : 6  # 执行 job失败后,可重试的次数,默认 6
  manualSelector : true  # 是否可以使用 Selector选择器选择Pod,默认false
  
  
  selector : # 选择器,通过它指定该控制器管理那些 pod
  	 matchLabels :  # Labels配置规则
  	 	app : nginx-pod
  	 matchExpressions :  # Expressions 匹配规则
  	 	-{key : app ,operator : In , values :{nginx-pod}}
  	 	
  template :
  	metadata :
  		labels :
  			app :counter-pod
  	spec :
  		restartPolicy : Never # 重启策略只能设置为 Never 或者OnFailure
  		containers :
  		- name :counter
  		  image : busybox:1.30
  		  command : ["bin/sh"."-c","for i in 9 8 7 6 5 4 3 2 1; do echo $i; sheel 3 ; done"]
6.7、CronJob (CJ)

  • 通过控制job进行执行任务,在指定时间点进行执行,可反复执行
apiVersion: v1  #版本号
kind: CronJob #资源类型

metadata: <Object> #元数据
  name: <string> #pod名称
  namespace: <string> #pod所属命名空间
  labels: 
  	controller : cronjob
    
spec: <Object> #必选,pod中容器的详细定义
  schedule :   # cron 格式的作业调度运行时间点,用于控制任务在什么时间点执行
  concurrengyPolicy :  # 并发执行策略,用于定义前一次作业运行尚未完成时是否以及如何运行最后一次作业
  failedJobHistoryLimit :  # 为失败任务执行保留的历史记录数,默认1
  successfulJobHistoryLimit :  # 为成功的任务执行保留的历史记录,默认3
  startingDeadlineSeconds :  # 启动作业错误的超时时间

  	 	
  jobTemplate :  # job控制器,用于生成 cronjob对象
  	metadata :
  		labels :
  			app : nginx-pod
  	spec :
  		restartPolicy : Never # 重启策略只能设置为 Never 或者OnFailure
  		containers :
  		- name :nginx
  		  image : nginx:1.17.1
  		  ports :
  		  -containerPort : 80

第七章 Service


7.1、Service 控制器简介


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5xex8FBS-1660605598029)(D:\software\typora\typor安装位置\笔记\图片\微信截图_20211225215401.png)]

资源类型

Service : 四层路由负载

ingress : 七层路由负载

实际作用 : kube-proxy服务进程,每个Node节点都运行这一个kube-proxy服务进程,当创建 Service的时候,会通过api-server 向 etcd写入创建的 service信息,kube-proxy会基于监听的机制发现 service的变化,然后转化为对应的访问规则

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OryIeHrp-1660605598030)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107160701018.png)]

7.2、kube-proxy工作模式


  • kube-proxy目前有三种工作模式
  • 规则会在集群的所有节点上都存在
7.2.1、userspace模式

userapace 模式下,kube-proxy会 为每一个Servicec创建一个监听端口,发向 Cluster IP 的请求被 iptables 规则重定向到 kube-proxy监听端口上,kube-proxy根据LB 算法选择一个提供服务的Pod并和其家里连接,以将请求转发到Pod上

	该模式下,kube-proxy充当一个四层负载均衡器的角色,由于kube-proxy运行在userspace中,在进行转发处理时会增加用户空间之间数据拷贝,虽然比较稳定,但效率较低

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EleWmLJc-1660605598031)(D:\software\typora\typor安装位置\笔记\图片\image-20211107161956334.png)]

7.2.2、Iptables模式

iptables 模式下,kube-proxy为service后端每个pod串讲对应的 iptables规则,直接发向 Cluster IP的请求重新定向到一个 Pod ip

	该模式下,kube-proxy 不承担四层负载均衡器的角色,值负责创建 iptables 规则,该模式的优点是较 userspace 模式效率更高,但不能提供灵活的LB策略,当后端 pod 不可用时,无法进行重试。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SE7VDApJ-1660605598032)(D:\software\typora\typor安装位置\笔记\图片\image-20211107162045044.png)]

7.2.3、Ipvs模式 (当前默认)

ipvs 模式和 iptables 类似,kube-proxy监空pod的变化,并创建对应的 ipvs 规则。 ipvs 相对 iptables 转化效率更高,除此以外,ipvs支持更多的LB算法。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Gl6FjbZO-1660605598034)(D:\software\typora\typor安装位置\笔记\图片\image-20211107162203254.png)]

# 此模式要求安装 ipvs内核模块,否则还会降级为iptables
# 开启ipvs
Kubectl edit cm kube-proxy -n hube-system

# 增加 
model : ipvs

# 删除 kube-proxy的pod
kubectl delete pod -1 k8s-app=kube-proxy -n kube-system

# 查看IPVS映射规则
ipvsadm -Ln

7.3、Service资源清单


apiVersion: v1 
kind: Service  # 资源类型
metadata:   # 元数据
  name: myapp  # 资源名称
  namespace: default   # 资源空间
spec:  # 描述
  selector:   # 选择器,用于确认当前Service代理那些pod
    app: myapp
    release: canary
  clusterIP: 10.97.97.97   # 虚拟服务地址(可设置、可不设置自动分配)
  sessionAffinity : # session 亲和性,支持ClientIP、None 两个选项(固定IP发来的请求发送到固定IP上去)
  type: ClusterIP   # service类型
  ports: # 端口信息
  - port: 80  # service端口
    targetPort: 80  # pod端口
    nodePort : 31122 # 主机端口
  • ClusterIP : 默认值,自动分配的虚拟IP,只对集群内部访问
  • NodePort : 将service指定的 Node上的端口暴露给外部,通过此方法可以在集群外部访问服务
  • LoadBalance : 使用外界负载均衡器完成到服务的负载分发,注意此模式需要外部云环境支持
  • ExternalName : 把集群外部的服务引入到集群内部,直接使用

7.4、Service使用


HeadLiness 类型的Service

在某些场景下,开发人员可能不想使用Service提供负载均衡的功能,而希望自己来控制负载均衡策略,针对这种情况,k8s 提供了HeadLiness Service, 这类 Service 不会分类 Cluster IP , 如果想要访问 Service , 只能通过 **Service 的域名进行查询**。

创建Service-headliness.yaml

apiVersion: v1 
kind: Service  # 资源类型
metadata:   # 元数据
  name: service-headliness  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  selector:   # 选择器,用于确认当前Service代理那些pod
    app: nginx-pod
  clusterIP: None   # 将 cluster IP 设置为 None,即可创造 headliness Service
  type: ClusterIP   # service类型
  ports: # 端口信息
  - port: 80  # service端口
    targetPort: 80  # pod端口
    nodePort : 31122 # 主机端口
    
    
    
# 查看 service 详细信息    
[root@linux123 ~]# kubectl describe svc service-clusterip on dev

7.5、NodePort 类型的 Service


NodePort 的工作原因为 将 Service的端口映射到 Node的一个端口上,然后可以通过 NodeIP:NodePort 来访问Service了。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5oYHp0xF-1660605598036)(D:\software\typora\typor安装位置\笔记\图片\image-20211107182139680.png)]

创建 Serice-nodeport.yaml

apiVersion: v1 
kind: Service  # 资源类型
metadata:   # 元数据
  name: service-nodeport  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  selector:   # 选择器,用于确认当前Service代理那些pod
    app: nginx-pod
  Service
  type: NodePort   # service类型
  ports: # 端口信息
  - port: 80  # service端口
    targetPort: 80  # pod端口
    nodePort : 31122 # 主机端口

7.6、LoadBalance 类型的 Service


LoadBalance 和 NodePort 很相似,目的都是向外暴扣一个端口,区别于LoadBalance 会在集群的外部再来做一个负载均衡设备,而这个设备需要外部环境支持的,外部服务发送到这个设备上的请求,会被设备负载之后转发到集群中。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pVLr9Iv3-1660605598037)(D:\software\typora\typor安装位置\笔记\图片\image-20211107182658751.png)]

7.7、ExternalName 类型的 Service


ExternalName 类型的 Service 用于引入到集群外部的服务,它通过 externalName 属性指定外部一个服务的地址,然后再集群内部访问此 Service 就可以访问到外部的服务了。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-i94JQOpM-1660605598038)(D:\software\typora\typor安装位置\笔记\图片\image-20211107182956282.png)]

apiVersion: v1 
kind: Service  # 资源类型
metadata:   # 元数据
  name: service-externalname  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  selector:   # 选择器,用于确认当前Service代理那些pod
    app: nginx-pod
  Service
  type: ExternalName   # service类型
  ExternalName : www.baidu.com  # 改成ip地址也可以

7.8、Ingress介绍


Ingresss 只需要一个 NodePort 或者 一个 LB 就可以 满足暴露多个 Service 的需求,工作机制大概如下 :

ingress 中写入多个 域名,每个域名对应一个Service

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pOxWtI5D-1660605598039)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107183629564.png)]

ingress 相当于一个 7 层负载均衡器,是kubernets 对反向代理的一个抽象,工作原理类似于 nginx , 可以理解为 ingress 上建立注意点映射规则, ingress Controller 通过监听这些配置规则并转化成 Nginx 的反向代理 配置,然后对外提供服务。在这里有两个核心概念 :

  • Ingress : K8S 的一个对象,作用是定义请求如何转发到 service 的规则
  • Ingress controller : 具体实现反向代理的负载均衡程序, 对ingress定义的规则进行解析,根据配置的额规则来实现请求转发,实现方式很多种,比如 nginx, Contour ,haproxy 等等。

Ingress (Nginx 为例)的工作原理如下 :

  1. 用户编写 ingress规则,说明哪个域名对应 kubernetes 集群中的哪个 Servcie
  2. Ingress 控制器动态感知 Ingress 服务规则的变化,然后生成一段对应的 Nginx配置
  3. Ingress 控制器会将生成的 Nginx 配置写入到一个运行着的 Nginx服务中,并动态更新
  4. 至此为止,其实真正的工作的就是一个 Nginx了,内部配置了用户定义的请求转发规则

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Srv4cy6h-1660605598040)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107185501349.png)]

7.8.1、Http 代理

创建 ingress-http.yaml

apiVersion: extensions/v1beta1 
kind: Ingress  # 资源类型
metadata:   # 元数据
  name: ingress-http  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  rules:   # 规则
  	- host : nginx.itheima.com
  	  http :
  	  	paths :
  	  	- path : /  # 路径
  	  	  backend :
  	  	  	 serviceName : nginx-service
  	  	  	 servicePort : 80
  	  	  	 
  	- host : tomcat.itheima.com
  	  http :
  	  	paths :
  	  	- path : /  # 路径
  	  	  backend :
  	  	  	 serviceName : tomcat-service
  	  	  	 servicePort : 80
7.8.2、https代理

# 生成证书
# 生成秘钥


apiVersion: extensions/v1beta1 
kind: Ingress  # 资源类型
metadata:   # 元数据
  name: ingress-http  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  tls :
  	- hosts :
  		- nginx.ithema.xom
  		- tomcat.ithema.com
  		secretName : tls-secret # 指定秘钥
  rules:   # 规则
  	- host : nginx.itheima.com
  	  http :
  	  	paths :
  	  	- path : /  # 路径
  	  	  backend :
  	  	  	 serviceName : nginx-service
  	  	  	 servicePort : 80
  	  	  	 
  	- host : tomcat.itheima.com
  	  http :
  	  	paths :
  	  	- path : /  # 路径
  	  	  backend :
  	  	  	 serviceName : tomcat-service
  	  	  	 servicePort : 80

第八章 数据存储


定义 :Volume 是 Pod中能够被多个 容器访问的共享目录,它被定义在 Pod上,然后被一个 Pod 里的多个容器挂载到具体的文件目录下,k8s 通过 Volume 实现同一个 Pod中不同容器之间数据共享以及数据的持久化存储。

Volume 的生命容器不与 Pod 中单个容器的生命周期相关,当容器终止或者重启时, Volume中的数据不会丢失。

  • 简单存储 :EmptyDir、HostPath、NFS
  • 高级存储 :PV 、PVC
  • 配置存储 :ConfigMap、Secret

8.1、基本存储 -EmptyDir


EmptyDir 是最基本的 Volume类型,一个 EmptyDir 就是 host 上的一个空目录

EmptyDir 是在Pod分配到 Node 时创建的,它的初始内容为空,并且无需指定宿主机上对应的目录文件,因为k8s会自动分配一个目录,当 Pod 销毁时,EmptyDir 中的数据也会被永久删除。 EmptyDir 用途如下 :

  • 临时空间 :例如用于某些应用程序运行时所需的临时目录,且无须永久保留
  • 一个容器需要从另外一个容器中获取数据的目录(多容器共享目录)

接下来 ,通过一个容器之间文件共享的案例来使用一下 EmptyDir

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RuSUXtj4-1660605598040)(D:\software\typora\typor安装位置\笔记\图片\微信截图_20211226111537.png)]

创建一个 volume-emptydir.yaml

apiVersion: v1
kind: Pod  # 资源类型
metadata:   # 元数据
  name: volume-emptydir  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  containers :
  
  - name : nginx
  	image : nginx:1.17.1
  	port :
  	- containerPort : 80
  	volumeMounts : # 将 logs-volume 挂在到nginx容器中,对应的目录为 /var/log/nginx
  	- name : logs-volume
  	  mountPath : /var/log/nginx
  	  
  - name: busybox
    image : busybox:1.30
    command : ["/bin/sh","-c","tail -f /logs/access.log"]  # 初始命令,动态读取指定文件中内容
    volumeMounts : # 将logs-volume 挂载到 busybox容器中,对应的目录为 /logs
    - name : logs-volume
      mountPath : /logs
      
 volumes : # 声明 volume , name 为log-volume,类型为 emptyDir
    - name : logs-volume
      emptyDir :{}
      
      
      
# 查看日志信息
kubectl logs -f volume-emptydir 0n dev -c busybox

8.2、基本存储 - HostPath


将 Node主机中一个是实际目录挂到Pod中,以供容器使用,这样设计就可以保证Pod销毁后,数据依据可以存在于Pod主机上

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ki7lY8PI-1660605598041)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107202724158.png)]

创建 volume-hostpath.yaml

apiVersion: v1
kind: Pod  # 资源类型
metadata:   # 元数据
  name: volume-hostpath  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  containers :
  - name : nginx
  	image : nginx:1.17.1
  	port :
  	- containerPort : 80
  	volumeMounts : # 将 logs-volume 挂在到nginx容器中,对应的目录为 /var/log/nginx
  	- name : logs-volume
  	  mountPath : /var/log/nginx
  - name: busybox
    image : busybox:1.30
    command : ["/bin/sh","-c","tail -f /logs/access.log"]  # 初始命令,动态读取指定文件中内容
    volumeMounts : # 将logs-volume 挂载到 busybox容器中,对应的目录为 /logs
    - name : logs-volume
      mountPath : /logs
      
      
  volumes : # 声明 volume , name 为log-volume,类型为 hostPart
    - name : logs-volume
      hostPart :
      	  path :/root/logs
      	  type : DirectoryOrCreate  # 目录存在就使用,不存在就创建
      
      
      
# 查看日志信息
kubectl logs -f volume-emptydir 0n dev -c busybox

8.3、基本存储 - NFS


单独的网路存储系统

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-AYslO1O4-1660605598042)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107203441158.png)]

apiVersion: v1
kind: Pod  # 资源类型
metadata:   # 元数据
  name: volume-hostpath  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  containers :
  - name : nginx
  	image : nginx:1.17.1
  	port :
  	- containerPort : 80
  	volumeMounts : # 将 logs-volume 挂在到nginx容器中,对应的目录为 /var/log/nginx
  	- name : logs-volume
  	  mountPath : /var/log/nginx
  - name: busybox
    image : busybox:1.30
    command : ["/bin/sh","-c","tail -f /logs/access.log"]  # 初始命令,动态读取指定文件中内容
    volumeMounts : # 将logs-volume 挂载到 busybox容器中,对应的目录为 /logs
    - name : logs-volume
      mountPath : /logs
      
      
  volumes : # 声明 volume , name 为log-volume,类型为 nfs
    - name : logs-volume
      nfs :
      	  server : 192.168.109.100  # nfs 服务器地址
      	  path :/root/logs
      
      
# 查看日志信息
kubectl logs -f volume-emptydir 0n dev -c busybox
8.4、高级存储 - PV & PVC

  • PV : 持久化卷,是对底层共享存储的一种抽象,PV 一般由 K8S管理员进行创建和配置,它与底层具体的共享存储技术有关,并通过插件完成与共享存储的对接
  • PVC : 持久卷声明的意思 ,是用户对存储需求的一种声明。向K8S系统发出的有一种资源需求申请

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-mesUTTIf-1660605598043)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107211425486.png)]

PV资源清单

apiVersion: v1
kind: PersistentVolume  # 资源类型
metadata:   # 元数据
  name: pv2  # 资源名称
spec:  # 描述
  nfs :  # 存储类型,与底层真正存储对应
  	path : /root/data/pv1
  	server : 192.168.109.100
  capacity : 存储能力,目前只支持存储空间的设置
      storage : 2Gi
  accessMode : # 访问模式
  storageClassName : # 存储类别
  persistenVolumeReclaimPolicy :  # 回收策略

PVC资源清单

apiVersion: v1
kind: PersistentVolumeClaim  # 资源类型
metadata:   # 元数据
  name: pvc  # 资源名称
  namespace : dev
spec:  # 描述
  nfs :  # 存储类型,与底层真正存储对应
  	path : /root/data/pv1
  	server : 192.168.109.100
  capacity : 存储能力,目前只支持存储空间的设置
      storage : 2Gi
  accessMode : # 访问模式
  storageClassName : # 存储类别
  resources : # 请求空间
  	request :
  		storage : 5Gi

PV & PVC的生命周期

  • 资源供应
  • 资源绑定
  • 资源使用
  • 资源释放
  • 资源回收

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Rw4NrUii-1660605598044)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211107214127784.png)]

8.4、配置存储 - ConfigMap


  • ConfigMap 是一种比较特殊的存储卷、它的主要作用是用来存储配置信息

创建 configmap.yaml 内容如下 :

apiVersion: v1
kind: ConfigMap  # 资源类型
metadata:   # 元数据
  name: configmap  # 资源名称
  namespace : dev
data :
	info :
		username : admin
		password : 123456

创建 pod-configmap.yaml

apiVersion: v1
kind: Pod  # 资源类型
metadata:   # 元数据
  name: pod-configmap  # 资源名称
  namespace: dev   # 资源空间
spec:  # 描述
  containers :
  - name : nginx
  	image : nginx:1.17.1
  	volumeMounts : # 将 configmap 挂载到目录
  	- name : configmap
  	  mountPath : /configmap/config
  	  mountPath : /var/log/nginx

    volumes : # 引用 configmap
    - name : config
      configMap :
      	 name : configmap   # 与上面的名字相对应

第九章 安全认证


9.1、访问控制概述


K8S作为一个分布式集群管理工具,保证集群安全性的一个重要的任务。所谓的安全性其实就是保证对 K8S 的各种客户端进行认证和鉴权操作

客户端 通常分为两类

  • User Account : 一般是独立的 kubernetes 之外的其他服务管理的用户账号
  • Service Account : k8s 管理的账号,用于为Pod的服务中进程在访问 K8S时提供身份标识

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KKigxqIO-1660605598045)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211109213704032.png)]

9.1.1、认证、授权与准入控制

ApiServer 是访问及管理资源对象的位移入口。如何一个请求访问ApiServer, 都要经过下面三个流程 :

  • Authentication (认证) :身份鉴别,只有正确的账号才能够通过认证
  • Authorization (授权) :判断用户是否有权限对访问的资源执行特定的动作
  • Admission Control (准入控制) :用于补充授权机制以实现更加精细的访问控制功能

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8EoUaYuH-1660605598046)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211109214317482.png)]

9.2、认证管理


目的是确认客户端的身份是否合法

  • HTTP Base 认证 : 通过用户名 + 密码 的方式认证
对账号和密码 通过 Base64 算法进行编码后的字符串放在 http 请求中的 Header Authorization 域里发送给服务端。服务端收到后进行解码,获取用户名及密码,然后进行用户身份认证的过程
  • HTTP Token 认证 :通过一个 Token来识别合法用户
这种认证的是用一个很长的难以模仿的字符串来标明用户的身份,每个token对应一个用户名,当客户端发起API调用请求时,需要在 HTTP Header里放入 token,API Server接到 Token后悔跟服务器中保存的 token进行对比,然后进行用户身份认证的过程
  • HTTPS证书认证 : 基于CA 根证书签名的的双向数字证书认证方式
这种认证方式最安全,同时操作最麻烦

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-TLwaDpVN-1660605598047)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211109220236271.png)]

9.3、授权管理


确认用户是否有权限访问服务资源,鉴权

每个发送给ApiServer的请求都带有用户和资源的信息,比如 发送请求的用户,请求的路径、请求的动作等,授权就是根据这些信息和授权策略进行比较,如果符合策略,则认为授权通过否则返回错误。

Api Server 目前支持的集中授权策略 :

  • AlwaysDeny : 表示拒绝所有请求,一般用于测试
  • AlwaysAllow : 允许接受所有请求,相当于集群不需要授权(默认策略)
  • ABAC : 基于属性的访问控制,表示使用用户配置的授权规则对用户请求进行匹配和控制
  • Webhook : 通过调用外部 Rest 服务对用户进行授权
  • Node : 是一种专用模式,用于对 kubelet 发出的请求进行访问控制
  • RBAC : 基于角色的访问控制 (kubeadm 安装方式下的默认选项)

RBAC (role-based access control ) 基于角色的访问控制,主要是描述一件事情 : 给那些对象授予那些权限

  • 对象 : User 、 Groups 、ServiceAccount
  • 角色 : 代表着一组定义在资源上的可操作的动作
  • 绑定 : 将定义好的橘色跟用户绑定在一起

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Uc3a0d8M-1660605598048)(C:\Users\wzh\AppData\Roaming\Typora\typora-user-images\image-20211111223830786.png)]

RBAC引入了4个顶级资源对象

  • Role,ClusterRole : 角色,用于指定一组权限
  • RoleBinding, ClusterRoleBinding : 角色绑定,用于将橘色权限赋予给对象

Role、ClusterRole

一个角色就是一组权限的集合,这里的权限都是许可形式的(白名单)

apiVersion: v1
kind: Role# 资源类型
apiVersion : rbac.authorization.k8s.io/v1beta1
metadata:   # 元数据
  name: pod-configmap  # 资源名称
  namespace: dev   # 
rules :
- apiGroup : [**]  # 支持API组列表,** 空字符串,表示核心api群
  resources : ["pods"]  # 支持的资源对象列表
  verbs : ["get","watch","list"]  # 允许的对象资源的操作方法列表


# ClusterRole 可以对集群范围内资源,跨nameSpace的范围资源,非资源类型进行授权

  
kind: ClusterRole# 资源类型
apiVersion : rbac.authorization.k8s.io/v1beta1
metadata:   # 元数据
  name: authorization-clusterrole  # 资源名称
  namespace: dev   # 
rules :
- apiGroup : [**]  # 支持API组列表,** 空字符串,表示核心api群
  resources : ["pods"]  # 支持的资源对象列表
  verbs : ["get","watch","list"]  # 允许的对象资源的操作方法列