最新版 Kubernetes 集群搭建教程(kubeadm 方式)

一、版本选择与调整原因

1. 核心版本升级

本次教程将 Kubernetes 版本从 1.18.0 升级至1.28.x (当前稳定且应用广泛的版本),Docker 替换为containerd(K8s 1.24 + 已移除对 Docker 的直接支持,Docker 作为 CRI 需通过 cri-dockerd 适配,而 containerd 是 K8s 官方推荐的容器运行时)。

2. 调整核心原因

  • Docker CRI 支持移除:K8s 1.24 + 不再内置对 Docker 的 CRI 支持,继续用 Docker 需额外安装 cri-dockerd,而 containerd 是 CNCF 毕业项目,原生适配 K8s,性能更优、资源占用更低。
  • 版本兼容性:1.18.0 为 2020 年版本,存在大量安全漏洞和功能限制,1.28.x 修复了漏洞,支持更多新特性(如原生容器网络策略增强、StatefulSet 扩容优化等)。
  • 镜像源优化:原 CentOS 7 官方源失效,且部分镜像仓库(如 quay.io)国内访问不稳定,替换为阿里云、网易云等国内镜像源。
  • 系统要求适配:新增对内核参数、SELinux、防火墙的更精细配置,适配新版 K8s 的安全要求。

二、核心术语解释

术语 解释
kubeadm K8s 官方提供的集群部署工具,自动化完成集群初始化、节点加入等核心流程,降低部署门槛
containerd 轻量级容器运行时(CRI),负责容器生命周期管理(创建、启动、停止),是 K8s 1.24 + 默认推荐的 CRI
CRI(Container Runtime Interface) 容器运行时接口,K8s 通过该接口与容器运行时交互,解耦 K8s 与具体容器运行时实现
Pod K8s 最小部署单元,包含一个或多个容器,共享网络、存储资源
Node K8s 集群的工作节点(Master/Worker),Master 负责控制平面,Worker 负责运行业务 Pod
kubelet 运行在每个 Node 上的核心组件,负责维护 Pod 生命周期,与 Master 通信执行调度指令
CNI(Container Network Interface) 容器网络接口,定义 Pod 之间、Pod 与外部网络的通信规则,本次使用 Calico(替代原 Flannel,功能更丰富)
swap 分区 磁盘虚拟内存,K8s 禁止 swap 是为了保证 Pod 资源调度的准确性(避免 Pod 使用 swap 导致性能波动)
控制平面(Control Plane) 集群的管理节点,包含 kube-apiserver、etcd、kube-controller-manager、kube-scheduler 等核心组件

三、环境准备

1. 服务器要求

角色 配置 数量 IP 示例 操作系统
Master 2 核 4G 以上,硬盘 40G+ 1(单 Master) 192.168.177.130 CentOS 7.x/8.x(推荐 7.9)
Worker 2 核 2G 以上,硬盘 40G+ 2 192.168.177.131/132 CentOS 7.x/8.x

2. 基础环境要求

  • 所有节点网络互通,能访问外网(或配置内网镜像源);
  • 禁止 swap 分区(K8s 强制要求,避免资源调度异常);
  • 内核版本≥3.10(CentOS 7 默认满足,CentOS 8 需≥4.18);
  • 关闭 SELinux、防火墙(或配置放行 K8s 端口)。

四、全节点初始化操作

1. 系统基础配置

复制代码
# 1. 关闭防火墙(生产环境可按需放行端口,此处为简化)
systemctl stop firewalld && systemctl disable firewalld
# 放行关键端口(生产环境推荐)
# firewall-cmd --permanent --add-port=6443/tcp --add-port=2379-2380/tcp --add-port=10250-10259/tcp
# firewall-cmd --reload && systemctl restart firewalld

# 2. 关闭SELinux
sed -i 's/^SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config
setenforce 0

# 3. 关闭swap(永久+临时)
swapoff -a
sed -i '/swap/s/^/#/' /etc/fstab

# 4. 设置主机名(按角色执行)
# Master节点
hostnamectl set-hostname k8s-master
# Worker1节点
hostnamectl set-hostname k8s-worker1
# Worker2节点
hostnamectl set-hostname k8s-worker2

# 5. 配置hosts(所有节点执行)
cat >> /etc/hosts << EOF
192.168.177.130 k8s-master
192.168.177.131 k8s-worker1
192.168.177.132 k8s-worker2
EOF

# 6. 配置内核参数(适配K8s网络)
cat > /etc/sysctl.d/k8s.conf << EOF
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1  # 开启IP转发,解决Pod网络互通
vm.swappiness = 0        # 禁止使用swap
EOF
sysctl --system  # 生效内核参数

# 7. 时间同步(确保集群节点时间一致)
#CentOS 7 官方源已经失效 导致 yum 报错
mkdir -p /etc/yum.repos.d/bak
mv /etc/yum.repos.d/*.repo /etc/yum.repos.d/bak/

curl -o /etc/yum.repos.d/CentOS-Base.repo https://mirrors.aliyun.com/repo/Centos-7.repo

sed -i 's/mirrorlist/#mirrorlist/g' /etc/yum.repos.d/CentOS-Base.repo
sed -i 's|#baseurl=http://mirror.centos.org|baseurl=https://mirrors.aliyun.com|g' /etc/yum.repos.d/CentOS-Base.repo

yum clean all
yum makecache

# 时间同步
yum install ntpdate -y
ntpdate time.windows.com

# 8. 安装依赖包
yum install -y wget vim curl iproute-tc conntrack-tools

2. 安装 containerd(替代 Docker)

复制代码
# 1. 安装containerd(从阿里云源安装)
yum install -y yum-utils
yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
yum install -y containerd.io

# 2. 生成containerd默认配置
mkdir -p /etc/containerd
containerd config default > /etc/containerd/config.toml

# 3. 修改配置(替换镜像源+设置SystemdCgroup)
sed -i 's/registry.k8s.io\/pause/registry.aliyuncs.com\/google_containers\/pause/g' /etc/containerd/config.toml
sed -i 's/SystemdCgroup = false/SystemdCgroup = true/g' /etc/containerd/config.toml  # 适配Systemd cgroup

# 4. 重启并设置开机自启
systemctl restart containerd && systemctl enable containerd

3. 安装 kubeadm、kubelet、kubectl

复制代码
# 1. 添加K8s阿里云源
cat > /etc/yum.repos.d/kubernetes.repo << EOF
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64/
enabled=1
gpgcheck=1
repo_gpgcheck=1
gpgkey=https://mirrors.aliyun.com/kubernetes/yum/doc/yum-key.gpg https://mirrors.aliyun.com/kubernetes/yum/doc/rpm-package-key.gpg
EOF

# 2. 安装指定版本(1.28.2为稳定版)
yum install -y kubeadm-1.28.2 kubelet-1.28.2 kubectl-1.28.2
systemctl enable kubelet  # kubelet需等待集群初始化后启动

五、初始化 Master 节点

1. 集群初始化

复制代码
kubeadm init --apiserver-advertise-address=192.168.190.136 --image-repository=registry.aliyuncs.com/google_containers --kubernetes-version=v1.28.2 --service-cidr=10.96.0.0/12 --pod-network-cidr=10.244.0.0/16 --ignore-preflight-errors=all

解释:

复制代码
kubeadm init \
  --apiserver-advertise-address=192.168.177.130 \  # Master节点IP
  --image-repository=registry.aliyuncs.com/google_containers \  # 国内镜像源
  --kubernetes-version=v1.28.2 \  # K8s版本
  --service-cidr=10.96.0.0/12 \  # Service虚拟网络段(固定)
  --pod-network-cidr=10.244.0.0/16 \  # Pod网络段(需与CNI插件配置一致)
  --ignore-preflight-errors=all  # 忽略预检错误(生产环境按需关闭)

2. 配置 kubectl(Master 节点)

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

# 验证配置
kubectl get nodes  # 此时Master节点状态为NotReady(未安装CNI)

3. 保存节点加入命令

初始化完成后,终端会输出kubeadm join命令(如下示例),务必保存

复制代码
kubeadm join 192.168.177.130:6443 --token abcdef.0123456789abcdef \
  --discovery-token-ca-cert-hash sha256:xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

若丢失 token,可通过以下命令重新生成:

复制代码
kubeadm token create --print-join-command

六、安装 CNI 网络插件(Calico)(master)

1. 下载 Calico 配置文件

复制代码
#下载并修改 Calico 网络配置
wget https://ghproxy.com/https://raw.githubusercontent.com/projectcalico/calico/v3.26.1/manifests/calico.yaml -O calico.yaml

# 修改Pod网络段(需与kubeadm init的--pod-network-cidr一致)
sed -i 's/192.168.0.0\/16/10.244.0.0\/16/g' calico.yaml

#安装
kubectl apply -f calico.yaml

2. 部署 Calico

复制代码
# 验证Calico Pod状态
kubectl get pods -n kube-system | grep calico
# 等待5分钟,验证Master节点状态
kubectl get nodes  # 状态变为Ready即为成功

七、加入 Worker 节点

1. 执行加入命令(所有 Worker 节点)

work 节点 只需要做一件事

执行从 master 复制过来的 kubeadm join 加入命令其他什么都不用做!

复制代码
# 替换为自己保存的join命令
kubeadm join 192.168.177.130:6443 --token abcdef.0123456789abcdef \
  --discovery-token-ca-cert-hash sha256:xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx

2. 验证集群节点

回到 Master 节点执行:

复制代码
kubectl get nodes
# 输出示例(所有节点状态为Ready)
NAME         STATUS   ROLES           AGE   VERSION
k8s-master   Ready    control-plane   10m   v1.28.2
k8s-worker1  Ready    <none>          5m    v1.28.2
k8s-worker2  Ready    <none>          5m    v1.28.2

八、集群测试

1. 创建 Nginx Deployment

复制代码
kubectl create deployment nginx --image=nginx:1.25-alpine
# 扩缩容为2个副本
kubectl scale deployment nginx --replicas=2
# 查看Pod状态
kubectl get pods

2. 暴露 Nginx 服务

复制代码
# 暴露NodePort类型服务(外网可访问)
kubectl expose deployment nginx --port=80 --type=NodePort
# 查看服务端口
kubectl get svc nginx
# 输出示例
NAME    TYPE       CLUSTER-IP      EXTERNAL-IP   PORT(S)        AGE
nginx   NodePort   10.96.123.45    <none>        80:30080/TCP   1m

3. 访问测试

在浏览器访问http://Worker节点IP:30080(如http://192.168.177.131:30080),能看到 Nginx 默认页面即为成功。

九、常见问题与解决方案

1. 节点状态 NotReady

  • 原因:CNI 插件未部署或部署失败;

  • 解决:重新部署 Calico,查看 Calico Pod 日志

    复制代码
    kubectl logs -n kube-system calico-node-xxxxxx

2. containerd 启动失败

  • 原因:SystemdCgroup 未开启;
  • 解决:重新修改/etc/containerd/config.toml,确保SystemdCgroup = true,重启 containerd。

3. 镜像拉取失败

  • 原因:外网访问受限;
  • 解决:使用阿里云镜像源,或提前下载镜像导入节点。

十、与旧版教程的核心差异总结

维度 旧版(1.18.0+Docker) 新版(1.28.2+containerd) 调整原因
容器运行时 Docker containerd K8s 1.24 + 移除 Docker CRI 支持,containerd 原生适配
网络插件 Flannel Calico Calico 支持网络策略、跨子网通信,功能更丰富
镜像源 部分依赖国外仓库 全量国内镜像源 解决国内访问不稳定问题
内核参数 基础配置 新增 IP 转发、cgroup 配置 适配新版 K8s 的安全和网络要求
版本兼容性 老旧版本,漏洞多 稳定新版,功能完善 生产环境需使用安全、稳定的版本
相关推荐
Monster丶6262 小时前
Docker 部署 Ollama 全流程指南:支持 CPU/GPU、生产环境可用的工程化实践
运维·人工智能·docker·容器
白花生2 小时前
k8s集群内的ollama pod持久化调用本地大模型
云原生·容器·kubernetes
hkNaruto2 小时前
【Docker】关于hub.docker.com,无法打开,国内使用dockers.xuanyuan.me搜索容器镜像、查看容器镜像的使用文档
运维·docker·容器
秋刀鱼什么味_2 小时前
kubernetes服务质量之QoS类
容器·kubernetes
姚不倒2 小时前
从 Docker 到 Kubernetes:容器编排核心原理与网络实践
运维·云原生·容器·kubernetes
m0_694845574 小时前
Docker 从入门到实践教程:docker_practice 完整学习指南
运维·服务器·docker·容器·云计算·github
qq_254674415 小时前
Docker Docker Compose
运维·docker·容器
Aurora(^*_*^)5 小时前
docker 部署openclaw踩坑记录
运维·docker·容器
人间打气筒(Ada)6 小时前
go实战案例:如何基于 Conul 给微服务添加服务注册与发现?
开发语言·微服务·zookeeper·golang·kubernetes·etcd·consul