k8s的核心组件、运行时的理解

一、kubelet、CRI、运行时的关系

1、CRI(Container Runtime Interface)是一个标准化的接口

容器运行时接口 用于 kubelet 与容器运行时(container runtime)之间的通信。

🔁 CRI:Kubernetes 和容器运行时的桥梁

  • Kubernetes 通过 CRI(Container Runtime Interface) 与容器运行时通信。

  • 不直接绑定某个运行时,只要符合 CRI 标准都能用。

  • 这也是为什么可以支持 containerd、CRI-O 等多种运行时。

2. CRI 接口集成封装在kubelet 中

CRI 接口的集成和封装主要位于 kubelet 的代码中,具体在 Kubernetes 源码的以下部分:

  • 代码位置
    • CRI 的实现主要在 Kubernetes 源码的 pkg/kubelet 目录下,尤其是与容器运行时交互相关的模块。
    • 核心文件包括:
      • pkg/kubelet/container_runtime.go:定义了容器运行时的接口和抽象。
      • pkg/kubelet/kuberuntime:实现了基于 CRI 的容器运行时逻辑。
      • pkg/kubelet/cri:包含 CRI 客户端的实现,用于与容器运行时通信。
    • CRI 客户端通过 gRPC 协议与容器运行时进行交互,gRPC 相关代码位于 vendor/k8s.io/cri-api 中。
  • 实现细节
    • kubelet 通过 CRI 定义的 gRPC 接口与容器运行时通信。CRI 接口由 k8s.io/cri-api 提供,定义了如 RuntimeService 和 ImageService 等服务。
    • kubelet 的 kuberuntime 组件负责将 Pod 的操作(创建、删除、更新等)转换为 CRI 的 gRPC 调用。
    • 具体来说,kuberuntime_manager.go 中的 KubeGenericRuntimeManager 是 CRI 的主要封装点,它实现了 ContainerRuntime 接口,处理 Pod 和容器的生命周期管理。

3、CRI Shim(CRI 接口的 gRPC 服务端)

  • 容器运行时(如 containerd、CRI-O)实现了 CRI 接口的 gRPC 服务端(称为 CRI Shim)。kubelet 作为客户端通过 gRPC 调用这些服务。
  • 例如,containerd 的 cri plugin 位于 containerd 的 plugins/cri 模块中,负责处理 kubelet 的 CRI 请求。

4、常见的容器运行时有哪些?

容器运行时描述当前使用情况
containerd 轻量、稳定,由 Docker 拆分出来 ✅ Kubernetes 默认推荐
CRI-O 为 Kubernetes 专门设计,兼容 CRI ✅ 常用于 Red Hat 系
Docker(已不推荐) 早期广泛使用,现在 Kubernetes 已弃用其作为运行时 ❌ v1.20+ 已不推荐
runc 实际执行容器的底层工具(containerd 的依赖) 🔧 containerd 的内部组件

kubelet、CRI 和容器运行时之间的关系可以总结为以下层次结构和工作流程:

关系概述

  • kubelet
    • kubelet 是 Kubernetes 节点上的核心组件,负责管理节点上的 Pod 和容器。
    • 它通过 CRI 与容器运行时通信,抽象了底层容器运行时的具体实现。
    • kubelet 并不直接操作容器,而是通过 CRI 接口将任务委托给容器运行时。
  • CRI(Container Runtime Interface)
    • CRI 是 Kubernetes 定义的一套标准化 gRPC 接口,桥接 kubelet 和容器运行时。
    • 它定义了两类服务:
      • RuntimeService:用于管理 Pod 和容器的生命周期(如创建、启动、停止、删除)。
      • ImageService:用于管理容器镜像(如拉取、删除)。
    • CRI 的设计目标是解耦 kubelet 和容器运行时,允许 Kubernetes 支持多种容器运行时(如 containerd、CRI-O、Docker 等)。
  • Container Runtime
    • 容器运行时是实际执行容器操作的组件,负责创建、运行、停止容器,以及管理镜像和存储等。
    • 常见的容器运行时包括:
      • containerd:通过其 CRI 插件支持 CRI。
      • CRI-O:专为 Kubernetes 设计的轻量级 CRI 运行时。
      • Docker(早期):通过 dockershim 适配 CRI(现已废弃)。
    • 容器运行时通过 CRI Shim 实现 CRI 的 gRPC 服务端,响应 kubelet 的请求。

工作流程

  1. Pod 创建流程
    • kubelet 接收到 API Server 的 Pod 创建请求。
    • kubelet 通过 CRI 的 gRPC 客户端调用容器运行时的 RuntimeService(如 CreatePodSandbox)。
    • 容器运行时创建 Pod 沙箱(sandbox,通常是一个 pause 容器,提供网络和命名空间)。
    • kubelet 再通过 CRI 调用 CreateContainer 和 StartContainer 创建并启动容器。
  2. 镜像管理
    • kubelet 通过 CRI 的 ImageService 调用容器运行时的镜像管理功能(如 PullImage)。
    • 容器运行时负责从镜像仓库拉取镜像并存储。
  3. 通信方式
    • kubelet 和容器运行时通过 gRPC 协议通信(通常通过 Unix socket,如 /run/containerd/containerd.sock)。
    • CRI Shim 在容器运行时中处理这些 gRPC 请求,并将任务转换为底层容器操作(如调用 runc)。

kubelet -> CRI (gRPC) -> CRI Shim -> 底层容器运行时(如 runc) 图解

+-----------------+
|     kubelet     |
|  (CRI Client)   |
+-----------------+
         |
         | gRPC (CRI 接口)
         v
+-----------------+
|  CRI Shim       |
| (containerd/CRI-O)|
+-----------------+
         |
         | 底层容器操作
         v
+-----------------+
|  runc/libcontainer |
|  (实际容器执行)  |
+-----------------+

6、k8s 为啥放弃docker

  • 多了一层: Docker 本身依赖 containerd、runc,使用它比直接用 containerd 更复杂。

  • 性能和维护负担: Dockershim 增加了维护成本。

  • CRI-O、containerd 已完全兼容容器运时接口CRI,更轻、更快。

Kubelet
  ├─> CRI 接口
  │     └─> Dockershim
  │           └─> Docker Engine API
  │                 └─> containerd(Docker 内部用)
  │                       └─> runc

二、核心组件

1、master节点组件:

组件功能简介默认部署位置
kube-apiserver 所有组件的 API 接口,是集群的“网关”唯一入口,并提供认证、授权、访问控制、API 注册和发现等机制; Master 节点
etcd 集群的配置和状态数据库,保存所有对象信息(Pod、Deployment等) Master 节点
kube-scheduler 负责 Pod 的调度(选择运行在哪个 Node 上) Master 节点
kube-controller-manager 各种控制器的集合,负责维护集群的状态,故障检测,自动扩展、滚动更新 Master 节点
cloud-controller-manager(可选) 云平台资源控制器,如负载均衡器、云盘、节点自动注册等 Master 节点(公有云场景)

2、从节点节点组件:

组件功能简介默认部署位置
kubelet 每个节点上的“守护进程”,负责接收并执行 Pod 管理命令(启动、停止容器) 所有 Node
kube-proxy 负责实现 Kubernetes 的 Service 网络代理和负载均衡(iptables 或 IPVS 模式) 所有 Node
容器运行时(Container Runtime) 实际启动容器,如 containerd、CRI-O 等(支持 CRI) 所有 Node
cni 网络插件(非K8s原生) 提供 Pod 间通信能力,如 Calico、Flannel、Cilium 等 所有 Node
日志/监控插件(可选) 如 Fluentd、Promtail(日志采集),Node Exporter(指标) 所有 Node

3、maste 节点和从节点的通信:

  • 所有通信都通过 kube-apiserver 中转。

  • kubeletkube-proxy 会周期性与 apiserver 保持心跳/状态同步。

  • 控制器通过kube-apiserver 中转监听 etcd 中的变化来驱动状态变更。

组件心跳/同步机制默认时间相关参数
Kubelet 更新 Node Lease 和 Node Status 心跳/状态更新:10秒 --node-status-update-frequency
Kube-Proxy Watch Service/Endpoints,同步网络规则 同步周期:30秒 --proxy-sync-period
Etcd 内部 Raft 心跳,API Server watch 数据变更 心跳:100毫秒,选举超时:1秒 --heartbeat-interval--election-timeout
Kube-Controller-Manager Watch 资源变化,Node Controller 检查节点状态 节点检查:5秒 --node-monitor-period--node-eviction-rate
Kube-Scheduler Watch Pod/Node 变化,调度 Pod 实时(依赖 watch) 无明确心跳参数
Kube-API-Server 更新 Lease 对象,发布自身身份 秒级(未明确指定) 无明确心跳参数

比如典型的创建 Pod 的流程为

  • kubectl -> API Server:提交 Pod 定义(HTTP/HTTPS)。
  • API Server -> etcd:存储 Pod 对象(gRPC/HTTP)。
  • Scheduler -> API Server:查询 Pod 和节点,绑定节点(HTTP/HTTPS)。
  • kubelet -> API Server:监控分配的 Pod(HTTP/HTTPS)。
  • kubelet -> Container Runtime:通过 CRI(gRPC)创建沙箱、拉取镜像、启动容器。
  • Container Runtime -> runc:执行容器操作(本地调用)。
  • kubelet -> API Server:更新 Pod 状态(HTTP/HTTPS)。  

三、集群用到的端口号

注意iptables卸载后,docker将无法运行

 

k8s中rancher的高可用,端口

 https://kubernetes.feisky.xyz/concepts/components

 

Auto Copied
posted @ 2020-05-14 14:13  凡人半睁眼  阅读(1224)  评论(0)    收藏  举报