本文将力图说清楚如何使用kubeadm快速部署一个Kubernetes v1.30.13集群,并简单说明如何在集群上部署MetalLB、Metrics Server、Ingress Nginx和Kuboard等Add-Ons,以帮助读者朋友快速构建出基本生产可用的Kubernetes集群环境。
一、主机环境预设
本示例中的Kubernetes集群部署将基于以下环境进行。
OS: Ubuntu 22.04
Kubernetes:v1.30
Container Runtime:
Continerd.io 1.7.27
二、 测试环境说明
测试使用的Kubernetes集群可由一个master主机及一个以上(建议至少两个)node主机组成,这些主机可以是物理服务器,也可以运行于vmware、virtualbox或kvm等虚拟化平台上的虚拟机,甚至是公有云上的VPS主机。
本测试环境将由k8s-master01、k8s-node01、k8s-node02和k8s-node03四个独立的主机组成,它们分别拥有4核心的CPU及8G的内存资源,操作系统环境均为最小化部署的Ubuntu Server 22.04.5 LTS,启用了SSH服务,域名为joe.com。此外,各主机需要预设的系统环境如下:
(1)借助于chronyd服务(程序包名称chrony)设定各节点时间精确同步;
(2)通过DNS完成各节点的主机名称解析;
root@joe:~# echo "k8s-master01" | sudo tee /etc/hostname
k8s-master01
root@joe:~# reboot #重启
(3)各节点禁用所有的Swap设备;
root@joe:~# vim /etc/fstab

sudo systemctl daemon-reexec
sudo systemctl restart kubelet
(4)各节点禁用默认配置的iptables防火墙服务;
ufw disable
注意:为了便于操作,后面将在各节点直接以系统管理员root用户进行操作。若用户使用了普通用户,建议将如下各命令以sudo方式运行。
2.1 Ubuntu 切换root用户访问操作
2.1.1 切换root用户
root@joe:/home/joe# sudo -s
2.1.2 设置 root 用户的密码。
root@joe:/home/joe# sudo passwd root
New password:
Retype new password:
passwd: password updated successfully
2.1.3 启用 root 用户
root@joe:/home/joe# sudo passwd -u root
passwd: password expiry information changed.
root@joe:/home/joe#
2.1.4 修改/etc/ssh/sshd_config文件
root@joe:/home/joe# vim /etc/ssh/sshd_config
修改如图:
修改前:
![图片[1] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/34cca2f948b5466493e1d0a16c06cb29.png)
修改后:

2.1.5保存修改,重启ssh服务

root@joe:/home/joe# service ssh restart
三、设定时钟同步
若节点可直接访问互联网,安装chrony程序包后,可直接启动chronyd系统服务,并设定其随系统引导而启动。随后,chronyd服务即能够从默认的时间服务器同步时间。
第一种方式:
root@k8s-master01:~# timedatectl set-timezone Asia/Shanghai
第二种方式:
root@k8s-node02:~# apt install chrony
root@k8s-node02:~# systemctl start chrony.service
四、主机名称解析
出于简化配置步骤的目的,本测试环境使用hosts文件进行各节点名称解析,文件内容如下所示。其中,我们使用kubeapi主机名作为API Server在高可用环境中的专用接入名称,也为控制平面的高可用配置留下便于配置的余地。
注意:192.168.56.10是配置在第一个master节点k8s-master01上的第二个地址。在高可用的master环境中,它可作为VIP,由keepalived进行管理。但为了简化本示例先期的部署过程,这里直接将其作为辅助IP地址,配置在k8s-master01节点之上。
| IP地址 | 主机名 |
|---|---|
| 192.168.56.10 | kubeapi.joe.com kubeapi |
| 192.168.56.32 | k8s-master01.joe.com k8s-master01 |
| 192.168.56.20 | k8s-master02.joe.com k8s-master01 |
| 192.168.56.21 | k8s-master03.joe.com k8s-master03 |
| 192.168.56.27 | k8s-node01.joe.com k8s-node01 |
| 192.168.56.30 | k8s-node02.joe.com k8s-node02 |
| 192.168.56.31 | k8s-node03.joe.com k8s-node03 |
提示:本示例后续的部署步骤中,并未使用k8s-master02和k8s-master03两个主机来部署高可用的master,只是为了便于后续为其设置高可用环境而保留的预设,因此,它们是可选的主机。

五、 安装程序包
Ubuntu 22.04上安装Containerd有两种选择,一是Ubuntu系统官方程序包仓库中的containerd,另一个则是Docker社区提供的containerd.io。本文将选择使用后者。
5.1 安装并启动Containerd.io
首先,生成containerd.io相关程序包的仓库,这里以阿里云的镜像服务器为例进行说明:
以下在所有节点上都要做
root@k8s-master01:~# root@k8s-master01:~# apt -y install apt-transport-https ca-certificates curl software-properties-common
root@k8s-master01:~# curl -fsSL http://mirrors.aliyun.com/docker-ce/linux/ubuntu/gpg | apt-key add -
Warning: apt-key is deprecated. Manage keyring files in trusted.gpg.d instead (see apt-key(8)).
OK
root@k8s-master01:~# add-apt-repository "deb [arch=amd64] http://mirrors.aliyun.com/docker-ce/linux/ubuntu $(lsb_release -cs) stable"
root@k8s-master01:~# apt update
接下来,安装相关的程序包,Ubuntu 22.04上要使用的程序包名称为containerd.io。
root@k8s-master01:~# apt-get install containerd.io
5.2 配置Containerd.io
首先,运行如下命令打印默认并保存默认配置
root@k8s-master01:~# mkdir /etc/containerd
root@k8s-master01:~# containerd config default > /etc/containerd/config.toml
接下来,编辑生成的配置文件,完成如下几项相关的配置:
root@k8s-master01:~# vim /etc/containerd/config.toml
1.修改containerd使用SystemdCgroup
[plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc]
[plugins."io.containerd.grpc.v1.cri".containerd.runtimes.runc.options]
SystemdCgroup = true
![图片[2] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/89474ce3f61c4b23aeff6fda89c22732.png)
2.配置Containerd使用国内Mirror站点上的pause镜像及指定的版本
[plugins."io.containerd.grpc.v1.cri"]
sandbox_image = "registry.aliyuncs.com/google_containers/pause:3.8"
3.配置Containerd使用国内的Image加速服务,以加速Image获取
[plugins."io.containerd.grpc.v1.cri".registry.configs]
[plugins."io.containerd.grpc.v1.cri".registry.configs."registry.magedu.com".tls]
insecure_skip_verify = true
[plugins."io.containerd.grpc.v1.cri".registry.headers]
[plugins."io.containerd.grpc.v1.cri".registry.mirrors]
[plugins."io.containerd.grpc.v1.cri".registry.mirrors."docker.io"]
endpoint = ["https://docker.mirrors.ustc.edu.cn", "https://registry.docker-cn.com"]
[plugins."io.containerd.grpc.v1.cri".registry.mirrors."registry.k8s.io"]
endpoint = ["https://registry.aliyuncs.com/google_containers"]
[plugins."io.containerd.grpc.v1.cri".registry.mirrors."registry.magedu.com"]
endpoint = ["https://registry.magedu.com"]
![图片[3] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/3576fcc65a3c46948fbcb97ab78b1ad4.png)
4.重启查看
root@k8s-master01:~# systemctl daemon-reload
root@k8s-master01:~# systemctl restart containerd
root@k8s-node01:~# containerd -v
containerd containerd.io 1.7.27 05044ec0a9a75232cad458027ca83437aae3f4da
5.3 配置crictl客户端
安装containerd.io时,会自动安装命令行客户端工具crictl,该客户端通常需要通过正确的unix sock文件才能接入到containerd服务。编辑配置文件/etc/crictl.yaml,添加如下内容即可。
root@k8s-master01:~# vim /etc/crictl.yaml
runtime-endpoint: unix:///run/containerd/containerd.sock
image-endpoint: unix:///run/containerd/containerd.sock
timeout: 10
debug: true
![图片[4] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/1814b856343145e5996a2e580b7f6b99.png)
随后即可正常使用crictl程序管理Image、Container和Pod等对象。另外,containerd.io还有另一个名为ctr的客户端程序可以,其功能也更为丰富。
六、 安装kubelet、kubeadm和kubectl
自 v1.28版本开始,Kubernetes官方变更了仓库的存储路径及使用方式(不同的版本将会使用不同的仓库),并提供了向后兼容至v1.24版本。因此,对于v1.24及之后的版本来说,可以使用如下有别于传统配置的方式来安装相关的程序包。以本示例中要安装的v1.30版本为例来说,配置要使用的程序包仓库,需要使用的命令如下。如若需要安装其它版本,则将下面命令中的版本号“v1.30”予以替换即可。
6.1 简单介绍
kubeadm 是自动引导整个集群的工具,本质上 k8s 就是一些容器服务相互配合完成管理集群的任务,如果你知道具体安装哪些容器那么可以不用这个。
kubalet 是各个节点的总管,它上面都管,管理Pod、资源、日志、节点健康状态等等,它不是一个容器,是一个本地软件,所以必须得安装
kubectl 是命令行工具,给我们敲命令与 k8s 交互用的,必须得安装.
6.2 安装
首先得保证源都是新的:
root@k8s-master01:~# apt-get update && apt-get install -y apt-transport-https
![图片[5] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/310a73f0499f44bb82eea0b6cf190739.png)
然后安装一些必要工具
如果 /etc/apt/keyrings 目录不存在,先创建
root@k8s-node02:~# sudo mkdir -p -m 755 /etc/apt/keyrings
root@k8s-master01:~# curl -fsSL https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.30/deb/Release.key | gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg
root@k8s-master01:~# echo "deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.30/deb/ /" | tee /etc/apt/sources.list.d/kubernetes.list
root@k8s-master01:~# apt-get update
接下来,运行如下命令安装kubelet、kubeadm和kubectl等程序包
root@k8s-node02:~# apt-get install -y kubelet kubeadm kubectl
root@k8s-master01:~# sudo apt-mark hold kubelet kubeadm kubectl
kubelet set on hold.
kubeadm set on hold.
kubectl set on hold.
启动 kubelet ,并且设置开机自启:
root@k8s-master01:~# sudo systemctl enable --now kubelet
看看有没有安装成功:
root@k8s-master01:~# kubeadm version
kubeadm version: &version.Info{
Major:"1", Minor:"30", GitVersion:"v1.30.13", GitCommit:"50 af91c466658b6a33d123fae8a487db1630971c", GitTreeState:"clean", BuildDate:"2025-05-15T09:55 :10Z", GoVersion:"go1.23.8", Compiler:"gc", Platform:"linux/amd64"}
七、初始化master节点(在master01上完成如下操作)
7.1、提前拉取镜像(可选)
在运行初始化命令之前先运行如下命令单独获取相关的镜像文件,而后再运行后面的kubeadm init命令,以便于观察到镜像文件的下载过程。
提示:若您选择使用的是docker-ce和cri-dockerd这一容器运行时环境,本文后续内容中使用的kubeadm命令,都需要额外添加“–cri-socket=unix:///var/run/cri-docker.sock”选项,以明确指定其所要关联的容器运行时。这是因为,docker-ce和cri-dockerd都提供了unix sock类型的socket地址,这会导致kubeadm在自动扫描和加载该类文件时无法自动判定要使用哪个文件。而使用containerd.io运行时,则不存在该类问题,因而无须明确指定
root@k8s-master01:~# kubeadm config images list
I0520 19:05:56.469972 49397 version.go:256] remote version is much newer: v1.33.1; falling back to: stable-1.30
registry.k8s.io/kube-apiserver:v1.30.13
registry.k8s.io/kube-controller-manager:v1.30.13
registry.k8s.io/kube-scheduler:v1.30.13
registry.k8s.io/kube-proxy:v1.30.13
registry.k8s.io/coredns/coredns:v1.11.3
registry.k8s.io/pause:3.9
registry.k8s.io/etcd:3.5.15-0
root@k8s-master01:~#
上面的命令会列出类似如下的Image信息,由如下的命令结果可以看出,相关的Image都来自于registry.k8s.io,该服务上的Image通常需要借助于代理服务才能访问到。
若需要从国内的Mirror站点下载Image,还需要在命令上使用“--image-repository”选项来指定Mirror站点的相关URL。例如,下面的命令中使用了该选项将Image Registry指向国内可用的Aliyun的镜像服务,其命令结果显示的各Image也附带了相关的URL。
root@k8s-master01:~# kubeadm config images pull --image-repository=registry.aliyuncs.com/google_containers --kubernetes-version="v1.30.0"
[config/images] Pulled registry.aliyuncs.com/google_containers/kube-apiserver:v1.30.0
[config/images] Pulled registry.aliyuncs.com/google_containers/kube-controller-manager:v1.30.0
[config/images] Pulled registry.aliyuncs.com/google_containers/kube-scheduler:v1.30.0
[config/images] Pulled registry.aliyuncs.com/google_containers/kube-proxy:v1.30.0
[config/images] Pulled registry.aliyuncs.com/google_containers/coredns:v1.11.3
[config/images] Pulled registry.aliyuncs.com/google_containers/pause:3.9
[config/images] Pulled registry.aliyuncs.com/google_containers/etcd:3.5.15-0
7.2 初始化节点
root@k8s-master01:~# kubeadm init
--control-plane-endpoint="kubeapi.joe.com"
--kubernetes-version=v1.30.0
--pod-network-cidr=10.244.0.0/16
--service-cidr=10.96.0.0/12
--cri-socket=unix:///run/containerd/containerd.sock
--image-repository=registry.aliyuncs.com/google_containers
--upload-certs
命令中的各选项简单说明如下:
–image-repository:指定要使用的镜像仓库,默认为registry.k8s.io;
–kubernetes-version:kubernetes程序组件的版本号,它必须要与安装的kubelet程序包的版本号相同;
–control-plane-endpoint:控制平面的固定访问端点,可以是IP地址或DNS名称,会被用于集群管理员及集群组件的kubeconfig配置文件的API Server的访问地址;单控制平面部署时可以不使用该选项;
–pod-network-cidr:Pod网络的地址范围,其值为CIDR格式的网络地址,通常,
Flannel网络插件的默认为10.244.0.0/16,
Project Calico插件的默认值为192.168.0.0/16,
而Cilium的默认值为10.0.0.0/8;
–service-cidr:Service的网络地址范围,其值为CIDR格式的网络地址,kubeadm使用的默认为10.96.0.0/12;通常,仅在使用Flannel一类的网络插件需要手动指定该地址;
–apiserver-advertise-address:apiserver通告给其他组件的IP地址,一般应该为Master节点的用于集群内部通信的IP地址,0.0.0.0表示节点上所有可用地址;
–token-ttl:共享令牌(token)的过期时长,默认为24小时,0表示永不过期;为防止不安全存储等原因导致的令牌泄露危及集群安全,建议为其设定过期时长。未设定该选项时,在token过期后,若期望再向集群中加入其它节点,可以使用如下命令重新创建token,并生成节点加入命令。
上诉报错:

7.3 开启流量转发(7.2报错原因修复)
开这个的原因是让各个主机承担起网络路由的角色,因为后续还要安装网络插件,要有一个路由器各个 Pod 才能互相通信。执行:
root@k8s-master01:~# cat <<EOF | sudo tee /etc/sysctl.d/k8s.conf
net.ipv4.ip_forward = 1
EOF
应用参数:
root@k8s-master01:~# sudo sysctl --system
查看是否开启成功:
root@k8s-master01:~# sysctl net.ipv4.ip_forward
net.ipv4.ip_forward = 1
7.4.初始化完成后的操作步骤
7.4.1 初始化完成后的操作步骤
对于Kubernetes系统的新用户来说,无论使用上述哪种方法,命令运行结束后,请记录最后的kubeadm join命令输出的最后提示的操作步骤。下面的内容是需要用户记录的一个命令输出示例,它提示了后续需要的操作步骤。
# 下面是成功完成第一个控制平面节点初始化的提示信息及后续需要完成的步骤
Your Kubernetes control-plane has initialized successfully!
# 为了完成初始化操作,管理员需要额外手动完成几个必要的步骤
To start using your cluster, you need to run the following as a regular user:
# 第1个步骤提示, Kubernetes集群管理员认证到Kubernetes集群时使用的kubeconfig配置文件
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
# 我们也可以不做上述设定,而使用环境变量KUBECONFIG为kubectl等指定默认使用的
Alternatively, if you are the root user, you can run:
export KUBECONFIG=/etc/kubernetes/admin.conf
# 第2个步骤提示,为Kubernetes集群部署一个网络插件,具体选用的插件则取决于管理员;
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/
# 第3个步骤提示,向集群添加额外的控制平面节点,但本文会略过该步骤,并将在其它文章介绍其实现方式。
You can now join any number of the control-plane node running the following command on each as root:
# 在部署好kubeadm等程序包的其他控制平面节点上以root用户的身份运行类似如下命令,
# 命令中的hash信息对于不同的部署环境来说会各不相同;该步骤只能在其它控制平面节点上执行;
# 提示:与cri-dockerd结合使用docker-ce作为container runtime时,通常需要为下面的命令
# 额外附加“--cri-socket unix:///run/cri-dockerd.sock”选项;
kubeadm join kubeapi.joe.com:6443 --token mbsh3v.5eqsvigid9zcj2xt
--discovery-token-ca-cert-hash sha256:6d1f23a1ef74a8d81309fd8d57b66248bf9f32141071a19649b7b6cec22a6612
--control-plane --certificate-key 7945d35520d330f31912fee2aae762c445700d3e528cb137a8798f30a947a1cd
# 因为在初始化命令“kubeadm init”中使用了“--upload-certs”选项,因而初始化过程会自动上传添加其它Master时用到的数字证书等信息;
# 出于安全考虑,这些内容会在2小时之后自动删除
Please note that the certificate-key gives access to cluster sensitive data, keep it secret!
As a safeguard, uploaded-certs will be deleted in two hours; If necessary, you can use
"kubeadm init phase upload-certs --upload-certs" to reload certs afterward.
# 第4个步骤提示,向集群添加工作节点
Then you can join any number of worker nodes by running the following on each as root:
# 在部署好kubeadm等程序包的各工作节点上以root用户运行类似如下命令;
# 提示:与cri-dockerd结合使用docker-ce作为container runtime时,通常需要为下面的命令
# 额外附加“--cri-socket unix:///run/cri-dockerd.sock”选项;
kubeadm join kubeapi.joe.com:6443 --token mbsh3v.5eqsvigid9zcj2xt
--discovery-token-ca-cert-hash sha256:6d1f23a1ef74a8d81309fd8d57b66248bf9f32141071a19649b7b6cec22a6612
另外,kubeadm init命令完整参考指南请移步官方文档,地址为https://kubernetes.io/docs/reference/setup-tools/kubeadm/kubeadm-init/。
7.4.2 设定kubectl
kubectl是kube-apiserver的命令行客户端程序,实现了除系统部署之外的几乎全部的管理操作,是kubernetes管理员使用最多的命令之一。kubectl需经由API server认证及授权后方能执行相应的管理操作,kubeadm部署的集群为其生成了一个具有管理员权限的认证配置文件/etc/kubernetes/admin.conf,它可由kubectl通过默认的“$HOME/.kube/config”的路径进行加载。当然,用户也可在kubectl命令上使用–kubeconfig选项指定一个别的位置。
下面复制认证为Kubernetes系统管理员的配置文件至目标用户(例如当前用户root)的家目录下:
root@k8s-master01:~# mkdir ~/.kube
root@k8s-master01:~# cp /etc/kubernetes/admin.conf ~/.kube/config
7.4.3 安装网络插件 flannel
Kubernetes系统上Pod网络的实现依赖于第三方插件进行,这类插件有近数十种之多,较为著名的有flannel、calico、canal和kube-router等,简单易用的实现是为CoreOS提供的flannel项目。下面的命令用于在线部署flannel至Kubernetes系统之上,我们需要在初始化的第一个master节点k8s-master01上运行如下命令,以完成部署。
root@k8s-master01:~# kubectl apply -f https://raw.githubusercontent.com/flannel-io/flannel/v0.22.0/Documentation/kube-flannel.yml
而后使用如下命令确认其输出结果中Pod的状态为“Running”,类似如下命令及其输入的结果所示:
kubectl get pods -n kube-flannel
上述命令应该会得到类似如下输出,这表示kube-flannel已然正常运行。

7.5 验证master节点已经就绪
root@k8s-master01:~# kubectl get nodes
NAME STATUS ROLES AGE VERSION
k8s-master01 NotReady control-plane 106s v1.30.13
7.6 添加节点到集群中
下面的两个步骤,需要分别在k8s-node01、k8s-node02和k8s-node03上各自完成。
1、若未禁用Swap设备,编辑kubelet的配置文件/etc/default/kubelet,设置其忽略Swap启用的状态错误,内容如下: KUBELET_EXTRA_ARGS=“–fail-swap-on=false”
2、将节点加入第二步中创建的master的集群中,要使用主节点初始化过程中记录的kubeadm join命令。再次提示,若使用docker-ce和cri-dockerd运行时环境,则需要在如下命令中额外添加“–cri-socket=unix:///var/run/cri-dockerd.sock”选项。
root@k8s-node01:~# kubeadm join kubeapi.joe.com:6443 --token ndtnld.82ln4g5jruv20mff
--discovery-token-ca-cert-hash sha256:a7ae8bfad46d28d05ace9e14daf412590a01ac689b55880fc43e27b0b51412f3
![图片[6] - 【云原生】-【1】部署Kubernetes集群(v1.30) - 宋马](https://pic.songma.com/blogimg/20250525/c824e6131cbd468682c52c2bdcc5cd97.png)
提示:在未禁用Swap设备的情况下,还需要为上面的命令额外附加“–ignore-preflight-errors=Swap”选项。
7.7 验证节点添加结果
root@k8s-master01:~# kubectl get nodes
NAME STATUS ROLES AGE VERSION
k8s-master01 Ready control-plane 2m15s v1.30.13
k8s-node01 Ready <none> 15s v1.30.13
k8s-node02 Ready <none> 12s v1.30.13
k8s-node03 Ready <none> 8s v1.30.13
到此为止,一个master,并附带有三个worker的kubernetes集群基础设施已经部署完成,用户随后即可测试其核心功能。例如,下面的命令可将demoapp以Pod的形式编排运行于集群之上,并通过在集群外部进行访问:


















暂无评论内容