一、初识Kubernetes

一、初识Kubernetes

1、认识Kubernetes

1.1 什么是Kubernetes

Kubernetes(简称K8s,希腊语,意为舵手)是一个开源的容器编排系统,用于容器的自动化部署、扩展,以及提供高可用和负载均衡的运行环境。

Kubernetes提供了一个便携、高效的PaaS平台,降低了在物理机或虚拟机上调度和运行服务的难度,同时Kubernetes还整合了网络、存储、安全、监控等能力,是一个非常完善的“云原生操作系统”

Kubernetes的前身是谷歌内部的Borg系统,是基于谷歌15年生产环境经验的基础上开源的一个项目。由谷歌设计并在2014年开源,之后捐献给了CNCF,称为CNCF第一个开源的顶级项目,目前已成为云原生领域的标准。

1.2 Kubernetes里程碑

image.png-671.6kB

1.3 为什么K8s是云原生基座的最佳选择

1.3.1 有了Docker,为什么还要用K8s?

  • 单独的Docker无法满足生产需求
    • 缺乏完整的生命周期管理
    • 缺乏服务发现、负载均衡、配置管理、存储管理
    • 程序的扩容、部署、回滚和更新依旧不够灵活
    • 宿主机宕机容器无法自动恢复
    • 程序级健康检查依旧不到位
    • 端口管理比较复杂
    • 流量管理依旧复杂

1.3.2 Kubernetes特点和能力

  • 开源开放
  • 弹性伸缩
  • 服务发现
  • 负载均衡
  • 自愈能力
  • 健康检查
  • 滚动更新
  • 一键回滚
  • 高可用
  • 声明式
  • 多环境
  • 隔离性

1.4 K8s给运维和开发带来的效益和挑战

1.4.1 提升开发效率

之前 之后
多环境程序日志查询困难 无需登录机器即可查询
多环境代码发布迭代缓慢 不可变基础设施一键发布
无关代码占用大量精力 Namespace隔离一键复制
多环境搭建过程复杂 只需要关心业务逻辑代码
环境迁移过程繁琐且费力 通过包管理工具一键迁移
等等 等等

1.4.2 降低运维难度

之前 之后
基础环境管理难度大 一次构建多次部署
宕机人工处理耗精力 全自动容灾机制无需干预
中间件搭建与维护困难 一键扩缩容无需更改配置
应用扩缩容繁琐且复杂 包管理工具一键安装管理
程序端口维护很麻烦 无需特别关心端口冲突
等等 等等

1.5 K8s核心组件及架构剖析

1.5.1 Kubernetes架构

image.png-410.2kB

1.5.2 Kubernetes控制节点核心组件

  • APIServer:APIServer是整个集群的控制中枢,提供集群中各个模块之间的数据交换,并将集群状态和信息存储到分布式键-值(key-value)存储系统Etcd集群中。同时它也是集群管理、资源配额、提供完备的集群安全机制的入口,为集群各类资源对象提供增删改查以及watch的REST API接口。
  • Scheduler:Scheduler是集群Pod的调度中心,主要是通过调度算法将Pod分配到最佳的Node节点,它通过APIServer监听所有Pod的状态,一旦发现新的未被调度到任何Node节点的Pod(pod.spec.nodeName为空),就会根据一系列策略选择最佳节点进行调度,对每一个Pod创建一个绑定(binding),然后被调度的节点上的Kubelet负责启动该Pod。
  • Controller Manager:Controller Manager是集群状态管理器,以保证Pod或其他资源达到期望值。比如集群中某个服务的副本数或其他资源因故障和错误导致无法正常运行,没有达到设定的值时,ControllerManager会尝试自动修复并使其达到期望状态。
  • Etcd:Etcd用作Kubernetes的后台数据库,用于存储Kubernetes集群中的数据。Etcd由CoreOS开发,是一种持久性、轻量型、分布式的键-值(key-value)数据存储组件。

1.5.3 Kubernetes工作节点核心组件

  • Kubelet:负责管理该节点上的Pod,同时对容器进行健康检查及监控,并且负责上报节点和节点上面Pod的状态。
  • Kube-Proxy:负责维护节点上的网络规则,允许从集群内部或外部的网络与Pod进行网络通信。同时负责维护Service和Pod之间的请求路由和流量转发。
  • Container Runtime:符合CRI接口规范的容器运行时,负责管理Kubernetes环境中容器的生命周期。
  • CoreDNS:用于Kubernetes集群内部Service的解析,和上游域名的解析转发。可以让Pod把Service名称解析成Service的IP,然后通过Service的IP地址进行连接到对应的应用上,同时对外部的域名将会转发到外部的DNS进行解析。
  • Calico:符合CNI标准的一个网络插件,它负责给每个Pod分配一个不会重复的IP,并且把每个节点当做一各“路由器”,这样一个节点的Pod就可以通过Pod的IP地址访问到其他节点的Pod。
  • Metrics Server:一个用于Kubernetes集群的监控工具,它负责收集、存储和提供关于集群中各种资源的度量数据,比如CPU和内存。同时为Horizontal Pod Autoscaler(HPA)和Vertical Pod Autoscaler(VPA)提供所需的资源指标数据。

1.5.4 Kubernetes组件细节

  • APIServer:无状态组件,是唯一一个直接和Etcd通信的Kubernetes组件,可以直接进行横向扩容。
  • Scheduler和Controller:有状态组件,主节点信息保存在了leases资源中,可以通过 kubectl get leases -n kube-system 获取,也可以进行横向扩容,选主过程无需人工干预。
  • Kube-Proxy:可选组件,如果使用Cilium作为CNI组件,可以不安装Proxy。
  • Etcd:生产环境中建议部署为大于3的奇数个的Etcd节点,以保证数据的安全性和可恢复性,并且Etcd的数据盘需要使用SSD硬盘。
  • Kubectl:集群的管理工具,只要有Kubeconfig和Kubectl文件,就可以在任意的地方对Kubernetes集群进行管理操作。

1.5.5 Kubernetes交互链路

image.png-239.1kB

1.6 Kubernetes核心资源剖析

1.6.1 Kubernetes常用核心资源分类

image.png-441.3kB

1.6.2 Kubernetes核心资源关系图

image.png-215.2kB

1.7 K8s为什么设计出这么多抽象的概念

1.7.1 K8s设计思想

image.png-323.8kB

1.7.2 K8s调度资源

image.png-572.4kB

1.7.3 K8s服务发布

image.png-513.8kB

1.7.4 K8s配置管理

image.png-379.5kB

1.7.5 K8s资源隔离

image.png-313.8kB

2、K8s快速入门安装

2.1 环境准备

2.1.1 集群规划

主机名称 物理IP 系统 资源配置 说明
k8s-master01 192.168.200.50 Rocky9.4 2C4C40G Master节点
k8s-node01 192.168.200.51 Rocky9.4 2C4C40G Node01节点
k8s-node02 192.168.200.52 Rocky9.4 2C4C40G Node02节点

2.1.2 配置(三节点执行)

# 关闭防火墙
[root@k8s-master01 ~]# systemctl disable --now firewalld
[root@k8s-master01 ~]# systemctl disable --now dnsmasq

# 关闭selinux
[root@k8s-master01 ~]# setenforce 0
[root@k8s-master01 ~]# sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/sysconfig/selinux
[root@k8s-master01 ~]# sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/selinux/config

# 关闭swap分区
[root@k8s-master01 ~]# swapoff -a && sysctl -w vm.swappiness=0
[root@k8s-master01 ~]# sed -ri '/^[^#]*swap/s@^@#@' /etc/fstab
# 配置阿里云镜像源
[root@k8s-master01 ~]# sed -e 's|^mirrorlist=|#mirrorlist=|g' -e 's|^#baseurl=http://dl.rockylinux.org/$contentdir|baseurl=https://mirrors.aliyun.com/rockylinux|g'  -i.bak /etc/yum.repos.d/*.repo

[root@k8s-master01 ~]# dnf makecache
# 安装常用命令
[root@k8s-master01 ~]# yum -y install wget jq psmisc vim net-tools telnet yum-utils device-mapper-persistent-data lvm2 git tree make cmake gcc gcc-c++ lrzsz lsof sysstat tcpdump nc 

#把系统中的命令版本全部更新为最新
[root@k8s-master01 ~]# yum -y update

2.2 Runtime安装(三节点执行)

2.2.1 下载安装 containerd

# 下载源码
[root@k8s-master01 ~]# yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo

# 安装 containerd
[root@k8s-master01 ~]# yum install containerd.io -y

2.2.2 配置内核

# 配置内核
[root@k8s-master01 ~] cat <<EOF | tee /etc/modules-load.d/containerd.conf
overlay
br_netfilter
EOF

[root@k8s-master01 ~] modprobe overlay
[root@k8s-master01 ~] modprobe br_netfilter

[root@k8s-master01 ~] cat <<EOF | tee /etc/sysctl.d/99-kubernetes-cri.conf
net.bridge.bridge-nf-call-iptables  = 1
net.ipv4.ip_forward                 = 1
net.bridge.bridge-nf-call-ip6tables = 1
EOF

[root@k8s-master01 ~] sysctl --system

2.2.3 配置文件

# 创建配置文件
[root@k8s-master01 ~]# mkdir -p /etc/containerd

# 生成配置文件
[root@k8s-master01 ~]# containerd config default | tee /etc/containerd/config.toml

# 修改配置文件
[root@k8s-master01 ~]# sed -i 's#SystemdCgroup = false#SystemdCgroup = true#g' /etc/containerd/config.toml
[root@k8s-master01 ~]# sed -i 's#registry.k8s.io/pause#registry.cn-hangzhou.aliyuncs.com/google_containers/pause#g'  /etc/containerd/config.toml

[root@k8s-master01 ~]# sed -n "67p;139p" /etc/containerd/config.toml
    sandbox_image = "registry.cn-hangzhou.aliyuncs.com/google_containers/pause:3.8"
            SystemdCgroup = true
# 启动Containerd
[root@k8s-master01 ~]# systemctl daemon-reload
[root@k8s-master01 ~]# systemctl enable --now containerd

[root@k8s-master01 ~]# ctr plugin ls|egrep "overlayfs|cri"
io.containerd.snapshotter.v1           overlayfs                linux/amd64    ok        
io.containerd.grpc.v1                  cri                      linux/amd64    ok  

2.3 Kubernetes安装

2.3.1 下载安装k8s(三节点执行)

# 配置源
[root@k8s-master01 ~]# cat <<EOF | tee /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.32/rpm/
enabled=1
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.32/rpm/repodata/repomd.xml.key
EOF
# 安装k8s
[root@k8s-master01 ~]# yum install kubeadm-1.32.* kubelet-1.32.* kubectl-1.32.* -y

# 启动k8s
[root@k8s-master01 ~]# systemctl enable --now kubelet

2.3.2 初始化集群

# 下载镜像(三节点执行)
[root@k8s-master01 ~]# kubeadm config images pull --image-repository registry.cn-hangzhou.aliyuncs.com/google_containers --kubernetes-version 1.32.5
# 初始化集群(master节点执行)
[root@k8s-master01 ~]# kubeadm init --apiserver-advertise-address 192.168.200.50 --image-repository registry.cn-hangzhou.aliyuncs.com/google_containers --cri-socket "unix:///var/run/containerd/containerd.sock" --kubernetes-version 1.32.5
...
To start using your cluster, you need to run the following as a regular user:

  mkdir -p $HOME/.kube
  sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
  sudo chown $(id -u):$(id -g) $HOME/.kube/config

Alternatively, if you are the root user, you can run:

  export KUBECONFIG=/etc/kubernetes/admin.conf

You should now deploy a pod network to the cluster.
Run "kubectl apply -f [podnetwork].yaml" with one of the options listed at:
  https://kubernetes.io/docs/concepts/cluster-administration/addons/

Then you can join any number of worker nodes by running the following on each as root:

kubeadm join 192.168.200.50:6443 --token 4skn39.a1m3ugn8znmarchv \
	--discovery-token-ca-cert-hash sha256:e05d83a90f8aa46b37afea87abc5ff7121c708c93b9c87e54d67b0a045b78ebb
	
[root@k8s-master01 ~]# mkdir -p $HOME/.kube
[root@k8s-master01 ~]# sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
[root@k8s-master01 ~]# sudo chown $(id -u):$(id -g) $HOME/.kube/config
# 工作节点加入集群
[root@k8s-master01 ~]# kubeadm join 192.168.200.50:6443 --token 4skn39.a1m3ugn8znmarchv \
	--discovery-token-ca-cert-hash sha256:e05d83a90f8aa46b37afea87abc5ff7121c708c93b9c87e54d67b0a045b78ebb

2.4 K8s Addons安装(master节点)

# 拉取包
[root@k8s-master01 ~]# git clone https://gitee.com/dukuan/k8s-ha-install.git
[root@k8s-master01 ~]# cd k8s-ha-install/
# 切换到对应的分支
[root@k8s-master01 k8s-ha-install]# git checkout remotes/origin/manual-installation-v1.32.x

# 安装
[root@k8s-master01 k8s-ha-install]# cd single/
[root@k8s-master01 single]# kubectl apply -f .

# 查看安装完的pod
[root@k8s-master01 single]# kubectl get pod -n kube-system
NAME                                       READY   STATUS    RESTARTS   AGE
calico-kube-controllers-6f497d8478-5n2db   1/1     Running   0          11m
calico-node-g58pw                          1/1     Running   0          11m
calico-node-l5ql9                          1/1     Running   0          11m
calico-node-mfs28                          1/1     Running   0          11m
coredns-76fccbbb6b-vnwpf                   1/1     Running   0          25m
coredns-76fccbbb6b-vqmg7                   1/1     Running   0          25m
etcd-k8s-master01                          1/1     Running   0          25m
kube-apiserver-k8s-master01                1/1     Running   0          25m
kube-controller-manager-k8s-master01       1/1     Running   0          25m
kube-proxy-98cz6                           1/1     Running   0          20m
kube-proxy-bpxfw                           1/1     Running   0          25m
kube-proxy-tfwdl                           1/1     Running   0          20m
kube-scheduler-k8s-master01                1/1     Running   0          25m
metrics-server-57954884df-6jsl9            1/1     Running   0          11m
# 查看节点状态
[root@k8s-master01 single]# kubectl get nodes
NAME           STATUS   ROLES           AGE   VERSION
k8s-master01   Ready    control-plane   26m   v1.32.5
k8s-node01     Ready    <none>          21m   v1.32.5
k8s-node02     Ready    <none>          21m   v1.32.5

[root@k8s-master01 single]# kubectl top node
NAME           CPU(cores)   CPU(%)   MEMORY(bytes)   MEMORY(%)   
k8s-master01   219m         10%      787Mi           22%         
k8s-node01     86m          4%       375Mi           10%         
k8s-node02     119m         5%       818Mi           23% 

2.5 K8s 可视化操作Dashboard

# 查看PORT信息
[root@k8s-master01 ~]# kubectl get svc -n kubernetes-dashboard
NAME                        TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)         AGE
dashboard-metrics-scraper   ClusterIP   10.101.245.105   <none>        8000/TCP        16m
kubernetes-dashboard        NodePort    10.106.178.95    <none>        443:31397/TCP   16m

web界面 浏览器访问

image.png-63.1kB

# 生成一个管理员的token
# 生成的token默认2小时,如果想延长可以在命令后加上`--duration=365h`
[root@k8s-master01 ~]# kubectl create token admin-user -n kube-system
eyJhbGciOiJSUzI1NiIsImtpZCI6ImtiTm05eWxpaVR2WEFPM25hblMyX09SdXZndVZBN3lxWElwMjhvVjdudW8ifQ.eyJhdWQiOlsiaHR0cHM6Ly9rdWJlcm5ldGVzLmRlZmF1bHQuc3ZjLmNsdXN0ZXIubG9jYWwiXSwiZXhwIjoxNzQ4ODczNDAyLCJpYXQiOjE3NDg4Njk4MDIsImlzcyI6Imh0dHBzOi8va3ViZXJuZXRlcy5kZWZhdWx0LnN2Yy5jbHVzdGVyLmxvY2FsIiwianRpIjoiMGE0MDQ0NjItNzg0YS00ZmUyLTg0NzYtYTk4NTA5MmJmYTVkIiwia3ViZXJuZXRlcy5pbyI6eyJuYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsInNlcnZpY2VhY2NvdW50Ijp7Im5hbWUiOiJhZG1pbi11c2VyIiwidWlkIjoiMTg1Y2M1NzYtMGRlZS00MDBjLWIyYjctYmUwODZhODVhMGM0In19LCJuYmYiOjE3NDg4Njk4MDIsInN1YiI6InN5c3RlbTpzZXJ2aWNlYWNjb3VudDprdWJlLXN5c3RlbTphZG1pbi11c2VyIn0.bhHey0nIj0J-z2UrtMu9MlfKDwlO48WbL7vK3WiGrBuNoroE5TYljU8nMdY3oAM1EUr5iCsLgeBV9l-MUkIFHZ6FmmZhyKyXe_pRM5lzIrVWb0x8aNhvYmuKdryfBrdX8nLpgCu41aA8ojLJgc3Q05Mt9vEKmRr0-3QBDVLhKQh1Fq7rROAIM79eucxMvnSDGfPb57-yuY_3H0mm8PnRRBNY8Sm2Azo5iQS0A7G1xe1jyAElfEPUHCSHS5472xxJaA7XXIaZWOhcD-Qsb736q1VqIxogTPYeqidI77i4O4njK-alroyui91UXB7iULZQ4HZrvHIdCa-_wRxpcH9D1w

image.png-66.3kB

image.png-149.5kB

2.6 快速上线一个服务

# 通过一个镜像创建一个pod
[root@k8s-master01 ~]# kubectl create deployment counter --image=crpi-q1nb2n896zwtcdts.cn-beijing.personal.cr.aliyuncs.com/ywb01/counter:v1

# 查看
[root@k8s-master01 ~]# kubectl get deployment
NAME      READY   UP-TO-DATE   AVAILABLE   AGE
counter   1/1     1            1           51s
[root@k8s-master01 ~]# kubectl get po
NAME                       READY   STATUS    RESTARTS   AGE
counter-7dd9fb465f-8j2wq   1/1     Running   0          4m25s

# 编辑一个服务
kubectl edit deployment counter

# 删除一个服务
kubectl delete deployment counter
# 如何暴露一个k8s端口能被外部访问
[root@k8s-master01 ~]# kubectl expose deployment counter --port 80 --type NodePort 

[root@k8s-master01 ~]# kubectl get svc
NAME         TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE
counter      NodePort    10.110.6.148   <none>        80:31345/TCP   4s
kubernetes   ClusterIP   10.96.0.1      <none>        443/TCP        58m

web界面 浏览器访问

image.png-23kB

此博客来源于:https://edu.51cto.com/lecturer/11062970.html