一、系统架构
本系统部署在三台服务器上,系统为Rocky10
| IP地址 | 服务器名 | Swap | Firewalld |
|---|
| 192.168.2.101 | k8s-master | 关闭 | 关闭 |
| 192.168.2.102 | k8s-slave1 | 关闭 | 关闭 |
| 192.168.2.103 | k8s-slave2 | 关闭 | 关闭 |
在三台服务器上的/etc/hosts写入如下内容
1
2
3
| 192.168.2.101 k8s-master
192.168.2.102 k8s-slave1
192.168.2.103 k8s-slave2
|
还有一个harbor服务器,IP为:192.168.2.104,启动的80端口。
执行命令,开启网络支持
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| # 开启内核转发和网桥过滤
cat <<EOF | sudo tee /etc/modules-load.d/k8s.conf
overlay
br_netfilter
EOF
sudo modprobe overlay
sudo modprobe br_netfilter
cat <<EOF | sudo tee /etc/sysctl.d/k8s.conf
net.bridge.bridge-nf-call-iptables = 1
net.bridge.bridge-nf-call-ip6tables = 1
net.ipv4.ip_forward = 1
EOF
sudo sysctl --system
|
二、安装containerd
在三台服务器上执行
2.1、安装
使用下列命令进行安装
1
2
3
4
5
6
| # 1. 安装流量转发工具
sudo dnf install -y yum-utils
# 2. 添加阿里云源
sudo yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# 3. 安装最新版 containerd
sudo dnf install -y containerd.io
|
2.2、进行配置
创建配置文件并进行修改
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
| # 1. 创建配置目录并生成默认配置
sudo mkdir -p /etc/containerd
containerd config default | sudo tee /etc/containerd/config.toml
# 2. 启用 SystemdCgroup (K8s 官方推荐,增强稳定性)
sudo sed -i 's/SystemdCgroup = false/SystemdCgroup = true/g' /etc/containerd/config.toml
# 3. 修改 Sandbox 镜像地址为阿里云,版本指定为 3.10.1
# 注意:国内镜像站同步 registry.k8s.io 较慢,建议使用以下镜像路径
sudo sed -i 's|registry.k8s.io/pause:3.10.1|registry.cn-hangzhou.aliyuncs.com/google_containers/pause:3.10.1|g' /etc/containerd/config.toml
#4、配置信任192.168.2.104
sudo sed -i "s|config_path = \"\"|config_path = \"/etc/containerd/certs.d\"|g" /etc/containerd/config.toml
#如果这里配置不成功,请手工修改,保证内容如下
#[plugins.'io.containerd.cri.v1.images'.registry]
# config_path = '/etc/containerd/certs.d'
#5、创建其他的文件
#为了连接上harbor执行下列配置
echo -n "admin:Harbor12345" | base64
# 将输出的内容写入/etc/containerd/certs.d/192.168.2.104/hosts.toml
mkdir -p /etc/containerd/certs.d/192.168.2.104
touch /etc/containerd/certs.d/192.168.2.104/hosts.toml
#在下列文件中写入
# 1. 创建配置目录(如果不存在)
sudo mkdir -p /etc/containerd/certs.d/192.168.2.104
# 2. 使用带有引号的 EOF 写入,防止特殊字符被 Shell 误解析
sudo tee /etc/containerd/certs.d/192.168.2.104/hosts.toml <<'EOF'
server = "http://192.168.2.104"
[host."http://192.168.2.104"]
capabilities = ["pull", "resolve"]
skip_verify = true
[host."http://192.168.2.104".header]
Authorization = "Basic YWRtaW46SGFyYm9yMTIzNDU="
EOF
#配置cri,让命令正常
cat <<EOF > /etc/crictl.yaml
runtime-endpoint: unix:///run/containerd/containerd.sock
image-endpoint: unix:///run/containerd/containerd.sock
timeout: 10
debug: false
EOF
|
2.3、启动服务
1
2
3
4
| sudo systemctl restart containerd
sudo systemctl enable containerd
# 检查 containerd 是否因为配置错误而无法启动
sudo systemctl status containerd
|
三、安装 Kubeadm, Kubelet, Kubectl
在所有节点执行
1
2
3
4
5
6
7
8
9
10
11
| cat <<EOF | sudo tee /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.35/rpm/
enabled=1
gpgcheck=1
gpgkey=https://mirrors.aliyun.com/kubernetes-new/core/stable/v1.35/rpm/repodata/repomd.xml.key
EOF
dnf install -y kubelet kubeadm kubectl
systemctl enable --now kubelet
|
四、集群初始化
4.1、启动集群
在master执行
1
2
3
4
5
6
7
8
9
10
11
12
| kubeadm init \
--apiserver-advertise-address=192.168.2.101 \
--image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers \
--kubernetes-version=v1.35.2 \
--service-cidr=10.96.0.0/12 \
--pod-network-cidr=10.244.0.0/16
#在执行如下命令
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
#退出武器,再进入
|
如果正常,在输出的最后将出现,如下的提示,将该提示在另外两个节点执行
1
2
| kubeadm join 192.168.2.101:6443 --token rghxkw.d2wlhlrjgeqye2t6 \
--discovery-token-ca-cert-hash sha256:1e8e065bcf816fb681bc351ec47489619794cc339bb5ccb8259268c46128deea
|
如果该命令遗忘,在master执行下列命令重新获取
1
| `kubeadm token create --print-join-command`
|
现在使用kubectl get nodes查看系统状态,都应该是notready状态,需要安装网络组件
4.2、安装网络组件
因为网络问题,需要提前在harbor服务器上下载网络组件,并推送到私有仓库
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| # 定义变量
HARBOR="192.168.2.104/library"
# 1. 下载并推送 Calico
images=(cni node kube-controllers)
for img in "${images[@]}"; do
docker pull calico/$img:v3.27.0
docker tag calico/$img:v3.27.0 $HARBOR/calico-$img:v3.27.0
docker push $HARBOR/calico-$img:v3.27.0
done
# 2. 下载并推送 Ingress
docker pull registry.k8s.io/ingress-nginx/controller:v1.9.5
docker tag registry.k8s.io/ingress-nginx/controller:v1.9.5 $HARBOR/ingress-controller:v1.9.5
docker push $HARBOR/ingress-controller:v1.9.5
|
harbor上取得镜像之后,在master上执行
1
2
3
4
5
6
7
8
| curl -O https://raw.githubusercontent.com/projectcalico/calico/v3.27.0/manifests/calico.yaml
#将默认的镜像地址修改到192.168.2.104
sed -i 's|docker.io/calico/|192.168.2.104/library/calico-|g' calico.yaml
#启动网络组件
kubectl apply -f calico.yaml
#使用命令查看node状态,如果全部是ready即可
kubectl get nodes
#返回如下即可
|
| Name | STATUS | ROLES | AGE | VERSION |
|---|
| k8s-master | Ready | control-plane | 84m | v1.35.3 |
| k8s-slave1 | Ready | | 81m | v1.35.3 |
| k8s-slave2 | Ready | | 81m | v1.35.3 |
五、部署ingress-nginx
5.1、下载镜像
1
2
3
4
5
6
7
8
9
10
| # 1. 定义变量(方便后续操作)
ORIGIN_IMAGE="registry.cn-hangzhou.aliyuncs.com/google_containers/kube-webhook-certgen:v20231011-8b53cabe0"
MY_HARBOR="192.168.2.104/library/kube-webhook-certgen:v20231011"
# 2. 拉取镜像(这里推荐用阿里源作为中转,比 registry.k8s.io 稳得多)
docker pull $ORIGIN_IMAGE
# 3. 打标签并推送到你的 Harbor
docker tag $ORIGIN_IMAGE $MY_HARBOR
docker push $MY_HARBOR
|
5.2、下载部署文件
1
2
3
4
5
6
7
8
9
10
| # 下载部署文件
curl -O https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.9.5/deploy/static/provider/cloud/deploy.yaml
#替换成本地image
sed -i 's|registry.k8s.io/ingress-nginx/controller:v1.9.5|192.168.2.104/library/ingress-controller:v1.9.5|g' deploy.yaml
# 替换刚才报错的 Webhook Certgen (注意去掉那个长长的 sha256 摘要,直接用 tag)
sed -i 's|registry.k8s.io/ingress-nginx/kube-webhook-certgen:.*$|192.168.2.104/library/kube-webhook-certgen:v20231011|g' deploy.yaml
# 针对已经下载好的 deploy.yaml
sed -i 's/@sha256:[a-f0-9]*//g' deploy.yaml
# 验证,显示没有各种奇奇怪怪的sha256就行
grep "image:" deploy.yaml
|
5.3、启动
1
2
3
| kubectl apply -f deploy.yaml
#检查,只要里面的pod运行起来就行
kubectl get pods -n ingress-nginx
|
六、自动更新证书
创建一个脚本,用来自动更新证书
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
| cat > /usr/local/bin/k8s-cert-renew.sh << 'EOF'
#!/bin/bash
# ==============================================================================
# 脚本名称: k8s-cert-renew.sh
# 脚本说明: 每月自动续期 Kubernetes (kubeadm) 证书
# ==============================================================================
set -e
# 日志输出函数
log() {
echo "$(date '+%Y-%m-%d %H:%M:%S') - $1"
}
log "开始执行 K8s 证书自动续期流程..."
# 1. 备份现有证书和配置 (保留最近30天的备份)
BACKUP_DIR="/etc/kubernetes/pki.backup.$(date +%Y%m%d)"
log "备份当前证书到 $BACKUP_DIR"
cp -r /etc/kubernetes/pki $BACKUP_DIR
\cp -f /etc/kubernetes/admin.conf /etc/kubernetes/admin.conf.backup.$(date +%Y%m%d)
# 清理超过30天的旧备份
find /etc/kubernetes/ -maxdepth 1 -name "pki.backup.*" -type d -mtime +30 -exec rm -rf {} \;
find /etc/kubernetes/ -maxdepth 1 -name "admin.conf.backup.*" -type f -mtime +30 -exec rm -f {} \;
# 2. 使用 kubeadm 续期所有证书
log "执行 kubeadm certs renew all..."
kubeadm certs renew all
# 3. 更新管理员的 kubeconfig 文件 (使用 \cp -f 绕过 alias 并强制覆盖)
log "更新 ~/.kube/config 配置文件..."
\cp -f /etc/kubernetes/admin.conf ~/.kube/config
chown $(id -u):$(id -g) ~/.kube/config
# 4. 重启控制平面组件以加载新证书
log "重启控制平面静态 Pod..."
export KUBECONFIG=/etc/kubernetes/admin.conf
kubectl delete pod -n kube-system -l component=kube-apiserver
kubectl delete pod -n kube-system -l component=kube-controller-manager
kubectl delete pod -n kube-system -l component=kube-scheduler
kubectl delete pod -n kube-system -l component=etcd
log "检查新证书有效期:"
kubeadm certs check-expiration | grep -E "CERTIFICATE|admin.conf"
log "K8s 证书续期流程执行完毕!"
EOF
|
对脚本添加可执行权限,并添加到计划任务
1
2
3
4
| chmod +x /usr/local/bin/k8s-cert-renew.sh
crontab -e
#写入如下内容
0 1 1 * * /bin/bash /usr/local/bin/k8s-cert-renew.sh
|