Stories

Detail Return Return

使用kubeadm部署高可用IPV4/IPV6集羣---V1.32 - Stories Detail

使用kubeadm部署高可用IPV4/IPV6集羣

https://github.com/cby-chen/Kubernetes 開源不易,幫忙點個star,謝謝了

k8s基礎系統環境配置

配置IP

# 注意!
# 若虛擬機是進行克隆的那麼網卡的UUID和MachineID會重複
# 需要重新生成新的UUIDUUID和MachineID
# UUID和MachineID重複無法DHCP獲取到IPV6地址
ssh root@192.168.1.189 "rm -rf /etc/machine-id; systemd-machine-id-setup;reboot"
ssh root@192.168.1.190 "rm -rf /etc/machine-id; systemd-machine-id-setup;reboot"
ssh root@192.168.1.191 "rm -rf /etc/machine-id; systemd-machine-id-setup;reboot"
ssh root@192.168.1.192 "rm -rf /etc/machine-id; systemd-machine-id-setup;reboot"
ssh root@192.168.1.193 "rm -rf /etc/machine-id; systemd-machine-id-setup;reboot"
# 
# 查看當前的網卡列表和 UUID:
# nmcli con show
# 刪除要更改 UUID 的網絡連接:
# nmcli con delete uuid <原 UUID>
# 重新生成 UUID:
# nmcli con add type ethernet ifname <接口名稱> con-name <新名稱>
# 重新啓用網絡連接:
# nmcli con up <新名稱>

# 更改網卡的UUID
# 先配置靜態IP之後使用ssh方式配置不斷連
ssh root@192.168.1.189 "nmcli con delete uuid d1141403-18c6-3149-907c-ed5f09663a7f;nmcli con add type ethernet ifname ens160 con-name ens160;nmcli con up ens160"
ssh root@192.168.1.190 "nmcli con delete uuid d1141403-18c6-3149-907c-ed5f09663a7f;nmcli con add type ethernet ifname ens160 con-name ens160;nmcli con up ens160"
ssh root@192.168.1.191 "nmcli con delete uuid d1141403-18c6-3149-907c-ed5f09663a7f;nmcli con add type ethernet ifname ens160 con-name ens160;nmcli con up ens160"
ssh root@192.168.1.192 "nmcli con delete uuid d1141403-18c6-3149-907c-ed5f09663a7f;nmcli con add type ethernet ifname ens160 con-name ens160;nmcli con up ens160"
ssh root@192.168.1.193 "nmcli con delete uuid d1141403-18c6-3149-907c-ed5f09663a7f;nmcli con add type ethernet ifname ens160 con-name ens160;nmcli con up ens160"

# 參數解釋
# 
# ssh ssh root@192.168.1.21
# 使用SSH登錄到IP為192.168.1.21的主機,使用root用户身份。
# 
# nmcli con delete uuid 708a1497-2192-43a5-9f03-2ab936fb3c44
# 刪除 UUID 為 708a1497-2192-43a5-9f03-2ab936fb3c44 的網絡連接,這是 NetworkManager 中一種特定網絡配置的唯一標識符。
# 
# nmcli con add type ethernet ifname ens160 con-name ens160
# 添加一種以太網連接類型,並指定接口名為 ens160,連接名稱也為 ens160。
# 
# nmcli con up ens160
# 開啓 ens160 這個網絡連接。
# 
# 簡單來説,這個命令的作用是刪除一個特定的網絡連接配置,並添加一個名為 ens160 的以太網連接,然後啓用這個新的連接。

# 修改靜態的IPv4地址
ssh root@192.168.1.189 "nmcli con mod ens160 ipv4.addresses 192.168.1.21/24; nmcli con mod ens160 ipv4.gateway  192.168.1.1; nmcli con mod ens160 ipv4.method manual; nmcli con mod ens160 ipv4.dns "8.8.8.8"; nmcli con up ens160"
ssh root@192.168.1.190 "nmcli con mod ens160 ipv4.addresses 192.168.1.22/24; nmcli con mod ens160 ipv4.gateway  192.168.1.1; nmcli con mod ens160 ipv4.method manual; nmcli con mod ens160 ipv4.dns "8.8.8.8"; nmcli con up ens160"
ssh root@192.168.1.191 "nmcli con mod ens160 ipv4.addresses 192.168.1.23/24; nmcli con mod ens160 ipv4.gateway  192.168.1.1; nmcli con mod ens160 ipv4.method manual; nmcli con mod ens160 ipv4.dns "8.8.8.8"; nmcli con up ens160"
ssh root@192.168.1.192 "nmcli con mod ens160 ipv4.addresses 192.168.1.24/24; nmcli con mod ens160 ipv4.gateway  192.168.1.1; nmcli con mod ens160 ipv4.method manual; nmcli con mod ens160 ipv4.dns "8.8.8.8"; nmcli con up ens160"
ssh root@192.168.1.193 "nmcli con mod ens160 ipv4.addresses 192.168.1.25/24; nmcli con mod ens160 ipv4.gateway  192.168.1.1; nmcli con mod ens160 ipv4.method manual; nmcli con mod ens160 ipv4.dns "8.8.8.8"; nmcli con up ens160"


# 參數解釋
# 
# ssh root@192.168.1.189
# 使用SSH登錄到IP為192.168.1.189的主機,使用root用户身份。
# 
# "nmcli con mod ens160 ipv4.addresses 192.168.1.21/24"
# 修改ens160網絡連接的IPv4地址為192.168.1.21,子網掩碼為 24。
# 
# "nmcli con mod ens160 ipv4.gateway 192.168.1.1"
# 修改ens160網絡連接的IPv4網關為192.168.1.1。
# 
# "nmcli con mod ens160 ipv4.method manual"
# 將ens160網絡連接的IPv4配置方法設置為手動。
# 
# "nmcli con mod ens160 ipv4.dns "8.8.8.8"
# 將ens160網絡連接的IPv4 DNS服務器設置為 8.8.8.8。
# 
# "nmcli con up ens160"
# 啓動ens160網絡連接。
# 
# 總體來説,這條命令是通過SSH遠程登錄到指定的主機,並使用網絡管理命令 (nmcli) 修改ens160網絡連接的配置,包括IP地址、網關、配置方法和DNS服務器,並啓動該網絡連接。

# 我這裏有公網的IPv6的地址,但是是DHCP動態的,無法固定,使用不方便
# 所以我配置了內網的IPv6地址,可以實現固定的訪問地址

# 我使用的方式。只配置IPv6地址不配置網關DNS
ssh root@192.168.1.21 "nmcli con mod ens160 ipv6.addresses fc00::21/8; nmcli con up ens160"
ssh root@192.168.1.22 "nmcli con mod ens160 ipv6.addresses fc00::22/8; nmcli con up ens160"
ssh root@192.168.1.23 "nmcli con mod ens160 ipv6.addresses fc00::23/8; nmcli con up ens160"
ssh root@192.168.1.24 "nmcli con mod ens160 ipv6.addresses fc00::24/8; nmcli con up ens160"
ssh root@192.168.1.25 "nmcli con mod ens160 ipv6.addresses fc00::25/8; nmcli con up ens160"

# IPv6地址路由DNS,樣例
ssh root@192.168.1.21 "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::10; nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1; nmcli con mod ens160 ipv6.method manual; nmcli con mod ens160 ipv6.dns "2400:3200::1"; nmcli con up ens160"
ssh root@192.168.1.22 "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::20; nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1; nmcli con mod ens160 ipv6.method manual; nmcli con mod ens160 ipv6.dns "2400:3200::1"; nmcli con up ens160"
ssh root@192.168.1.23 "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::30; nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1; nmcli con mod ens160 ipv6.method manual; nmcli con mod ens160 ipv6.dns "2400:3200::1"; nmcli con up ens160"
ssh root@192.168.1.24 "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::40; nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1; nmcli con mod ens160 ipv6.method manual; nmcli con mod ens160 ipv6.dns "2400:3200::1"; nmcli con up ens160"
ssh root@192.168.1.25 "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::50; nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1; nmcli con mod ens160 ipv6.method manual; nmcli con mod ens160 ipv6.dns "2400:3200::1"; nmcli con up ens160"

# 參數解釋
# 
# ssh root@192.168.1.21
# 通過SSH連接到IP地址為192.168.1.21的遠程主機,使用root用户進行登錄。
# 
# "nmcli con mod ens160 ipv6.addresses fc00:43f4:1eea:1::10"
# 使用nmcli命令修改ens160接口的IPv6地址為fc00:43f4:1eea:1::10。
# 
# "nmcli con mod ens160 ipv6.gateway fc00:43f4:1eea:1::1"
# 使用nmcli命令修改ens160接口的IPv6網關為fc00:43f4:1eea:1::1。
# 
# "nmcli con mod ens160 ipv6.method manual"
# 使用nmcli命令將ens160接口的IPv6配置方法修改為手動配置。
# 
# "nmcli con mod ens160 ipv6.dns "2400:3200::1"
# 使用nmcli命令設置ens160接口的IPv6 DNS服務器為2400:3200::1。
# 
# "nmcli con up ens160"
# 使用nmcli命令啓動ens160接口。
# 
# 這個命令的目的是在遠程主機上配置ens160接口的IPv6地址、網關、配置方法和DNS服務器,並啓動ens160接口。

# 查看網卡配置
# nmcli device show ens160
# nmcli con show ens160
[root@localhost ~]#  cat /etc/NetworkManager/system-connections/ens160.nmconnection 
[connection]
id=ens160
uuid=d199c6e0-4212-4bf8-9a7b-a2da247ca759
type=ethernet
interface-name=ens160
timestamp=1742703386

[ethernet]

[ipv4]
address1=192.168.1.21/24,192.168.1.1
dns=192.168.1.99;
method=manual

[ipv6]
addr-gen-mode=default
address1=fc00::21/8
method=auto

[proxy]

設置主機名

hostnamectl set-hostname k8s-master01
hostnamectl set-hostname k8s-master02
hostnamectl set-hostname k8s-master03
hostnamectl set-hostname k8s-node01
hostnamectl set-hostname k8s-node02

配置yum源

# 其他系統的源地址
# https://help.mirrors.cernet.edu.cn/

# 對於私有倉庫
sed -e 's|^mirrorlist=|#mirrorlist=|g' -e 's|^#baseurl=http://mirror.centos.org/\$contentdir|baseurl=http://192.168.1.123/centos|g' -i.bak  /etc/yum.repos.d/CentOS-*.repo

# 對於 Ubuntu
sed -i 's/cn.archive.ubuntu.com/mirrors.ustc.edu.cn/g' /etc/apt/sources.list

# epel擴展源
sudo yum install -y epel-release
sudo sed -e 's!^metalink=!#metalink=!g' \
    -e 's!^#baseurl=!baseurl=!g' \
    -e 's!https\?://download\.fedoraproject\.org/pub/epel!https://mirror.nju.edu.cn/epel!g' \
    -e 's!https\?://download\.example/pub/epel!https://mirror.nju.edu.cn/epel!g' \
    -i /etc/yum.repos.d/epel{,-testing}.repo

# 對於 CentOS 7
sudo sed -e 's|^mirrorlist=|#mirrorlist=|g' \
         -e 's|^#baseurl=http://mirror.centos.org/centos|baseurl=https://mirror.nju.edu.cn/centos|g' \
         -i.bak \
         /etc/yum.repos.d/CentOS-*.repo

# 對於 CentOS 8
sudo sed -e 's|^mirrorlist=|#mirrorlist=|g' \
         -e 's|^#baseurl=http://mirror.centos.org/$contentdir|baseurl=https://mirror.nju.edu.cn/centos|g' \
         -i.bak \
         /etc/yum.repos.d/CentOS-*.repo

# 對於CentOS 9
cat <<'EOF' > /etc/yum.repos.d/centos.repo
[baseos]
name=CentOS Stream $releasever - BaseOS
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/BaseOS/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-baseos-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=1

[baseos-debuginfo]
name=CentOS Stream $releasever - BaseOS - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/BaseOS/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-baseos-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[baseos-source]
name=CentOS Stream $releasever - BaseOS - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/BaseOS/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-baseos-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[appstream]
name=CentOS Stream $releasever - AppStream
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/AppStream/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-appstream-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=1

[appstream-debuginfo]
name=CentOS Stream $releasever - AppStream - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/AppStream/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-appstream-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[appstream-source]
name=CentOS Stream $releasever - AppStream - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/AppStream/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-appstream-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[crb]
name=CentOS Stream $releasever - CRB
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/CRB/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-crb-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=1

[crb-debuginfo]
name=CentOS Stream $releasever - CRB - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/CRB/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-crb-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[crb-source]
name=CentOS Stream $releasever - CRB - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/CRB/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-crb-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0
EOF

cat <<'EOF' > /etc/yum.repos.d/centos-addons.repo
[highavailability]
name=CentOS Stream $releasever - HighAvailability
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/HighAvailability/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-highavailability-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=0

[highavailability-debuginfo]
name=CentOS Stream $releasever - HighAvailability - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/HighAvailability/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-highavailability-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[highavailability-source]
name=CentOS Stream $releasever - HighAvailability - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/HighAvailability/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-highavailability-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[nfv]
name=CentOS Stream $releasever - NFV
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/NFV/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-nfv-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=0

[nfv-debuginfo]
name=CentOS Stream $releasever - NFV - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/NFV/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-nfv-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[nfv-source]
name=CentOS Stream $releasever - NFV - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/NFV/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-nfv-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[rt]
name=CentOS Stream $releasever - RT
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/RT/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-rt-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=0

[rt-debuginfo]
name=CentOS Stream $releasever - RT - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/RT/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-rt-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[rt-source]
name=CentOS Stream $releasever - RT - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/RT/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-rt-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[resilientstorage]
name=CentOS Stream $releasever - ResilientStorage
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/ResilientStorage/$basearch/os
# metalink=https://mirrors.centos.org/metalink?repo=centos-resilientstorage-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=0

[resilientstorage-debuginfo]
name=CentOS Stream $releasever - ResilientStorage - Debug
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/ResilientStorage/$basearch/debug/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-resilientstorage-debug-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[resilientstorage-source]
name=CentOS Stream $releasever - ResilientStorage - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/$releasever-stream/ResilientStorage/source/tree/
# metalink=https://mirrors.centos.org/metalink?repo=centos-resilientstorage-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-centosofficial
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0

[extras-common]
name=CentOS Stream $releasever - Extras packages
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/SIGs/$releasever-stream/extras/$basearch/extras-common
# metalink=https://mirrors.centos.org/metalink?repo=centos-extras-sig-extras-common-$stream&arch=$basearch&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-SIG-Extras-SHA512
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
countme=1
enabled=1

[extras-common-source]
name=CentOS Stream $releasever - Extras packages - Source
baseurl=https://mirrors.tuna.tsinghua.edu.cn/centos-stream/SIGs/$releasever-stream/extras/source/extras-common
# metalink=https://mirrors.centos.org/metalink?repo=centos-extras-sig-extras-common-source-$stream&arch=source&protocol=https,http
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-CentOS-SIG-Extras-SHA512
gpgcheck=1
repo_gpgcheck=0
metadata_expire=6h
enabled=0
EOF

安裝一些必備工具

# 對於 Ubuntu
apt update && apt upgrade -y && apt install -y wget psmisc vim net-tools nfs-kernel-server telnet lvm2 git tar curl

# 對於 CentOS 7
yum update -y && yum -y install  wget psmisc vim net-tools nfs-utils telnet yum-utils device-mapper-persistent-data lvm2 git tar curl

# 對於 CentOS 8
yum update -y && yum -y install wget psmisc vim net-tools nfs-utils telnet yum-utils device-mapper-persistent-data lvm2 git network-scripts tar curl

# 對於 CentOS 9
yum update -y && yum -y install wget psmisc vim net-tools nfs-utils telnet yum-utils device-mapper-persistent-data lvm2 git tar curl

關閉防火牆

# Ubuntu忽略,CentOS執行
systemctl disable --now firewalld

關閉SELinux

# Ubuntu忽略,CentOS執行
setenforce 0
sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/selinux/config

關閉交換分區

sed -ri 's/.*swap.*/#&/' /etc/fstab
swapoff -a && sysctl -w vm.swappiness=0

cat /etc/fstab
# /dev/mapper/centos-swap swap                    swap    defaults        0 0

網絡配置(倆種方式二選一)

# Ubuntu忽略,CentOS執行,CentOS9不支持方式一

# 方式一
# systemctl disable --now NetworkManager
# systemctl start network && systemctl enable network

# 方式二
cat > /etc/NetworkManager/conf.d/calico.conf << EOF 
[keyfile]
unmanaged-devices=interface-name:cali*;interface-name:tunl*
EOF
systemctl restart NetworkManager

# 參數解釋
#
# 這個參數用於指定不由 NetworkManager 管理的設備。它由以下兩個部分組成
# 
# interface-name:cali*
# 表示以 "cali" 開頭的接口名稱被排除在 NetworkManager 管理之外。例如,"cali0", "cali1" 等接口不受 NetworkManager 管理。
# 
# interface-name:tunl*
# 表示以 "tunl" 開頭的接口名稱被排除在 NetworkManager 管理之外。例如,"tunl0", "tunl1" 等接口不受 NetworkManager 管理。
# 
# 通過使用這個參數,可以將特定的接口排除在 NetworkManager 的管理範圍之外,以便其他工具或進程可以獨立地管理和配置這些接口。

進行時間同步

# 服務端
# apt install chrony -y
yum install chrony -y
cat > /etc/chrony.conf << EOF 
pool ntp.aliyun.com iburst
driftfile /var/lib/chrony/drift
makestep 1.0 3
rtcsync
allow 192.168.1.0/24
local stratum 10
keyfile /etc/chrony.keys
leapsectz right/UTC
logdir /var/log/chrony
EOF

systemctl restart chronyd ; systemctl enable chronyd

# 客户端
# apt install chrony -y
yum install chrony -y
cat > /etc/chrony.conf << EOF 
pool 192.168.1.21 iburst
driftfile /var/lib/chrony/drift
makestep 1.0 3
rtcsync
keyfile /etc/chrony.keys
leapsectz right/UTC
logdir /var/log/chrony
EOF

systemctl restart chronyd ; systemctl enable chronyd

#使用客户端進行驗證
chronyc sources -v

# 參數解釋
#
# pool ntp.aliyun.com iburst
# 指定使用ntp.aliyun.com作為時間服務器池,iburst選項表示在初始同步時會發送多個請求以加快同步速度。
# 
# driftfile /var/lib/chrony/drift
# 指定用於保存時鐘漂移信息的文件路徑。
# 
# makestep 1.0 3
# 設置當系統時間與服務器時間偏差大於1秒時,會以1秒的步長進行調整。如果偏差超過3秒,則立即進行時間調整。
# 
# rtcsync
# 啓用硬件時鐘同步功能,可以提高時鐘的準確性。
# 
# allow 192.168.0.0/24
# 允許192.168.0.0/24網段範圍內的主機與chrony進行時間同步。
# 
# local stratum 10
# 將本地時鐘設為stratum 10,stratum值表示時鐘的準確度,值越小表示準確度越高。
# 
# keyfile /etc/chrony.keys
# 指定使用的密鑰文件路徑,用於對時間同步進行身份驗證。
# 
# leapsectz right/UTC
# 指定時區為UTC。
# 
# logdir /var/log/chrony
# 指定日誌文件存放目錄。

配置ulimit

ulimit -SHn 65535
cat >> /etc/security/limits.conf <<EOF
* soft nofile 655360
* hard nofile 131072
* soft nproc 655350
* hard nproc 655350
* seft memlock unlimited
* hard memlock unlimitedd
EOF

# 參數解釋
#
# soft nofile 655360
# soft表示軟限制,nofile表示一個進程可打開的最大文件數,默認值為1024。這裏的軟限制設置為655360,即一個進程可打開的最大文件數為655360。
#
# hard nofile 131072
# hard表示硬限制,即系統設置的最大值。nofile表示一個進程可打開的最大文件數,默認值為4096。這裏的硬限制設置為131072,即系統設置的最大文件數為131072。
#
# soft nproc 655350
# soft表示軟限制,nproc表示一個用户可創建的最大進程數,默認值為30720。這裏的軟限制設置為655350,即一個用户可創建的最大進程數為655350。
#
# hard nproc 655350
# hard表示硬限制,即系統設置的最大值。nproc表示一個用户可創建的最大進程數,默認值為4096。這裏的硬限制設置為655350,即系統設置的最大進程數為655350。
#
# seft memlock unlimited
# seft表示軟限制,memlock表示一個進程可鎖定在RAM中的最大內存,默認值為64 KB。這裏的軟限制設置為unlimited,即一個進程可鎖定的最大內存為無限制。
#
# hard memlock unlimited
# hard表示硬限制,即系統設置的最大值。memlock表示一個進程可鎖定在RAM中的最大內存,默認值為64 KB。這裏的硬限制設置為unlimited,即系統設置的最大內存鎖定為無限制。

配置免密登錄

# apt install -y sshpass
yum install -y sshpass
ssh-keygen -f /root/.ssh/id_rsa -P ''
export IP="192.168.1.21 192.168.1.22 192.168.1.23 192.168.1.24 192.168.1.25"
export SSHPASS=123123
for HOST in $IP;do
     sshpass -e ssh-copy-id -o StrictHostKeyChecking=no $HOST
done

# 這段腳本的作用是在一台機器上安裝sshpass工具,並通過sshpass自動將本機的SSH公鑰複製到多個遠程主機上,以實現無需手動輸入密碼的SSH登錄。
# 
# 具體解釋如下:
# 
# 1. `apt install -y sshpass` 或 `yum install -y sshpass`:通過包管理器(apt或yum)安裝sshpass工具,使得後續可以使用sshpass命令。
# 
# 2. `ssh-keygen -f /root/.ssh/id_rsa -P ''`:生成SSH密鑰對。該命令會在/root/.ssh目錄下生成私鑰文件id_rsa和公鑰文件id_rsa.pub,同時不設置密碼(即-P參數後面為空),方便後續通過ssh-copy-id命令自動複製公鑰。
# 
# 3. `export IP="192.168.1.21 192.168.1.22 192.168.1.23 192.168.1.24 192.168.1.25"`:設置一個包含多個遠程主機IP地址的環境變量IP,用空格分隔開,表示要將SSH公鑰複製到這些遠程主機上。
# 
# 4. `export SSHPASS=123123`:設置環境變量SSHPASS,將sshpass所需的SSH密碼(在這裏是"123123")賦值給它,這樣sshpass命令可以自動使用這個密碼進行登錄。
# 
# 5. `for HOST in $IP;do`:遍歷環境變量IP中的每個IP地址,並將當前IP地址賦值給變量HOST。
# 
# 6. `sshpass -e ssh-copy-id -o StrictHostKeyChecking=no $HOST`:使用sshpass工具複製本機的SSH公鑰到遠程主機。其中,-e選項表示使用環境變量中的密碼(即SSHPASS)進行登錄,-o StrictHostKeyChecking=no選項表示連接時不檢查遠程主機的公鑰,以避免交互式確認。
# 
# 通過這段腳本,可以方便地將本機的SSH公鑰複製到多個遠程主機上,實現無需手動輸入密碼的SSH登錄。

添加啓用源

# Ubuntu忽略,CentOS執行

# 為 RHEL-9 SL-9 或 CentOS-9 安裝 ELRepo 
yum install https://www.elrepo.org/elrepo-release-9.el9.elrepo.noarch.rpm -y 
sed -i "s@mirrorlist@#mirrorlist@g" /etc/yum.repos.d/elrepo.repo 
sed -i "s@elrepo.org/linux@mirrors.tuna.tsinghua.edu.cn/elrepo@g" /etc/yum.repos.d/elrepo.repo 

# 為 RHEL-8或 CentOS-8配置源
yum install https://www.elrepo.org/elrepo-release-8.el8.elrepo.noarch.rpm -y 
sed -i "s@mirrorlist@#mirrorlist@g" /etc/yum.repos.d/elrepo.repo 
sed -i "s@elrepo.org/linux@mirrors.tuna.tsinghua.edu.cn/elrepo@g" /etc/yum.repos.d/elrepo.repo 

# 為 RHEL-7 SL-7 或 CentOS-7 安裝 ELRepo 
yum install https://www.elrepo.org/elrepo-release-7.el7.elrepo.noarch.rpm -y 
sed -i "s@mirrorlist@#mirrorlist@g" /etc/yum.repos.d/elrepo.repo 
sed -i "s@elrepo.org/linux@mirrors.tuna.tsinghua.edu.cn/elrepo@g" /etc/yum.repos.d/elrepo.repo 

# 查看可用安裝包
yum  --disablerepo="*"  --enablerepo="elrepo-kernel"  list  available

升級內核至4.18版本以上

# Ubuntu忽略,CentOS執行

# 安裝最新的內核
# 我這裏選擇的是穩定版kernel-ml   如需更新長期維護版本kernel-lt  
yum -y --enablerepo=elrepo-kernel  install  kernel-ml

# 查看已安裝那些內核
rpm -qa | grep kernel

# 查看默認內核
grubby --default-kernel

# 若不是最新的使用命令設置
grubby --set-default $(ls /boot/vmlinuz-* | grep elrepo)

# 重啓生效
reboot

# v8 整合命令為:
yum install https://www.elrepo.org/elrepo-release-8.el8.elrepo.noarch.rpm -y ; sed -i "s@mirrorlist@#mirrorlist@g" /etc/yum.repos.d/elrepo.repo ; sed -i "s@elrepo.org/linux@mirrors.tuna.tsinghua.edu.cn/elrepo@g" /etc/yum.repos.d/elrepo.repo ; yum  --disablerepo="*"  --enablerepo="elrepo-kernel"  list  available -y ; yum  --enablerepo=elrepo-kernel  install kernel-lt -y ; grubby --default-kernel ; reboot 

# v7 整合命令為:
yum install https://www.elrepo.org/elrepo-release-7.el7.elrepo.noarch.rpm -y ; sed -i "s@mirrorlist@#mirrorlist@g" /etc/yum.repos.d/elrepo.repo ; sed -i "s@elrepo.org/linux@mirrors.tuna.tsinghua.edu.cn/elrepo@g" /etc/yum.repos.d/elrepo.repo ; yum  --disablerepo="*"  --enablerepo="elrepo-kernel"  list  available -y ; yum  --enablerepo=elrepo-kernel  install  kernel-lt -y ; grubby --set-default $(ls /boot/vmlinuz-* | grep elrepo) ; grubby --default-kernel ; reboot 

# 離線版本 
yum install -y /root/cby/kernel-lt-*-1.el7.elrepo.x86_64.rpm ; grubby --set-default $(ls /boot/vmlinuz-* | grep elrepo) ; grubby --default-kernel ; reboot 

安裝ipvsadm

# 對於CentOS7離線安裝
# yum install /root/centos7/ipset-*.el7.x86_64.rpm /root/centos7/lm_sensors-libs-*.el7.x86_64.rpm  /root/centos7/ipset-libs-*.el7.x86_64.rpm /root/centos7/sysstat-*.el7_9.x86_64.rpm  /root/centos7/ipvsadm-*.el7.x86_64.rpm  -y

# 對於 Ubuntu
# apt install ipvsadm ipset sysstat conntrack -y

# 對於 CentOS
yum install ipvsadm ipset sysstat conntrack libseccomp -y
cat >> /etc/modules-load.d/ipvs.conf <<EOF 
ip_vs
ip_vs_rr
ip_vs_wrr
ip_vs_sh
nf_conntrack
ip_tables
ip_set
xt_set
ipt_set
ipt_rpfilter
ipt_REJECT
ipip
EOF

systemctl restart systemd-modules-load.service

lsmod | grep -e ip_vs -e nf_conntrack
ip_vs_sh               16384  0
ip_vs_wrr              16384  0
ip_vs_rr               16384  0
ip_vs                 237568  6 ip_vs_rr,ip_vs_sh,ip_vs_wrr
nf_conntrack          217088  3 nf_nat,nft_ct,ip_vs
nf_defrag_ipv6         24576  2 nf_conntrack,ip_vs
nf_defrag_ipv4         16384  1 nf_conntrack
libcrc32c              16384  5 nf_conntrack,nf_nat,nf_tables,xfs,ip_vs

# 參數解釋
#
# ip_vs
# IPVS 是 Linux 內核中的一個模塊,用於實現負載均衡和高可用性。它通過在前端代理服務器上分發傳入請求到後端實際服務器上,提供了高性能和可擴展的網絡服務。
#
# ip_vs_rr
# IPVS 的一種調度算法之一,使用輪詢方式分發請求到後端服務器,每個請求按順序依次分發。
#
# ip_vs_wrr
# IPVS 的一種調度算法之一,使用加權輪詢方式分發請求到後端服務器,每個請求按照指定的權重比例分發。
#
# ip_vs_sh
# IPVS 的一種調度算法之一,使用哈希方式根據源 IP 地址和目標 IP 地址來分發請求。
#
# nf_conntrack
# 這是一個內核模塊,用於跟蹤和管理網絡連接,包括 TCP、UDP 和 ICMP 等協議。它是實現防火牆狀態跟蹤的基礎。
#
# ip_tables
# 這是一個內核模塊,提供了對 Linux 系統 IP 數據包過濾和網絡地址轉換(NAT)功能的支持。
#
# ip_set
# 這是一個內核模塊,擴展了 iptables 的功能,支持更高效的 IP 地址集合操作。
#
# xt_set
# 這是一個內核模塊,擴展了 iptables 的功能,支持更高效的數據包匹配和操作。
#
# ipt_set
# 這是一個用户空間工具,用於配置和管理 xt_set 內核模塊。
#
# ipt_rpfilter
# 這是一個內核模塊,用於實現反向路徑過濾,用於防止 IP 欺騙和 DDoS 攻擊。
#
# ipt_REJECT
# 這是一個 iptables 目標,用於拒絕 IP 數據包,並向發送方發送響應,指示數據包被拒絕。
#
# ipip
# 這是一個內核模塊,用於實現 IP 封裝在 IP(IP-over-IP)的隧道功能。它可以在不同網絡之間創建虛擬隧道來傳輸 IP 數據包。

修改內核參數

cat <<EOF > /etc/sysctl.d/k8s.conf
net.ipv4.ip_forward = 1
net.bridge.bridge-nf-call-iptables = 1
fs.may_detach_mounts = 1
vm.overcommit_memory=1
vm.panic_on_oom=0
fs.inotify.max_user_watches=89100
fs.file-max=52706963
fs.nr_open=52706963
net.netfilter.nf_conntrack_max=2310720

net.ipv4.tcp_keepalive_time = 600
net.ipv4.tcp_keepalive_probes = 3
net.ipv4.tcp_keepalive_intvl =15
net.ipv4.tcp_max_tw_buckets = 36000
net.ipv4.tcp_tw_reuse = 1
net.ipv4.tcp_max_orphans = 327680
net.ipv4.tcp_orphan_retries = 3
net.ipv4.tcp_syncookies = 1
net.ipv4.tcp_max_syn_backlog = 16384
net.ipv4.ip_conntrack_max = 65536
net.ipv4.tcp_max_syn_backlog = 16384
net.ipv4.tcp_timestamps = 0
net.core.somaxconn = 16384

net.ipv6.conf.all.disable_ipv6 = 0
net.ipv6.conf.default.disable_ipv6 = 0
net.ipv6.conf.lo.disable_ipv6 = 0
net.ipv6.conf.all.forwarding = 1
EOF

sysctl --system

# 這些是Linux系統的一些參數設置,用於配置和優化網絡、文件系統和虛擬內存等方面的功能。以下是每個參數的詳細解釋:
# 
# 1. net.ipv4.ip_forward = 1
#    - 這個參數啓用了IPv4的IP轉發功能,允許服務器作為網絡路由器轉發數據包。
# 
# 2. net.bridge.bridge-nf-call-iptables = 1
#    - 當使用網絡橋接技術時,將數據包傳遞到iptables進行處理。
#   
# 3. fs.may_detach_mounts = 1
#    - 允許在掛載文件系統時,允許被其他進程使用。
#   
# 4. vm.overcommit_memory=1
#    - 該設置允許原始的內存過量分配策略,當系統的內存已經被完全使用時,系統仍然會分配額外的內存。
# 
# 5. vm.panic_on_oom=0
#    - 當系統內存不足(OOM)時,禁用系統崩潰和重啓。
# 
# 6. fs.inotify.max_user_watches=89100
#    - 設置系統允許一個用户的inotify實例可以監控的文件數目的上限。
# 
# 7. fs.file-max=52706963
#    - 設置系統同時打開的文件數的上限。
# 
# 8. fs.nr_open=52706963
#    - 設置系統同時打開的文件描述符數的上限。
# 
# 9. net.netfilter.nf_conntrack_max=2310720
#    - 設置系統可以創建的網絡連接跟蹤表項的最大數量。
# 
# 10. net.ipv4.tcp_keepalive_time = 600
#     - 設置TCP套接字的空閒超時時間(秒),超過該時間沒有活動數據時,內核會發送心跳包。
# 
# 11. net.ipv4.tcp_keepalive_probes = 3
#     - 設置未收到響應的TCP心跳探測次數。
# 
# 12. net.ipv4.tcp_keepalive_intvl = 15
#     - 設置TCP心跳探測的時間間隔(秒)。
# 
# 13. net.ipv4.tcp_max_tw_buckets = 36000
#     - 設置系統可以使用的TIME_WAIT套接字的最大數量。
# 
# 14. net.ipv4.tcp_tw_reuse = 1
#     - 啓用TIME_WAIT套接字的重新利用,允許新的套接字使用舊的TIME_WAIT套接字。
# 
# 15. net.ipv4.tcp_max_orphans = 327680
#     - 設置系統可以同時存在的TCP套接字垃圾回收包裹數的最大數量。
# 
# 16. net.ipv4.tcp_orphan_retries = 3
#     - 設置系統對於孤立的TCP套接字的重試次數。
# 
# 17. net.ipv4.tcp_syncookies = 1
#     - 啓用TCP SYN cookies保護,用於防止SYN洪泛攻擊。
# 
# 18. net.ipv4.tcp_max_syn_backlog = 16384
#     - 設置新的TCP連接的半連接數(半連接隊列)的最大長度。
# 
# 19. net.ipv4.ip_conntrack_max = 65536
#     - 設置系統可以創建的網絡連接跟蹤表項的最大數量。
# 
# 20. net.ipv4.tcp_timestamps = 0
#     - 關閉TCP時間戳功能,用於提供更好的安全性。
# 
# 21. net.core.somaxconn = 16384
#     - 設置系統核心層的連接隊列的最大值。
# 
# 22. net.ipv6.conf.all.disable_ipv6 = 0
#     - 啓用IPv6協議。
# 
# 23. net.ipv6.conf.default.disable_ipv6 = 0
#     - 啓用IPv6協議。
# 
# 24. net.ipv6.conf.lo.disable_ipv6 = 0
#     - 啓用IPv6協議。
# 
# 25. net.ipv6.conf.all.forwarding = 1
#     - 允許IPv6數據包轉發。

所有節點配置hosts本地解析

cat > /etc/hosts <<EOF
127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6

192.168.1.21 k8s-master01
192.168.1.22 k8s-master02
192.168.1.23 k8s-master03
192.168.1.24 k8s-node01
192.168.1.25 k8s-node02
192.168.1.36 lb-vip

fc00::21 k8s-master01
fc00::22 k8s-master02
fc00::23 k8s-master03
fc00::24 k8s-node01
fc00::25 k8s-node02
EOF

配置kubernetes安裝源

Debian / Ubuntu
  1. 在配置中添加鏡像(注意修改為自己需要的版本號):
curl -fsSL https://pkgs.k8s.io/core:/stable:/v1.32/deb/Release.key | gpg --dearmor -o /etc/apt/keyrings/kubernetes-apt-keyring.gpg

cat <<EOF | tee /etc/apt/sources.list.d/kubernetes.list
deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://mirrors.tuna.tsinghua.edu.cn/kubernetes/core:/stable:/v1.32/deb/ /
# deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://mirrors.tuna.tsinghua.edu.cn/kubernetes/addons:/cri-o:/stable:/v1.32/deb/ /
EOF
  1. 安裝必要應用:
apt-get update
apt-get install -y kubelet kubeadm kubectl
systemctl enable kubelet && systemctl start kubelet

# 如安裝指定版本
# apt install kubelet=1.28.2-00 kubeadm=1.28.2-00 kubectl=1.28.2-00
CentOS / RHEL / Fedora
  1. 執行如下命令(注意修改為自己需要的版本號):
cat <<EOF | tee /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=kubernetes
baseurl=https://mirrors.tuna.tsinghua.edu.cn/kubernetes/yum/repos/kubernetes-el7-$basearch
name=Kubernetes
baseurl=https://mirrors.tuna.tsinghua.edu.cn/kubernetes/core:/stable:/v1.32/rpm/
enabled=1
gpgcheck=1
gpgkey=https://pkgs.k8s.io/core:/stable:/v1.32/rpm/repodata/repomd.xml.key

[cri-o]
name=CRI-O
baseurl=https://mirrors.tuna.tsinghua.edu.cn/kubernetes/addons:/cri-o:/stable:/v1.32/rpm/
enabled=1
gpgcheck=1
gpgkey=https://pkgs.k8s.io/addons:/cri-o:/prerelease:/main/rpm/repodata/repomd.xml.key
EOF
  1. 安裝必要應用:
yum update
yum install -y kubelet kubeadm kubectl

# 如安裝指定版本
# yum install kubelet-1.28.2-0 kubeadm-1.28.2-0 kubectl-1.28.2-0

systemctl enable kubelet && systemctl start kubelet

# 將 SELinux 設置為 禁用
setenforce 0
sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/selinux/config

ps: 由於官網未開放同步方式, 可能會有索引gpg檢查失敗的情況, 這時請用 yum install -y --nogpgcheck kubelet kubeadm kubectl 安裝

k8s基本組件安裝

注意 :二選其一即可

安裝Containerd作為Runtime

# https://github.com/containernetworking/plugins/releases/
wget https://mirrors.chenby.cn/https://github.com/containernetworking/plugins/releases/download/v1.6.2/cni-plugins-linux-amd64-v1.6.2.tgz


#創建cni插件所需目錄
mkdir -p /etc/cni/net.d /opt/cni/bin 
#解壓cni二進制包
tar xf cni-plugins-linux-amd64-v*.tgz -C /opt/cni/bin/

# https://github.com/containerd/containerd/releases/
wget https://mirrors.chenby.cn/https://github.com/containerd/containerd/releases/download/v2.0.4/containerd-2.0.4-linux-amd64.tar.gz

#解壓
tar -xzf containerd-*-linux-amd64.tar.gz -C /usr/local/

#創建服務啓動文件
cat > /etc/systemd/system/containerd.service <<EOF
[Unit]
Description=containerd container runtime
Documentation=https://containerd.io
After=network.target local-fs.target

[Service]
ExecStartPre=-/sbin/modprobe overlay
ExecStart=/usr/local/bin/containerd
Type=notify
Delegate=yes
KillMode=process
Restart=always
RestartSec=5
LimitNPROC=infinity
LimitCORE=infinity
LimitNOFILE=infinity
TasksMax=infinity
OOMScoreAdjust=-999

[Install]
WantedBy=multi-user.target
EOF


# 參數解釋:
#
# 這是一個用於啓動containerd容器運行時的systemd unit文件。下面是對該文件不同部分的詳細解釋:
# 
# [Unit]
# Description=containerd container runtime
# 描述該unit的作用是作為containerd容器運行時。
# 
# Documentation=https://containerd.io
# 指向容器運行時的文檔的URL。
# 
# After=network.target local-fs.target
# 定義了在哪些依賴項之後該unit應該被啓動。在網絡和本地文件系統加載完成後啓動,確保了容器運行時在這些依賴項可用時才會啓動。
# 
# [Service]
# ExecStartPre=-/sbin/modprobe overlay
# 在啓動containerd之前執行的命令。這裏的命令是嘗試加載內核的overlay模塊,如果失敗則忽略錯誤繼續執行下面的命令。
# 
# ExecStart=/usr/local/bin/containerd
# 實際執行的命令,用於啓動containerd容器運行時。
# 
# Type=notify
# 指定服務的通知類型。這裏使用notify類型,表示當服務就緒時會通過通知的方式告知systemd。
# 
# Delegate=yes
# 允許systemd對此服務進行重啓和停止操作。
# 
# KillMode=process
# 在終止容器運行時時使用的kill模式。這裏使用process模式,表示通過終止進程來停止容器運行時。
# 
# Restart=always
# 定義了當容器運行時終止後的重啓策略。這裏設置為always,表示無論何時終止容器運行時,都會自動重新啓動。
# 
# RestartSec=5
# 在容器運行時終止後重新啓動之前等待的秒數。
# 
# LimitNPROC=infinity
# 指定容器運行時可以使用的最大進程數量。這裏設置為無限制。
# 
# LimitCORE=infinity
# 指定容器運行時可以使用的最大CPU核心數量。這裏設置為無限制。
# 
# LimitNOFILE=infinity
# 指定容器運行時可以打開的最大文件數。這裏設置為無限制。
# 
# TasksMax=infinity
# 指定容器運行時可以創建的最大任務數。這裏設置為無限制。
# 
# OOMScoreAdjust=-999
# 指定容器運行時的OOM(Out-Of-Memory)分數調整值。負數值表示容器運行時的優先級較高。
# 
# [Install]
# WantedBy=multi-user.target
# 定義了服務的安裝位置。這裏指定為multi-user.target,表示將服務安裝為多用户模式下的啓動項。

配置Containerd所需的模塊

cat <<EOF | sudo tee /etc/modules-load.d/containerd.conf
overlay
br_netfilter
EOF

# 參數解釋:
#
# containerd是一個容器運行時,用於管理和運行容器。它支持多種不同的參數配置來自定義容器運行時的行為和功能。
# 
# 1. overlay:overlay是容器d默認使用的存儲驅動,它提供了一種輕量級的、可堆疊的、逐層增量的文件系統。它通過在現有文件系統上疊加文件系統層來創建容器的文件系統視圖。每個容器可以有自己的一組文件系統層,這些層可以共享基礎鏡像中的文件,並在容器內部進行修改。使用overlay可以有效地使用磁盤空間,並使容器更加輕量級。
# 
# 2. br_netfilter:br_netfilter是Linux內核提供的一個網絡過濾器模塊,用於在容器網絡中進行網絡過濾和NAT轉發。當容器和主機之間的網絡通信需要進行DNAT或者SNAT時,br_netfilter模塊可以將IP地址進行轉換。它還可以提供基於iptables規則的網絡過濾功能,用於限制容器之間或容器與外部網絡之間的通信。
# 
# 這些參數可以在containerd的配置文件或者命令行中指定。例如,可以通過設置--storage-driver參數來選擇使用overlay作為存儲驅動,通過設置--iptables參數來啓用或禁用br_netfilter模塊。具體的使用方法和配置細節可以參考containerd的官方文檔。

加載模塊

systemctl restart systemd-modules-load.service

# 參數解釋:
# - `systemctl`: 是Linux系統管理服務的命令行工具,可以管理systemd init系統。
# - `restart`: 是systemctl命令的一個選項,用於重新啓動服務。
# - `systemd-modules-load.service`: 是一個系統服務,用於加載內核模塊。
# 
# 將上述參數結合在一起來解釋`systemctl restart systemd-modules-load.service`的含義:
# 這個命令用於重新啓動系統服務`systemd-modules-load.service`,它是負責加載內核模塊的服務。在重新啓動該服務後,系統會重新加載所有的內核模塊。

配置Containerd所需的內核

cat <<EOF | sudo 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

# 加載內核
sysctl --system

# 參數解釋:
# 
# 這些參數是Linux操作系統中用於網絡和網絡橋接設置的參數。
# 
# - net.bridge.bridge-nf-call-iptables:這個參數控制網絡橋接設備是否調用iptables規則處理網絡數據包。當該參數設置為1時,網絡數據包將被傳遞到iptables進行處理;當該參數設置為0時,網絡數據包將繞過iptables直接傳遞。默認情況下,這個參數的值是1,即啓用iptables規則處理網絡數據包。
# 
# - net.ipv4.ip_forward:這個參數用於控制是否啓用IP轉發功能。IP轉發使得操作系統可以將接收到的數據包從一個網絡接口轉發到另一個網絡接口。當該參數設置為1時,啓用IP轉發功能;當該參數設置為0時,禁用IP轉發功能。在網絡環境中,通常需要啓用IP轉發功能來實現不同網絡之間的通信。默認情況下,這個參數的值是0,即禁用IP轉發功能。
# 
# - net.bridge.bridge-nf-call-ip6tables:這個參數與net.bridge.bridge-nf-call-iptables類似,但是它用於IPv6數據包的處理。當該參數設置為1時,IPv6數據包將被傳遞到ip6tables進行處理;當該參數設置為0時,IPv6數據包將繞過ip6tables直接傳遞。默認情況下,這個參數的值是1,即啓用ip6tables規則處理IPv6數據包。
# 
# 這些參數的值可以通過修改操作系統的配置文件(通常是'/etc/sysctl.conf')來進行設置。修改完成後,需要使用'sysctl -p'命令重載配置文件使參數生效。

創建Containerd的配置文件

# 參數解釋:
# 
# 這段代碼是用於修改並配置containerd的參數。
# 
# 1. 首先使用命令`mkdir -p /etc/containerd`創建/etc/containerd目錄,如果該目錄已存在,則不進行任何操作。
# 2. 使用命令`containerd config default | tee /etc/containerd/config.toml`創建默認配置文件,並將輸出同時傳遞給/etc/containerd/config.toml文件。
# 3. 使用sed命令修改/etc/containerd/config.toml文件,將SystemdCgroup參數的值從false改為true。-i參數表示直接在原文件中進行編輯。
# 4. 使用cat命令結合grep命令查看/etc/containerd/config.toml文件中SystemdCgroup參數的值是否已修改為true。
# 5. 使用sed命令修改/etc/containerd/config.toml文件,將registry.k8s.io的地址替換為m.daocloud.io/registry.k8s.io。-i參數表示直接在原文件中進行編輯。
# 6. 使用cat命令結合grep命令查看/etc/containerd/config.toml文件中sandbox_image參數的值是否已修改為m.daocloud.io/registry.k8s.io。
# 7. 使用sed命令修改/etc/containerd/config.toml文件,將config_path參數的值從""改為"/etc/containerd/certs.d"。-i參數表示直接在原文件中進行編輯。
# 8. 使用cat命令結合grep命令查看/etc/containerd/config.toml文件中certs.d參數的值是否已修改為/etc/containerd/certs.d。
# 9. 使用mkdir命令創建/etc/containerd/certs.d/docker.io目錄,如果目錄已存在,則不進行任何操作。-p參數表示創建目錄時,如果父級目錄不存在,則自動創建父級目錄。
# 
# 最後,使用cat重定向操作符將內容寫入/etc/containerd/certs.d/docker.io/hosts.toml文件。該文件會配置加速器,其中server參數設置為"https://docker.io",host參數設置為"https://hub-mirror.c.163.com",並添加capabilities參數。

# 創建默認配置文件
mkdir -p /etc/containerd
containerd config default | tee /etc/containerd/config.toml

# 修改Containerd的配置文件

# sed -i "s#SystemdCgroup\ \=\ false#SystemdCgroup\ \=\ true#g" /etc/containerd/config.toml
# cat /etc/containerd/config.toml | grep SystemdCgroup

# 沙箱pause鏡像
sed -i "s#registry.k8s.io#registry.aliyuncs.com/chenby#g" /etc/containerd/config.toml
cat /etc/containerd/config.toml | grep sandbox

# 配置加速器
[root@k8s-master01 ~]# vim /etc/containerd/config.toml
[root@k8s-master01 ~]# cat /etc/containerd/config.toml | grep certs.d -C 5

    [plugins.'io.containerd.cri.v1.images'.pinned_images]
      sandbox = 'registry.aliyuncs.com/chenby/pause:3.10'

    [plugins.'io.containerd.cri.v1.images'.registry]
      config_path = '/etc/containerd/certs.d'

    [plugins.'io.containerd.cri.v1.images'.image_decryption]
      key_model = 'node'

  [plugins.'io.containerd.cri.v1.runtime']
[root@k8s-master01 ~]# 

mkdir /etc/containerd/certs.d/docker.io -pv
cat > /etc/containerd/certs.d/docker.io/hosts.toml << EOF
server = "https://docker.io"
[host."https://xxxxxxxxxxx.com"]
  capabilities = ["pull", "resolve"]
EOF

# 注意!
# 加速地址 自己去找 我這裏的地址已經失效了
# 
# SystemdCgroup參數是containerd中的一個配置參數,用於設置containerd在運行過程中使用的Cgroup(控制組)路徑。Containerd使用SystemdCgroup參數來指定應該使用哪個Cgroup來跟蹤和管理容器的資源使用。
# 
# Cgroup是Linux內核提供的一種資源隔離和管理機制,可以用於限制、分配和監控進程組的資源使用。使用Cgroup,可以將容器的資源限制和隔離,以防止容器之間的資源爭用和不公平的競爭。
# 
# 通過設置SystemdCgroup參數,可以確保containerd能夠找到正確的Cgroup路徑,並正確地限制和隔離容器的資源使用,確保容器可以按照預期的方式運行。如果未正確設置SystemdCgroup參數,可能會導致容器無法正確地使用資源,或者無法保證資源的公平分配和隔離。
# 
# 總而言之,SystemdCgroup參數的作用是為了確保containerd能夠正確地管理容器的資源使用,以實現資源的限制、隔離和公平分配。

啓動並設置為開機啓動

systemctl daemon-reload
# 用於重新加載systemd管理的單位文件。當你新增或修改了某個單位文件(如.service文件、.socket文件等),需要運行該命令來刷新systemd對該文件的配置。

systemctl enable --now containerd.service
# 啓用並立即啓動docker.service單元。docker.service是Docker守護進程的systemd服務單元。

systemctl stop containerd.service
# 停止運行中的docker.service單元,即停止Docker守護進程。

systemctl start containerd.service
# 啓動docker.service單元,即啓動Docker守護進程。

systemctl restart containerd.service
# 重啓docker.service單元,即重新啓動Docker守護進程。

systemctl status containerd.service
# 顯示docker.service單元的當前狀態,包括運行狀態、是否啓用等信息。

配置crictl客户端連接的運行時位置

# https://github.com/kubernetes-sigs/cri-tools/releases/
wget https://mirrors.chenby.cn/https://github.com/kubernetes-sigs/cri-tools/releases/download/v1.32.0/crictl-v1.32.0-linux-amd64.tar.gz

#解壓
tar xf crictl-v*-linux-amd64.tar.gz -C /usr/bin/
#生成配置文件
cat > /etc/crictl.yaml <<EOF
runtime-endpoint: unix:///run/containerd/containerd.sock
image-endpoint: unix:///run/containerd/containerd.sock
timeout: 10
debug: false
EOF

#測試
systemctl restart  containerd
crictl info

# 注意!
# 下面是參數`crictl`的詳細解釋
# 
# `crictl`是一個用於與容器運行時通信的命令行工具。它是容器運行時接口(CRI)工具的一個實現,可以對容器運行時進行管理和操作。
# 
# 1. `runtime-endpoint: unix:///run/containerd/containerd.sock`
# 指定容器運行時的終端套接字地址。在這個例子中,指定的地址是`unix:///run/containerd/containerd.sock`,這是一個Unix域套接字地址。
# 
# 2. `image-endpoint: unix:///run/containerd/containerd.sock`
# 指定容器鏡像服務的終端套接字地址。在這個例子中,指定的地址是`unix:///run/containerd/containerd.sock`,這是一個Unix域套接字地址。
# 
# 3. `timeout: 10`
# 設置與容器運行時通信的超時時間,單位是秒。在這個例子中,超時時間被設置為10秒。
# 
# 4. `debug: false`
# 指定是否開啓調式模式。在這個例子中,調式模式被設置為關閉,即`false`。如果設置為`true`,則會輸出更詳細的調試信息。
# 
# 這些參數可以根據需要進行修改,以便與容器運行時進行有效的通信和管理。

安裝docker作為Runtime

解壓docker程序

# 二進制包下載地址:https://download.docker.com/linux/static/stable/x86_64/
wget https://mirrors.tuna.tsinghua.edu.cn/docker-ce/linux/static/stable/x86_64/docker-28.0.2.tgz

#解壓
tar xf docker-*.tgz 
#拷貝二進制文件
cp docker/* /usr/bin/

創建containerd的service文件

#創建containerd的service文件,並且啓動
cat >/etc/systemd/system/containerd.service <<EOF
[Unit]
Description=containerd container runtime
Documentation=https://containerd.io
After=network.target local-fs.target

[Service]
ExecStartPre=-/sbin/modprobe overlay
ExecStart=/usr/bin/containerd
Type=notify
Delegate=yes
KillMode=process
Restart=always
RestartSec=5
LimitNPROC=infinity
LimitCORE=infinity
LimitNOFILE=1048576
TasksMax=infinity
OOMScoreAdjust=-999

[Install]
WantedBy=multi-user.target
EOF

# 參數解釋:
# 
# [Unit]
# - Description=containerd container runtime:指定服務的描述信息。
# - Documentation=https://containerd.io:指定服務的文檔鏈接。
# - After=network.target local-fs.target:指定服務的啓動順序,在網絡和本地文件系統啓動之後再啓動該服務。
# 
# [Service]
# - ExecStartPre=-/sbin/modprobe overlay:在啓動服務之前執行的命令,使用`-`表示忽略錯誤。
# - ExecStart=/usr/bin/containerd:指定服務的啓動命令。
# - Type=notify:指定服務的類型,`notify`表示服務會在啓動完成後向systemd發送通知。
# - Delegate=yes:允許服務代理其他服務的應答,例如收到關機命令後終止其他服務。
# - KillMode=process:指定服務終止時的行為,`process`表示終止服務進程。
# - Restart=always:指定服務終止後是否自動重啓,`always`表示總是自動重啓。
# - RestartSec=5:指定服務重啓的時間間隔,單位為秒。
# - LimitNPROC=infinity:限制服務的最大進程數,`infinity`表示沒有限制。
# - LimitCORE=infinity:限制服務的最大核心數,`infinity`表示沒有限制。
# - LimitNOFILE=infinity:限制服務的最大文件數,`infinity`表示沒有限制。
# - TasksMax=infinity:限制服務的最大任務數,`infinity`表示沒有限制。
# - OOMScoreAdjust=-999:指定服務的OOM(Out of Memory)得分,負數表示降低被終止的概率。
# 
# [Install]
# - WantedBy=multi-user.target:指定服務的安裝方式,`multi-user.target`表示該服務在多用户模式下安裝。


# 設置開機自啓
systemctl enable --now containerd.service

準備docker的service文件

#準備docker的service文件
cat > /etc/systemd/system/docker.service <<EOF
[Unit]
Description=Docker Application Container Engine
Documentation=https://docs.docker.com
After=network-online.target firewalld.service cri-docker.service docker.socket containerd.service
Wants=network-online.target
Requires=docker.socket containerd.service

[Service]
Type=notify
ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock
ExecReload=/bin/kill -s HUP $MAINPID
TimeoutSec=0
RestartSec=2
Restart=always
StartLimitBurst=3
StartLimitInterval=60s
LimitNOFILE=infinity
LimitNPROC=infinity
LimitCORE=infinity
TasksMax=infinity
Delegate=yes
KillMode=process
OOMScoreAdjust=-500

[Install]
WantedBy=multi-user.target
EOF

# 參數解釋:
# 
# [Unit]
# - Description: 描述服務的作用,這裏是Docker Application Container Engine,即Docker應用容器引擎。
# - Documentation: 提供關於此服務的文檔鏈接,這裏是Docker官方文檔鏈接。
# - After: 説明該服務在哪些其他服務之後啓動,這裏是在網絡在線、firewalld服務和containerd服務後啓動。
# - Wants: 説明該服務想要的其他服務,這裏是網絡在線服務。
# - Requires: 説明該服務需要的其他服務,這裏是containerd.service。
# 
# [Service]
# - Type: 服務類型,這裏是notify,表示服務在啓動完成時發送通知。
# - ExecStart: 命令,啓動該服務時會執行的命令,這裏是/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock,即啓動dockerd並指定一些參數,其中-H指定dockerd的監聽地址為fd://,--containerd指定containerd的sock文件位置。
# - ExecReload: 重載命令,當接收到HUP信號時執行的命令,這裏是/bin/kill -s HUP $MAINPID,即發送HUP信號給主進程ID。
# - TimeoutSec: 服務超時時間,這裏是0,表示沒有超時限制。
# - RestartSec: 重啓間隔時間,這裏是2秒,表示重啓失敗後等待2秒再重啓。
# - Restart: 重啓策略,這裏是always,表示總是重啓。
# - StartLimitBurst: 啓動限制次數,這裏是3,表示在啓動失敗後最多重試3次。
# - StartLimitInterval: 啓動限制時間間隔,這裏是60秒,表示兩次啓動之間最少間隔60秒。
# - LimitNOFILE: 文件描述符限制,這裏是infinity,表示沒有限制。
# - LimitNPROC: 進程數限制,這裏是infinity,表示沒有限制。
# - LimitCORE: 核心轉儲限制,這裏是infinity,表示沒有限制。
# - TasksMax: 最大任務數,這裏是infinity,表示沒有限制。
# - Delegate: 修改權限,這裏是yes,表示啓用權限修改。
# - KillMode: 殺死模式,這裏是process,表示殺死整個進程組。
# - OOMScoreAdjust: 用於調整進程在系統內存緊張時的優先級調整,這裏是-500,表示將OOM分數降低500。
# 
# [Install]
# - WantedBy: 安裝目標,這裏是multi-user.target,表示在多用户模式下安裝。
#      在WantedBy參數中,我們可以使用以下參數:
#      1. multi-user.target:指定該服務應該在多用户模式下啓動。
#      2. graphical.target:指定該服務應該在圖形化界面模式下啓動。
#      3. default.target:指定該服務應該在系統的默認目標(runlevel)下啓動。
#      4. rescue.target:指定該服務應該在系統救援模式下啓動。
#      5. poweroff.target:指定該服務應該在關機時啓動。
#      6. reboot.target:指定該服務應該在重啓時啓動。
#      7. halt.target:指定該服務應該在停止時啓動。
#      8. shutdown.target:指定該服務應該在系統關閉時啓動。
#      這些參數可以根據需要選擇一個或多個,以告知系統在何時啓動該服務。

準備docker的socket文件

#準備docker的socket文件
cat > /etc/systemd/system/docker.socket <<EOF
[Unit]
Description=Docker Socket for the API

[Socket]
ListenStream=/var/run/docker.sock
SocketMode=0660
SocketUser=root
SocketGroup=docker

[Install]
WantedBy=sockets.target
EOF

# 這是一個用於Docker API的socket配置文件,包含了以下參數:
# 
# [Unit]
# - Description:描述了該socket的作用,即為Docker API的socket。
# 
# [Socket]
# - ListenStream:指定了socket的監聽地址,該socket會監聽在/var/run/docker.sock上,即Docker守護程序使用的默認sock文件。
# - SocketMode:指定了socket文件的權限模式,此處為0660,即用户和用户組有讀寫權限,其他用户無權限。
# - SocketUser:指定了socket文件的所有者,此處為root用户。
# - SocketGroup:指定了socket文件的所屬用户組,此處為docker用户組。
# 
# [Install]
# - WantedBy:指定了該socket被啓用時的目標,此處為sockets.target,表示當sockets.target啓動時啓用該socket。
# 
# 該配置文件的作用是為Docker提供API訪問的通道,它監聽在/var/run/docker.sock上,具有root用户權限,但只接受docker用户組的成員的連接,並且其他用户無法訪問。這樣,只有docker用户組的成員可以通過該socket與Docker守護進程進行通信。

配置加速器

# 配置加速器
mkdir /etc/docker/ -pv
cat >/etc/docker/daemon.json <<EOF
{
  "exec-opts": ["native.cgroupdriver=systemd"],
  "registry-mirrors": [
    "https://xxxxxxxxxxxx.com"
  ],
  "max-concurrent-downloads": 10,
  "log-driver": "json-file",
  "log-level": "warn",
  "log-opts": {
    "max-size": "10m",
    "max-file": "3"
    },
  "data-root": "/var/lib/docker"
}
EOF


# 該參數文件中包含以下參數:
# 
# 加速地址自己找 我的已經失效了
# 
# 1. exec-opts: 用於設置Docker守護進程的選項,native.cgroupdriver=systemd表示使用systemd作為Cgroup驅動程序。
# 2. registry-mirrors: 用於指定Docker鏡像的鏡像註冊服務器。在這裏有三個鏡像註冊服務器:https://docker.m.daocloud.io、https://docker.mirrors.ustc.edu.cn和http://hub-mirror.c.163.com。
# 3. max-concurrent-downloads: 用於設置同時下載鏡像的最大數量,默認值為3,這裏設置為10。
# 4. log-driver: 用於設置Docker守護進程的日誌驅動程序,這裏設置為json-file。
# 5. log-level: 用於設置日誌的級別,這裏設置為warn。
# 6. log-opts: 用於設置日誌驅動程序的選項,這裏有兩個選項:max-size和max-file。max-size表示每個日誌文件的最大大小,這裏設置為10m,max-file表示保存的最大日誌文件數量,這裏設置為3。
# 7. data-root: 用於設置Docker守護進程的數據存儲根目錄,默認為/var/lib/docker,這裏設置為/var/lib/docker。

啓動docker

groupadd docker
#創建docker組

systemctl daemon-reload
# 用於重新加載systemd管理的單位文件。當你新增或修改了某個單位文件(如.service文件、.socket文件等),需要運行該命令來刷新systemd對該文件的配置。

systemctl enable --now docker.socket
# 啓用並立即啓動docker.socket單元。docker.socket是一個systemd的socket單元,用於接收來自網絡的Docker API請求。

systemctl enable --now docker.service
# 啓用並立即啓動docker.service單元。docker.service是Docker守護進程的systemd服務單元。

systemctl stop docker.service
# 停止運行中的docker.service單元,即停止Docker守護進程。

systemctl start docker.service
# 啓動docker.service單元,即啓動Docker守護進程。

systemctl restart docker.service
# 重啓docker.service單元,即重新啓動Docker守護進程。

systemctl status docker.service
# 顯示docker.service單元的當前狀態,包括運行狀態、是否啓用等信息。

docker info
#驗證

解壓cri-docker

# 由於1.24以及更高版本不支持docker所以安裝cri-docker
# 下載cri-docker 
# https://github.com/Mirantis/cri-dockerd/releases/
wget  https://mirrors.chenby.cn/https://github.com/Mirantis/cri-dockerd/releases/download/v0.3.16/cri-dockerd-0.3.16.amd64.tgz

# 解壓cri-docker
tar xvf cri-dockerd-*.amd64.tgz 
cp -r cri-dockerd/  /usr/bin/
chmod +x /usr/bin/cri-dockerd/cri-dockerd

寫入啓動cri-docker配置文件

# 寫入啓動配置文件
cat >  /usr/lib/systemd/system/cri-docker.service <<EOF
[Unit]
Description=CRI Interface for Docker Application Container Engine
Documentation=https://docs.mirantis.com
After=network-online.target firewalld.service docker.service
Wants=network-online.target
Requires=docker.service

[Service]
Type=notify
ExecStart=/usr/bin/cri-dockerd/cri-dockerd --network-plugin=cni --pod-infra-container-image=registry.aliyuncs.com/google_containers/pause:3.7
ExecReload=/bin/kill -s HUP $MAINPID
TimeoutSec=0
RestartSec=2
Restart=always
StartLimitBurst=3
StartLimitInterval=60s
LimitNOFILE=infinity
LimitNPROC=infinity
LimitCORE=infinity
TasksMax=infinity
Delegate=yes
KillMode=process

[Install]
WantedBy=multi-user.target
EOF


# [Unit]
# - Description:該參數用於描述該單元的功能,這裏描述的是CRI與Docker應用容器引擎的接口。
# - Documentation:該參數指定了相關文檔的網址,供用户參考。
# - After:該參數指定了此單元應該在哪些其他單元之後啓動,確保在網絡在線、防火牆和Docker服務啓動之後再啓動此單元。
# - Wants:該參數指定了此單元希望也啓動的所有單元,此處是希望在網絡在線之後啓動。
# - Requires:該參數指定了此單元需要依賴的單元,此處是cri-docker.socket單元。
# 
# [Service]
# - Type:該參數指定了服務的類型,這裏是notify,表示當服務啓動完成時向系統發送通知。
# - ExecStart:該參數指定了將要運行的命令和參數,此處是執行/usr/bin/cri-dockerd/cri-dockerd命令,並指定了網絡插件為cni和Pod基礎設施容器的鏡像為registry.aliyuncs.com/google_containers/pause:3.7。
# - ExecReload:該參數指定在服務重載時運行的命令,此處是發送HUP信號給主進程。
# - TimeoutSec:該參數指定了服務啓動的超時時間,此處為0,表示無限制。
# - RestartSec:該參數指定了自動重啓服務的時間間隔,此處為2秒。
# - Restart:該參數指定了在服務發生錯誤時自動重啓,此處是始終重啓。
# - StartLimitBurst:該參數指定了在給定時間間隔內允許的啓動失敗次數,此處為3次。
# - StartLimitInterval:該參數指定啓動失敗的時間間隔,此處為60秒。
# - LimitNOFILE:該參數指定了允許打開文件的最大數量,此處為無限制。
# - LimitNPROC:該參數指定了允許同時運行的最大進程數,此處為無限制。
# - LimitCORE:該參數指定了允許生成的core文件的最大大小,此處為無限制。
# - TasksMax:該參數指定了此服務的最大任務數,此處為無限制。
# - Delegate:該參數指定了是否將控制權委託給指定服務,此處為是。
# - KillMode:該參數指定了在終止服務時如何處理進程,此處是通過終止進程來終止服務。
# 
# [Install]
# - WantedBy:該參數指定了希望這個單元啓動的多用户目標。在這裏,這個單元希望在multi-user.target啓動。

寫入cri-docker的socket配置文件

# 寫入socket配置文件
cat > /usr/lib/systemd/system/cri-docker.socket <<EOF
[Unit]
Description=CRI Docker Socket for the API
PartOf=cri-docker.service

[Socket]
ListenStream=%t/cri-dockerd.sock
SocketMode=0660
SocketUser=root
SocketGroup=docker

[Install]
WantedBy=sockets.target
EOF


# 該配置文件是用於systemd的單元配置文件(unit file),用於定義一個socket單元。
# 
# [Unit]
# - Description:表示該單元的描述信息。
# - PartOf:表示該單元是cri-docker.service的一部分。
# 
# [Socket]
# - ListenStream:指定了該socket要監聽的地址和端口,這裏使用了%t佔位符,表示根據單元的類型來決定路徑。%t/cri-dockerd.sock表示將監聽Unix域套接字cri-dockerd.sock。Unix域套接字用於在同一台主機上的進程之間通信。
# - SocketMode:指定了socket文件的權限模式,此處為0660,即用户和用户組有讀寫權限,其他用户無權限。
# - SocketUser:指定了socket文件的所有者,此處為root用户。
# - SocketGroup:指定了socket文件的所屬用户組,此處為docker用户組。
# 
# [Install]
# - WantedBy:部分定義了該單元的安裝配置信息。WantedBy=sockets.target表示當sockets.target單元啓動時,自動啓動該socket單元。sockets.target是一個系統服務,用於管理所有的socket單元。

啓動cri-docker

systemctl daemon-reload
# 用於重新加載systemd管理的單位文件。當你新增或修改了某個單位文件(如.service文件、.socket文件等),需要運行該命令來刷新systemd對該文件的配置。

systemctl enable --now cri-docker.service
# 啓用並立即啓動cri-docker.service單元。cri-docker.service是cri-docker守護進程的systemd服務單元。

systemctl restart cri-docker.service
# 重啓cri-docker.service單元,即重新啓動cri-docker守護進程。

systemctl status docker.service
# 顯示docker.service單元的當前狀態,包括運行狀態、是否啓用等信息。

高可用keepalived、haproxy

安裝keepalived和haproxy服務

yum -y install keepalived haproxy

修改haproxy配置文件(配置文件一樣)

# cp /etc/haproxy/haproxy.cfg /etc/haproxy/haproxy.cfg.bak

cat >/etc/haproxy/haproxy.cfg<<"EOF"
global
 maxconn 2000
 ulimit-n 16384
 log 127.0.0.1 local0 err
 stats timeout 30s

defaults
 log global
 mode http
 option httplog
 timeout connect 5000
 timeout client 50000
 timeout server 50000
 timeout http-request 15s
 timeout http-keep-alive 15s


frontend monitor-in
 bind *:33305
 mode http
 option httplog
 monitor-uri /monitor

frontend k8s-master
 bind 0.0.0.0:9443
 bind 127.0.0.1:9443
 mode tcp
 option tcplog
 tcp-request inspect-delay 5s
 default_backend k8s-master


backend k8s-master
 mode tcp
 option tcplog
 option tcp-check
 balance roundrobin
 default-server inter 10s downinter 5s rise 2 fall 2 slowstart 60s maxconn 250 maxqueue 256 weight 100
 server  k8s-master01  192.168.1.21:6443 check
 server  k8s-master02  192.168.1.22:6443 check
 server  k8s-master03  192.168.1.23:6443 check
EOF

參數

這段配置代碼是指定了一個HAProxy負載均衡器的配置。下面對各部分進行詳細解釋:
1. global:
   - maxconn 2000: 設置每個進程的最大連接數為2000。
   - ulimit-n 16384: 設置每個進程的最大文件描述符數為16384。
   - log 127.0.0.1 local0 err: 指定日誌的輸出地址為本地主機的127.0.0.1,並且只記錄錯誤級別的日誌。
   - stats timeout 30s: 設置查看負載均衡器統計信息的超時時間為30秒。

2. defaults:
   - log global: 使默認日誌與global部分相同。
   - mode http: 設定負載均衡器的工作模式為HTTP模式。
   - option httplog: 使負載均衡器記錄HTTP協議的日誌。
   - timeout connect 5000: 設置與後端服務器建立連接的超時時間為5秒。
   - timeout client 50000: 設置與客户端的連接超時時間為50秒。
   - timeout server 50000: 設置與後端服務器連接的超時時間為50秒。
   - timeout http-request 15s: 設置處理HTTP請求的超時時間為15秒。
   - timeout http-keep-alive 15s: 設置保持HTTP連接的超時時間為15秒。

3. frontend monitor-in:
   - bind *:33305: 監聽所有IP地址的33305端口。
   - mode http: 設定frontend的工作模式為HTTP模式。
   - option httplog: 記錄HTTP協議的日誌。
   - monitor-uri /monitor: 設置監控URI為/monitor。

4. frontend k8s-master:
   - bind 0.0.0.0:9443: 監聽所有IP地址的9443端口。
   - bind 127.0.0.1:9443: 監聽本地主機的9443端口。
   - mode tcp: 設定frontend的工作模式為TCP模式。
   - option tcplog: 記錄TCP協議的日誌。
   - tcp-request inspect-delay 5s: 設置在接收到請求後延遲5秒進行檢查。
   - default_backend k8s-master: 設置默認的後端服務器組為k8s-master。

5. backend k8s-master:
   - mode tcp: 設定backend的工作模式為TCP模式。
   - option tcplog: 記錄TCP協議的日誌。
   - option tcp-check: 啓用TCP檢查功能。
   - balance roundrobin: 使用輪詢算法進行負載均衡。
   - default-server inter 10s downinter 5s rise 2 fall 2 slowstart 60s maxconn 250 maxqueue 256 weight 100: 設置默認的服務器參數。
   - server k8s-master01 192.168.1.21:6443 check: 增加一個名為k8s-master01的服務器,IP地址為192.168.1.21,端口號為6443,並對其進行健康檢查。
   - server k8s-master02 192.168.1.22:6443 check: 增加一個名為k8s-master02的服務器,IP地址為192.168.1.22,端口號為6443,並對其進行健康檢查。
   - server k8s-master03 192.168.1.23:6443 check: 增加一個名為k8s-master03的服務器,IP地址為192.168.1.23,端口號為6443,並對其進行健康檢查。

以上就是這段配置代碼的詳細解釋。它主要定義了全局配置、默認配置、前端監聽和後端服務器組的相關參數和設置。通過這些配置,可以實現負載均衡和監控功能。

Master01配置keepalived master節點

#cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.bak

cat > /etc/keepalived/keepalived.conf << EOF
! Configuration File for keepalived

global_defs {
    router_id LVS_DEVEL
}
vrrp_script chk_apiserver {
    script "/etc/keepalived/check_apiserver.sh"
    interval 5 
    weight -5
    fall 2
    rise 1
}
vrrp_instance VI_1 {
    state MASTER
    # 注意網卡名
    interface ens160 
    mcast_src_ip 192.168.1.21
    virtual_router_id 51
    priority 100
    nopreempt
    advert_int 2
    authentication {
        auth_type PASS
        auth_pass K8SHA_KA_AUTH
    }
    virtual_ipaddress {
        192.168.1.36
    }
    track_script {
      chk_apiserver 
} }

EOF

Master02配置keepalived backup節點

# cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.bak

cat > /etc/keepalived/keepalived.conf << EOF
! Configuration File for keepalived

global_defs {
    router_id LVS_DEVEL
}
vrrp_script chk_apiserver {
    script "/etc/keepalived/check_apiserver.sh"
    interval 5 
    weight -5
    fall 2
    rise 1

}
vrrp_instance VI_1 {
    state BACKUP
    # 注意網卡名
    interface ens160
    mcast_src_ip 192.168.1.22
    virtual_router_id 51
    priority 80
    nopreempt
    advert_int 2
    authentication {
        auth_type PASS
        auth_pass K8SHA_KA_AUTH
    }
    virtual_ipaddress {
        192.168.1.36
    }
    track_script {
      chk_apiserver 
} }

EOF

Master03配置keepalived backup節點

# cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.conf.bak

cat > /etc/keepalived/keepalived.conf << EOF
! Configuration File for keepalived

global_defs {
    router_id LVS_DEVEL
}
vrrp_script chk_apiserver {
    script "/etc/keepalived/check_apiserver.sh"
    interval 5 
    weight -5
    fall 2
    rise 1

}
vrrp_instance VI_1 {
    state BACKUP
    # 注意網卡名
    interface ens160
    mcast_src_ip 192.168.1.23
    virtual_router_id 51
    priority 50
    nopreempt
    advert_int 2
    authentication {
        auth_type PASS
        auth_pass K8SHA_KA_AUTH
    }
    virtual_ipaddress {
        192.168.1.36
    }
    track_script {
      chk_apiserver 
} }

EOF

參數

這是一個用於配置keepalived的配置文件。下面是對每個部分的詳細解釋:

- `global_defs`部分定義了全局參數。
- `router_id`參數指定了當前路由器的標識,這裏設置為"LVS_DEVEL"。

- `vrrp_script`部分定義了一個VRRP腳本。`chk_apiserver`是腳本的名稱,
    - `script`參數指定了腳本的路徑。該腳本每5秒執行一次,返回值為0表示服務正常,返回值為1表示服務異常。
    - `weight`參數指定了根據腳本返回的值來調整優先級,這裏設置為-5。
    - `fall`參數指定了失敗閾值,當連續2次腳本返回值為1時認為服務異常。
    - `rise`參數指定了恢復閾值,當連續1次腳本返回值為0時認為服務恢復正常。

- `vrrp_instance`部分定義了一個VRRP實例。`VI_1`是實例的名稱。
    - `state`參數指定了當前實例的狀態,這裏設置為MASTER表示當前實例是主節點。
    - `interface`參數指定了要監聽的網卡,這裏設置為ens160。
    - `mcast_src_ip`參數指定了VRRP報文的源IP地址,這裏設置為192.168.1.21。
    - `virtual_router_id`參數指定了虛擬路由器的ID,這裏設置為51。
    - `priority`參數指定了實例的優先級,優先級越高(數值越大)越有可能被選為主節點。
    - `nopreempt`參數指定了當主節點失效後不要搶佔身份,即不要自動切換為主節點。
    - `advert_int`參數指定了發送廣播的間隔時間,這裏設置為2秒。
    - `authentication`部分指定了認證參數
        - `auth_type`參數指定了認證類型,這裏設置為PASS表示使用密碼認證,
        - `auth_pass`參數指定了認證密碼,這裏設置為K8SHA_KA_AUTH。
    - `virtual_ipaddress`部分指定了虛擬IP地址,這裏設置為192.168.1.36。
    - `track_script`部分指定了要跟蹤的腳本,這裏跟蹤了chk_apiserver腳本。

健康檢查腳本配置(lb主機)

cat >  /etc/keepalived/check_apiserver.sh << EOF
#!/bin/bash

err=0
for k in \$(seq 1 3)
do
    check_code=\$(pgrep haproxy)
    if [[ \$check_code == "" ]]; then
        err=\$(expr \$err + 1)
        sleep 1
        continue
    else
        err=0
        break
    fi
done

if [[ \$err != "0" ]]; then
    echo "systemctl stop keepalived"
    /usr/bin/systemctl stop keepalived
    exit 1
else
    exit 0
fi
EOF

# 給腳本授權

chmod +x /etc/keepalived/check_apiserver.sh

# 這段腳本是一個簡單的bash腳本,主要用來檢查是否有名為haproxy的進程正在運行。
# 
# 腳本的主要邏輯如下:
# 1. 首先設置一個變量err為0,用來記錄錯誤次數。
# 2. 使用一個循環,在循環內部執行以下操作:
#    a. 使用pgrep命令檢查是否有名為haproxy的進程在運行。如果不存在該進程,將err加1,並暫停1秒鐘,然後繼續下一次循環。
#    b. 如果存在haproxy進程,將err重置為0,並跳出循環。
# 3. 檢查err的值,如果不為0,表示檢查失敗,輸出一條錯誤信息並執行“systemctl stop keepalived”命令停止keepalived進程,並退出腳本返回1。
# 4. 如果err的值為0,表示檢查成功,退出腳本返回0。
# 
# 該腳本的主要作用是檢查是否存在運行中的haproxy進程,如果無法檢測到haproxy進程,將停止keepalived進程並返回錯誤狀態。如果haproxy進程存在,則返回成功狀態。這個腳本可能是作為一個健康檢查腳本的一部分,在確保haproxy服務可用的情況下,才繼續運行其他操作。

啓動服務

systemctl daemon-reload
# 用於重新加載systemd管理的單位文件。當你新增或修改了某個單位文件(如.service文件、.socket文件等),需要運行該命令來刷新systemd對該文件的配置。
systemctl enable --now haproxy.service
# 啓用並立即啓動haproxy.service單元。haproxy.service是haproxy守護進程的systemd服務單元。
systemctl enable --now keepalived.service
# 啓用並立即啓動keepalived.service單元。keepalived.service是keepalived守護進程的systemd服務單元。
systemctl status haproxy.service
# haproxy.service單元的當前狀態,包括運行狀態、是否啓用等信息。
systemctl status keepalived.service
# keepalived.service單元的當前狀態,包括運行狀態、是否啓用等信息。

測試高可用

# 能ping同
[root@k8s-node02 ~]# ping 192.168.1.36

# 能telnet訪問
[root@k8s-node02 ~]# telnet 192.168.1.36 9443

# 關閉主節點,看vip是否漂移到備節點

初始化安裝

整改鏡像
# 查看最新版本有那些鏡像
[root@k8s-master01 ~]# kubeadm config images list --image-repository registry.aliyuncs.com/google_containers
registry.aliyuncs.com/google_containers/kube-apiserver:v1.32.3
registry.aliyuncs.com/google_containers/kube-controller-manager:v1.32.3
registry.aliyuncs.com/google_containers/kube-scheduler:v1.32.3
registry.aliyuncs.com/google_containers/kube-proxy:v1.32.3
registry.aliyuncs.com/google_containers/coredns:v1.11.3
registry.aliyuncs.com/google_containers/pause:3.10
registry.aliyuncs.com/google_containers/etcd:3.5.16-0
[root@k8s-master01 ~]# 

# 只有一個CRI的情況下
kubeadm config images pull --image-repository registry.aliyuncs.com/google_containers
# 指定CRI拉去鏡像
kubeadm config images pull --image-repository registry.aliyuncs.com/google_containers --cri-socket unix:///var/run/cri-dockerd.sock
kubeadm config images pull --image-repository registry.aliyuncs.com/google_containers --cri-socket unix:///var/run/containerd/containerd.sock

修改初始化配置

# 創建默認配置
kubeadm config print init-defaults > kubeadm-init.yaml
# 這是我使用的配置文件
cat > kubeadm.yaml << EOF
apiVersion: kubeadm.k8s.io/v1beta4
bootstrapTokens:
- groups:
  - system:bootstrappers:kubeadm:default-node-token
  token: abcdef.0123456789abcdef
  ttl: 24h0m0s
  usages:
  - signing
  - authentication
kind: InitConfiguration
localAPIEndpoint:
  advertiseAddress: 192.168.1.21
  bindPort: 6443
nodeRegistration:
  # criSocket: unix:///run/containerd/containerd.sock
  criSocket: unix:///var/run/cri-dockerd.sock
  imagePullPolicy: IfNotPresent
  imagePullSerial: true
  kubeletExtraArgs:
  - name: "node-ip"
    value: "192.168.1.21,fc00::21"
  name: k8s-master01
  taints:
  - effect: PreferNoSchedule
    key: node-role.kubernetes.io/master
timeouts:
  controlPlaneComponentHealthCheck: 4m0s
  discovery: 5m0s
  etcdAPICall: 2m0s
  kubeletHealthCheck: 4m0s
  kubernetesAPICall: 1m0s
  tlsBootstrap: 5m0s
  upgradeManifests: 5m0s
---
apiServer:
  certSANs:
    - x.oiox.cn
    - z.oiox.cn
    - k8s-master01
    - k8s-master02
    - k8s-master03
    - 192.168.1.21
    - 192.168.1.22
    - 192.168.1.23
    - 192.168.1.24
    - 192.168.1.25
    - 192.168.1.26
    - 192.168.1.27
    - 192.168.1.28
    - 192.168.1.29
    - 127.0.0.1
  timeoutForControlPlane: 4m0s
apiVersion: kubeadm.k8s.io/v1beta4
caCertificateValidityPeriod: 87600h0m0s
certificateValidityPeriod: 8760h0m0s
certificatesDir: /etc/kubernetes/pki
clusterName: kubernetes
controllerManager: {}
dns: {}
encryptionAlgorithm: RSA-2048
etcd:
  local:
    dataDir: /var/lib/etcd
imageRepository: registry.aliyuncs.com/google_containers
kind: ClusterConfiguration
kubernetesVersion: 1.32.3
networking:
  dnsDomain: cluster.local
  podSubnet: 172.16.0.0/12,fc00:2222::/64
  serviceSubnet: 10.96.0.0/16,fd00:1111::/112
proxy: {}
scheduler: {}
controlPlaneEndpoint: "192.168.1.36:9443"
---
apiVersion: kubeproxy.config.k8s.io/v1alpha1
kind: KubeProxyConfiguration
mode: ipvs
---
apiVersion: kubelet.config.k8s.io/v1beta1
authentication:
  anonymous:
    enabled: false
  webhook:
    cacheTTL: 0s
    enabled: true
  x509:
    clientCAFile: /etc/kubernetes/pki/ca.crt
authorization:
  mode: Webhook
  webhook:
    cacheAuthorizedTTL: 0s
    cacheUnauthorizedTTL: 0s
clusterDNS:
- 10.96.0.10
clusterDomain: cluster.local
cpuManagerReconcilePeriod: 0s
evictionPressureTransitionPeriod: 0s
fileCheckFrequency: 0s
healthzBindAddress: 127.0.0.1
healthzPort: 10248
httpCheckFrequency: 0s
imageMinimumGCAge: 0s
kind: KubeletConfiguration
cgroupDriver: systemd
logging: {}
memorySwap: {}
nodeStatusReportFrequency: 0s
nodeStatusUpdateFrequency: 0s
rotateCertificates: true
runtimeRequestTimeout: 0s
shutdownGracePeriod: 0s
shutdownGracePeriodCriticalPods: 0s
staticPodPath: /etc/kubernetes/manifests
streamingConnectionIdleTimeout: 0s
syncFrequency: 0s
volumeStatsAggPeriod: 0s
EOF

開始初始化

[root@k8s-master01 ~]# kubeadm init --config=kubeadm.yaml
W0323 14:33:08.483853   15471 initconfiguration.go:332] error unmarshaling configuration schema.GroupVersionKind{Group:"kubeadm.k8s.io", Version:"v1beta4", Kind:"ClusterConfiguration"}: strict decoding error: unknown field "apiServer.timeoutForControlPlane"
[init] Using Kubernetes version: v1.32.3
[preflight] Running pre-flight checks
    [WARNING Hostname]: hostname "node" could not be reached
    [WARNING Hostname]: hostname "node": lookup node on 192.168.1.99:53: no such host
[preflight] Pulling images required for setting up a Kubernetes cluster
[preflight] This might take a minute or two, depending on the speed of your internet connection
[preflight] You can also perform this action beforehand using 'kubeadm config images pull'
W0323 14:33:08.591394   15471 checks.go:846] detected that the sandbox image "registry.aliyuncs.com/google_containers/pause:3.7" of the container runtime is inconsistent with that used by kubeadm.It is recommended to use "registry.aliyuncs.com/google_containers/pause:3.10" as the CRI sandbox image.
[certs] Using certificateDir folder "/etc/kubernetes/pki"
[certs] Generating "ca" certificate and key
[certs] Generating "apiserver" certificate and key
[certs] apiserver serving cert is signed for DNS names [k8s-master01 k8s-master02 k8s-master03 kubernetes kubernetes.default kubernetes.default.svc kubernetes.default.svc.cluster.local node x.oiox.cn z.oiox.cn] and IPs [10.96.0.1 192.168.1.21 192.168.1.36 192.168.1.22 192.168.1.23 192.168.1.24 192.168.1.25 192.168.1.26 192.168.1.27 192.168.1.28 192.168.1.29 127.0.0.1]
[certs] Generating "apiserver-kubelet-client" certificate and key
[certs] Generating "front-proxy-ca" certificate and key
[certs] Generating "front-proxy-client" certificate and key
[certs] Generating "etcd/ca" certificate and key
[certs] Generating "etcd/server" certificate and key
[certs] etcd/server serving cert is signed for DNS names [localhost node] and IPs [192.168.1.21 127.0.0.1 ::1]
[certs] Generating "etcd/peer" certificate and key
[certs] etcd/peer serving cert is signed for DNS names [localhost node] and IPs [192.168.1.21 127.0.0.1 ::1]
[certs] Generating "etcd/healthcheck-client" certificate and key
[certs] Generating "apiserver-etcd-client" certificate and key
[certs] Generating "sa" key and public key
[kubeconfig] Using kubeconfig folder "/etc/kubernetes"
W0323 14:33:10.094613   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[kubeconfig] Writing "admin.conf" kubeconfig file
W0323 14:33:10.188907   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[kubeconfig] Writing "super-admin.conf" kubeconfig file
W0323 14:33:10.447566   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[kubeconfig] Writing "kubelet.conf" kubeconfig file
W0323 14:33:10.495558   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[kubeconfig] Writing "controller-manager.conf" kubeconfig file
W0323 14:33:10.579310   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[kubeconfig] Writing "scheduler.conf" kubeconfig file
[etcd] Creating static Pod manifest for local etcd in "/etc/kubernetes/manifests"
[control-plane] Using manifest folder "/etc/kubernetes/manifests"
[control-plane] Creating static Pod manifest for "kube-apiserver"
[control-plane] Creating static Pod manifest for "kube-controller-manager"
[control-plane] Creating static Pod manifest for "kube-scheduler"
[kubelet-start] Writing kubelet environment file with flags to file "/var/lib/kubelet/kubeadm-flags.env"
[kubelet-start] Writing kubelet configuration to file "/var/lib/kubelet/config.yaml"
[kubelet-start] Starting the kubelet
[wait-control-plane] Waiting for the kubelet to boot up the control plane as static Pods from directory "/etc/kubernetes/manifests"
[kubelet-check] Waiting for a healthy kubelet at http://127.0.0.1:10248/healthz. This can take up to 4m0s
[kubelet-check] The kubelet is healthy after 500.977478ms
[api-check] Waiting for a healthy API server. This can take up to 4m0s
[api-check] The API server is healthy after 11.652939705s
[upload-config] Storing the configuration used in ConfigMap "kubeadm-config" in the "kube-system" Namespace
[kubelet] Creating a ConfigMap "kubelet-config" in namespace kube-system with the configuration for the kubelets in the cluster
[upload-certs] Skipping phase. Please see --upload-certs
[mark-control-plane] Marking the node node as control-plane by adding the labels: [node-role.kubernetes.io/control-plane node.kubernetes.io/exclude-from-external-load-balancers]
[mark-control-plane] Marking the node node as control-plane by adding the taints [node-role.kubernetes.io/master:PreferNoSchedule]
[bootstrap-token] Using token: abcdef.0123456789abcdef
[bootstrap-token] Configuring bootstrap tokens, cluster-info ConfigMap, RBAC Roles
[bootstrap-token] Configured RBAC rules to allow Node Bootstrap tokens to get nodes
[bootstrap-token] Configured RBAC rules to allow Node Bootstrap tokens to post CSRs in order for nodes to get long term certificate credentials
[bootstrap-token] Configured RBAC rules to allow the csrapprover controller automatically approve CSRs from a Node Bootstrap Token
[bootstrap-token] Configured RBAC rules to allow certificate rotation for all node client certificates in the cluster
[bootstrap-token] Creating the "cluster-info" ConfigMap in the "kube-public" namespace
[kubelet-finalize] Updating "/etc/kubernetes/kubelet.conf" to point to a rotatable kubelet client certificate and key
[addons] Applied essential addon: CoreDNS
W0323 14:33:24.643627   15471 endpoint.go:57] [endpoint] WARNING: port specified in controlPlaneEndpoint overrides bindPort in the controlplane address
[addons] Applied essential addon: kube-proxy

Your Kubernetes control-plane has initialized successfully!

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/

You can now join any number of control-plane nodes by copying certificate authorities
and service account keys on each node and then running the following as root:

  kubeadm join 192.168.1.36:9443 --token abcdef.0123456789abcdef \
    --discovery-token-ca-cert-hash sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92 \
    --control-plane 

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

kubeadm join 192.168.1.36:9443 --token abcdef.0123456789abcdef \
    --discovery-token-ca-cert-hash sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92 
[root@k8s-master01 ~]# 



# 重新初始化

# 只有一個CRI的情況下
kubeadm reset
# 指定CRI重置
kubeadm reset --cri-socket unix:///var/run/cri-dockerd.sock
kubeadm reset --cri-socket unix:///var/run/containerd/containerd.sock

配置kubectl

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

配置證書

# 使用腳本將這如果你睡拷貝到其他maser節點
USER=root
CONTROL_PLANE_IPS="192.168.1.22 192.168.1.23"
for host in ${CONTROL_PLANE_IPS}; do
    scp /etc/kubernetes/pki/ca.crt "${USER}"@$host:
    scp /etc/kubernetes/pki/ca.key "${USER}"@$host:
    scp /etc/kubernetes/pki/sa.key "${USER}"@$host:
    scp /etc/kubernetes/pki/sa.pub "${USER}"@$host:
    scp /etc/kubernetes/pki/front-proxy-ca.crt "${USER}"@$host:
    scp /etc/kubernetes/pki/front-proxy-ca.key "${USER}"@$host:
    scp /etc/kubernetes/pki/etcd/ca.crt "${USER}"@$host:etcd-ca.crt
    # 如果你正使用外部 etcd,忽略下一行
    scp /etc/kubernetes/pki/etcd/ca.key "${USER}"@$host:etcd-ca.key
done

# 在其他的maser上面執行 ,將證書文件放入所需目錄
USER=root
mkdir -p /etc/kubernetes/pki/etcd
mv /${USER}/ca.crt /etc/kubernetes/pki/
mv /${USER}/ca.key /etc/kubernetes/pki/
mv /${USER}/sa.pub /etc/kubernetes/pki/
mv /${USER}/sa.key /etc/kubernetes/pki/
mv /${USER}/front-proxy-ca.crt /etc/kubernetes/pki/
mv /${USER}/front-proxy-ca.key /etc/kubernetes/pki/
mv /${USER}/etcd-ca.crt /etc/kubernetes/pki/etcd/ca.crt
# 如果你正使用外部 etcd,忽略下一行
mv /${USER}/etcd-ca.key /etc/kubernetes/pki/etcd/ca.key

初始化Master2


# 在maser02上執行操作,將加入控制節點
kubeadm config print join-defaults > kubeadm-join-master-02.yaml
cat > kubeadm-join-master-02.yaml << EOF
apiVersion: kubeadm.k8s.io/v1beta4
caCertPath: /etc/kubernetes/pki/ca.crt
discovery:
  bootstrapToken:
    apiServerEndpoint: 192.168.1.36:9443
    token: abcdef.0123456789abcdef
    caCertHashes:
    - "sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92"
    unsafeSkipCAVerification: true
  tlsBootstrapToken: abcdef.0123456789abcdef
kind: JoinConfiguration
controlPlane:
  localAPIEndpoint:
    advertiseAddress: "192.168.1.22"
    bindPort: 6443
nodeRegistration:
  # criSocket: unix:///run/containerd/containerd.sock
  criSocket: unix:///var/run/cri-dockerd.sock
  imagePullPolicy: IfNotPresent
  imagePullSerial: true
  name: k8s-master02
  taints:
  - effect: PreferNoSchedule
    key: node-role.kubernetes.io/master
  kubeletExtraArgs:
  - name: "node-ip"
    value: "192.168.1.22,fc00::22"
timeouts:
  controlPlaneComponentHealthCheck: 4m0s
  discovery: 5m0s
  etcdAPICall: 2m0s
  kubeletHealthCheck: 4m0s
  kubernetesAPICall: 1m0s
  tlsBootstrap: 5m0s
  upgradeManifests: 5m0s
EOF

kubeadm join --config=kubeadm-join-master-02.yaml

初始化Master3

# 在maser03上執行操作,將加入控制節點
kubeadm config print join-defaults > kubeadm-join-master-03.yaml
cat > kubeadm-join-master-03.yaml << EOF
apiVersion: kubeadm.k8s.io/v1beta4
caCertPath: /etc/kubernetes/pki/ca.crt
discovery:
  bootstrapToken:
    apiServerEndpoint: 192.168.1.36:9443
    token: abcdef.0123456789abcdef
    caCertHashes:
    - "sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92"
    unsafeSkipCAVerification: true
  tlsBootstrapToken: abcdef.0123456789abcdef
kind: JoinConfiguration
controlPlane:
  localAPIEndpoint:
    advertiseAddress: "192.168.1.23"
    bindPort: 6443
nodeRegistration:
  # criSocket: unix:///run/containerd/containerd.sock
  criSocket: unix:///var/run/cri-dockerd.sock
  imagePullPolicy: IfNotPresent
  imagePullSerial: true
  name: k8s-master03
  taints:
  - effect: PreferNoSchedule
    key: node-role.kubernetes.io/master
  kubeletExtraArgs:
  - name: "node-ip"
    value: "192.168.1.23,fc00::23"
timeouts:
  controlPlaneComponentHealthCheck: 4m0s
  discovery: 5m0s
  etcdAPICall: 2m0s
  kubeletHealthCheck: 4m0s
  kubernetesAPICall: 1m0s
  tlsBootstrap: 5m0s
  upgradeManifests: 5m0s
EOF

kubeadm join --config=kubeadm-join-master-03.yaml

初始化Node1

# 在node01上執行操作,將加入工作節點
kubeadm config print join-defaults > kubeadm-join-node-01.yaml
cat > kubeadm-join-node-01.yaml << EOF
apiVersion: kubeadm.k8s.io/v1beta4
caCertPath: /etc/kubernetes/pki/ca.crt
discovery:
  bootstrapToken:
    apiServerEndpoint: 192.168.1.36:9443
    token: abcdef.0123456789abcdef
    caCertHashes:
    - "sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92"
    unsafeSkipCAVerification: true
  tlsBootstrapToken: abcdef.0123456789abcdef
kind: JoinConfiguration
nodeRegistration:
  # criSocket: unix:///run/containerd/containerd.sock
  criSocket: unix:///var/run/cri-dockerd.sock
  imagePullPolicy: IfNotPresent
  imagePullSerial: true
  name: k8s-node01
  taints: null
  kubeletExtraArgs:
  - name: "node-ip"
    value: "192.168.1.24,fc00::24"
timeouts:
  controlPlaneComponentHealthCheck: 4m0s
  discovery: 5m0s
  etcdAPICall: 2m0s
  kubeletHealthCheck: 4m0s
  kubernetesAPICall: 1m0s
  tlsBootstrap: 5m0s
  upgradeManifests: 5m0s
EOF

kubeadm join --config=kubeadm-join-node-01.yaml

初始化Node2

# 在node02上執行操作,將加入工作節點
kubeadm config print join-defaults > kubeadm-join-node-02.yaml
cat > kubeadm-join-node-02.yaml << EOF
apiVersion: kubeadm.k8s.io/v1beta4
caCertPath: /etc/kubernetes/pki/ca.crt
discovery:
  bootstrapToken:
    apiServerEndpoint: 192.168.1.36:9443
    token: abcdef.0123456789abcdef
    caCertHashes:
    - "sha256:1a6196cd63edf4e78f39d34d448d6333d25e1ad0ff650839260fc7df25ec8a92"
    unsafeSkipCAVerification: true
  tlsBootstrapToken: abcdef.0123456789abcdef
kind: JoinConfiguration
nodeRegistration:
  # criSocket: unix:///run/containerd/containerd.sock
  criSocket: unix:///var/run/cri-dockerd.sock
  imagePullPolicy: IfNotPresent
  imagePullSerial: true
  name: k8s-node02
  taints: null
  kubeletExtraArgs:
  - name: "node-ip"
    value: "192.168.1.25,fc00::25"
timeouts:
  controlPlaneComponentHealthCheck: 4m0s
  discovery: 5m0s
  etcdAPICall: 2m0s
  kubeletHealthCheck: 4m0s
  kubernetesAPICall: 1m0s
  tlsBootstrap: 5m0s
  upgradeManifests: 5m0s
EOF

kubeadm join --config=kubeadm-join-node-02.yaml

查看集羣狀態

[root@k8s-master01 ~]# kubectl get nodes
NAME           STATUS     ROLES           AGE     VERSION
k8s-master01   NotReady   control-plane   3m56s   v1.32.3
k8s-master02   NotReady   control-plane   2m3s    v1.32.3
k8s-master03   NotReady   control-plane   40s     v1.32.3
k8s-node01     NotReady   <none>          8s      v1.32.3
k8s-node02     NotReady   <none>          5s      v1.32.3
[root@k8s-master01 ~]# 

安裝網絡插件

注意二選其一即可,建議在此處創建好快照後在進行操作,後續出問題可以回滾

centos7 要升級libseccomp 不然 無法安裝網絡插件

# https://github.com/opencontainers/runc/releases
# 升級runc
# wget https://mirrors.chenby.cn/https://github.com/opencontainers/runc/releases/download/v1.1.12/runc.amd64

install -m 755 runc.amd64 /usr/local/sbin/runc
cp -p /usr/local/sbin/runc  /usr/local/bin/runc
cp -p /usr/local/sbin/runc  /usr/bin/runc

#查看當前版本
[root@k8s-master-1 ~]# rpm -qa | grep libseccomp
libseccomp-2.5.2-2.el9.x86_64

#下載高於2.4以上的包
# yum -y install http://rpmfind.net/linux/centos/8-stream/BaseOS/x86_64/os/Packages/libseccomp-2.5.1-1.el8.x86_64.rpm
# 清華源
# yum -y install https://mirrors.tuna.tsinghua.edu.cn/centos/8-stream/BaseOS/x86_64/os/Packages/libseccomp-2.5.1-1.el8.x86_64.rpm

安裝Calico

更改calico網段


# 安裝operator
kubectl create -f https://mirrors.chenby.cn/https://raw.githubusercontent.com/projectcalico/calico/v3.29.2/manifests/tigera-operator.yaml


# 下載配置文件
curl https://mirrors.chenby.cn/https://raw.githubusercontent.com/projectcalico/calico/v3.29.2/manifests/custom-resources.yaml -O




# 修改地址池
vim custom-resources.yaml
apiVersion: operator.tigera.io/v1
kind: Installation
metadata:
  name: default
spec:
  calicoNetwork:
    ipPools:
    - name: default-ipv4-ippool
      blockSize: 26
      cidr: 172.16.0.0/12 
      encapsulation: VXLANCrossSubnet
      natOutgoing: Enabled
      nodeSelector: all()

---
apiVersion: operator.tigera.io/v1
kind: APIServer
metadata:
  name: default
spec: {}


# 執行安裝
kubectl create -f custom-resources.yaml



# 安裝客户端
curl -L https://mirrors.chenby.cn/https://github.com/projectcalico/calico/releases/download/v3.28.2/calicoctl-linux-amd64 -o calicoctl


# 給客户端添加執行權限
chmod +x ./calicoctl


# 查看集羣節點
./calicoctl get nodes
# 查看集羣節點狀態
./calicoctl node status
#查看地址池
./calicoctl get ipPool
./calicoctl get ipPool -o yaml

查看容器狀態

# calico 初始化會很慢 需要耐心等待一下,大約十分鐘左右
[root@k8s-master01 ~]# kubectl get pod -A | grep calico
NAMESPACE          NAME                                       READY   STATUS              RESTARTS   AGE
calico-apiserver   calico-apiserver-6c6d4589d6-hfzpg          1/1     Running             0          6m3s
calico-apiserver   calico-apiserver-6c6d4589d6-rs27g          1/1     Running             0          6m3s
calico-system      calico-kube-controllers-7cdf8468d9-9jc22   1/1     Running             0          6m3s
calico-system      calico-node-2qk9k                          1/1     Running             0          6m3s
calico-system      calico-node-755hv                          1/1     Running             0          6m3s
calico-system      calico-node-rncvq                          1/1     Running             0          6m3s
calico-system      calico-node-t694l                          1/1     Running             0          6m3s
calico-system      calico-node-txwr6                          1/1     Running             0          6m3s
calico-system      calico-typha-58c46dd757-8sn77              1/1     Running             0          6m3s
calico-system      calico-typha-58c46dd757-lsnkh              1/1     Running             0          5m57s
calico-system      calico-typha-58c46dd757-wpz64              1/1     Running             0          5m57s
calico-system      csi-node-driver-84xbq                      2/2     Running             0          6m3s
calico-system      csi-node-driver-gl8m7                      2/2     Running             0          6m3s
calico-system      csi-node-driver-lf4xp                      2/2     Running             0          6m3s
calico-system      csi-node-driver-mlwnf                      2/2     Running             0          6m3s
calico-system      csi-node-driver-pqpkb                      2/2     Running             0          6m3s

安裝cilium(推薦)

安裝helm

# [root@k8s-master01 ~]# curl -fsSL -o get_helm.sh https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3
# [root@k8s-master01 ~]# chmod 700 get_helm.sh
# [root@k8s-master01 ~]# ./get_helm.sh

wget https://mirrors.huaweicloud.com/helm/v3.17.2/helm-v3.17.2-linux-amd64.tar.gz
tar xvf helm-*-linux-amd64.tar.gz
cp linux-amd64/helm /usr/local/bin/

安裝cilium

# 添加源
helm repo add cilium https://helm.cilium.io

# 修改為國內源
helm pull cilium/cilium
tar xvf cilium-*.tgz
cd cilium/

# sed -i "s#quay.io/#quay.m.daocloud.io/#g" values.yaml

# 默認參數安裝
helm install  cilium ./cilium/ -n kube-system

# 啓用ipv6
# helm install cilium ./cilium/ --namespace kube-system --set ipv6.enabled=true

# 啓用路由信息和監控插件
# helm install cilium ./cilium/ --namespace kube-system --set ipv6.enabled=true --set hubble.relay.enabled=true --set hubble.ui.enabled=true --set prometheus.enabled=true --set operator.prometheus.enabled=true --set hubble.enabled=true --set hubble.metrics.enabled="{dns,drop,tcp,flow,port-distribution,icmp,http}" 

查看

[root@k8s-master01 ~]# kubectl  get pod -A | grep cil
NAMESPACE     NAME                               READY   STATUS    RESTARTS   AGE
kube-system   cilium-2tnfb                       1/1     Running   0          60s
kube-system   cilium-5tgcb                       1/1     Running   0          60s
kube-system   cilium-6shf5                       1/1     Running   0          60s
kube-system   cilium-ccbcx                       1/1     Running   0          60s
kube-system   cilium-cppft                       1/1     Running   0          60s
kube-system   cilium-operator-675f685d59-7q27q   1/1     Running   0          60s
kube-system   cilium-operator-675f685d59-kwmqz   1/1     Running   0          60s
[root@k8s-master01 ~]#

下載專屬監控面板

安裝時候沒有創建 監控可以忽略

[root@k8s-master01 yaml]# wget https://mirrors.chenby.cn/https://raw.githubusercontent.com/cilium/cilium/1.12.1/examples/kubernetes/addons/prometheus/monitoring-example.yaml

[root@k8s-master01 yaml]# sed -i "s#docker.io/#jockerhub.com/#g" monitoring-example.yaml

[root@k8s-master01 yaml]# kubectl  apply -f monitoring-example.yaml
namespace/cilium-monitoring created
serviceaccount/prometheus-k8s created
configmap/grafana-config created
configmap/grafana-cilium-dashboard created
configmap/grafana-cilium-operator-dashboard created
configmap/grafana-hubble-dashboard created
configmap/prometheus created
clusterrole.rbac.authorization.k8s.io/prometheus created
clusterrolebinding.rbac.authorization.k8s.io/prometheus created
service/grafana created
service/prometheus created
deployment.apps/grafana created
deployment.apps/prometheus created
[root@k8s-master01 yaml]#

修改為NodePort

安裝時候沒有創建 監控可以忽略

[root@k8s-master01 yaml]# kubectl  edit svc  -n kube-system hubble-ui
service/hubble-ui edited
[root@k8s-master01 yaml]#
[root@k8s-master01 yaml]# kubectl  edit svc  -n cilium-monitoring grafana
service/grafana edited
[root@k8s-master01 yaml]#
[root@k8s-master01 yaml]# kubectl  edit svc  -n cilium-monitoring prometheus
service/prometheus edited
[root@k8s-master01 yaml]#

type: NodePort

查看端口

安裝時候沒有創建 監控可以忽略

[root@k8s-master01 yaml]# kubectl get svc -A | grep NodePort
cilium-monitoring   grafana          NodePort    10.111.74.3      <none>        3000:32648/TCP   74s
cilium-monitoring   prometheus       NodePort    10.107.240.124   <none>        9090:30495/TCP   74s
kube-system         hubble-ui        NodePort    10.96.185.26     <none>        80:31568/TCP     99s

訪問

安裝時候沒有創建 監控可以忽略

http://192.168.1.31:32648
http://192.168.1.31:30495
http://192.168.1.31:31568

查看集羣

[root@k8s-master01 ~]# kubectl get node
NAME           STATUS   ROLES           AGE     VERSION
k8s-master01   Ready    control-plane   10m     v1.30.0
k8s-master02   Ready    control-plane   9m3s    v1.30.0
k8s-master03   Ready    control-plane   8m45s   v1.30.0
k8s-node01     Ready    <none>          8m34s   v1.30.0
k8s-node02     Ready    <none>          8m24s   v1.30.0
[root@k8s-master01 ~]# 
[root@k8s-master01 ~]# kubectl get pod -A
NAMESPACE     NAME                                   READY   STATUS    RESTARTS   AGE
kube-system   cilium-2vlhn                           1/1     Running   0          70s
kube-system   cilium-94pvm                           1/1     Running   0          70s
kube-system   cilium-dqllb                           1/1     Running   0          70s
kube-system   cilium-operator-84cc645cfd-nl286       1/1     Running   0          70s
kube-system   cilium-operator-84cc645cfd-v9lzh       1/1     Running   0          70s
kube-system   cilium-r649m                           1/1     Running   0          70s
kube-system   cilium-xhcb5                           1/1     Running   0          70s
kube-system   coredns-85c54ff74b-vgxbg               1/1     Running   0          27s
kube-system   coredns-85c54ff74b-zvr67               1/1     Running   0          42s
kube-system   etcd-k8s-master01                      1/1     Running   0          20m
kube-system   etcd-k8s-master02                      1/1     Running   0          8m20s
kube-system   etcd-k8s-master03                      1/1     Running   0          11m
kube-system   kube-apiserver-k8s-master01            1/1     Running   0          20m
kube-system   kube-apiserver-k8s-master02            1/1     Running   0          8m20s
kube-system   kube-apiserver-k8s-master03            1/1     Running   0          11m
kube-system   kube-controller-manager-k8s-master01   1/1     Running   0          20m
kube-system   kube-controller-manager-k8s-master02   1/1     Running   0          8m20s
kube-system   kube-controller-manager-k8s-master03   1/1     Running   0          11m
kube-system   kube-proxy-6bd4n                       1/1     Running   0          11m
kube-system   kube-proxy-77w24                       1/1     Running   0          8m26s
kube-system   kube-proxy-9d5m8                       1/1     Running   0          12m
kube-system   kube-proxy-jxcrx                       1/1     Running   0          20m
kube-system   kube-proxy-vr5w9                       1/1     Running   0          11m
kube-system   kube-scheduler-k8s-master01            1/1     Running   0          20m
kube-system   kube-scheduler-k8s-master02            1/1     Running   0          8m20s
kube-system   kube-scheduler-k8s-master03            1/1     Running   0          11m

集羣驗證

部署pod資源

cat<<EOF | kubectl apply -f -
apiVersion: v1
kind: Pod
metadata:
  name: busybox
  namespace: default
spec:
  containers:
  - name: busybox
    image: docker.m.daocloud.io/library/busybox:1.28
    command:
      - sleep
      - "3600"
    imagePullPolicy: IfNotPresent
  restartPolicy: Always
EOF

# 查看
kubectl  get pod
NAME      READY   STATUS    RESTARTS   AGE
busybox   1/1     Running   0          17s

用pod解析默認命名空間中的kubernetes

# 查看name
kubectl get svc
NAME         TYPE        CLUSTER-IP   EXTERNAL-IP   PORT(S)   AGE
kubernetes   ClusterIP   10.96.0.1    <none>        443/TCP   17h

# 進行解析
kubectl exec  busybox -n default -- nslookup kubernetes
3Server:    10.96.0.10
Address 1: 10.96.0.10 kube-dns.kube-system.svc.cluster.local

Name:      kubernetes
Address 1: 10.96.0.1 kubernetes.default.svc.cluster.local

測試跨命名空間是否可以解析

# 查看有那些name
kubectl  get svc -A
NAMESPACE     NAME             TYPE        CLUSTER-IP      EXTERNAL-IP   PORT(S)                  AGE
default       kubernetes       ClusterIP   10.96.0.1       <none>        443/TCP                  7m12s
kube-system   cilium-envoy     ClusterIP   None            <none>        9964/TCP                 3m31s
kube-system   hubble-peer      ClusterIP   10.96.247.148   <none>        443/TCP                  3m31s
kube-system   kube-dns         ClusterIP   10.96.0.10      <none>        53/UDP,53/TCP,9153/TCP   6m58s
kube-system   metrics-server   ClusterIP   10.96.18.184    <none>        443/TCP                  94s


# 進行解析
kubectl exec  busybox -n default -- nslookup kube-dns.kube-system
Server:    10.96.0.10
Address 1: 10.96.0.10 kube-dns.kube-system.svc.cluster.local

Name:      kube-dns.kube-system
Address 1: 10.96.0.10 kube-dns.kube-system.svc.cluster.local
[root@k8s-master01 metrics-server]# 

每個節點都必須要能訪問Kubernetes的kubernetes svc 443和kube-dns的service 53

telnet 10.96.0.1 443
Trying 10.96.0.1...
Connected to 10.96.0.1.
Escape character is '^]'.

telnet 10.96.0.10 53
Trying 10.96.0.10...
Connected to 10.96.0.10.
Escape character is '^]'.

curl 10.96.0.10:53
curl: (52) Empty reply from server

Pod和Pod之前要能通

kubectl get po -owide
NAME      READY   STATUS    RESTARTS   AGE   IP              NODE         NOMINATED NODE   READINESS GATES
busybox   1/1     Running   0          17m   172.27.14.193   k8s-node02   <none>           <none>

kubectl get po -n kube-system -owide
NAME                                       READY   STATUS    RESTARTS   AGE     IP               NODE           NOMINATED NODE   READINESS GATES
calico-kube-controllers-76754ff848-pw4xg   1/1     Running   0          38m     172.25.244.193   k8s-master01   <none>           <none>
calico-node-97m55                          1/1     Running   0          38m     192.168.1.34     k8s-node01     <none>           <none>
calico-node-hlz7j                          1/1     Running   0          38m     192.168.1.32     k8s-master02   <none>           <none>
calico-node-jtlck                          1/1     Running   0          38m     192.168.1.33     k8s-master03   <none>           <none>
calico-node-lxfkf                          1/1     Running   0          38m     192.168.1.35     k8s-node02     <none>           <none>
calico-node-t667x                          1/1     Running   0          38m     192.168.1.31     k8s-master01   <none>           <none>
calico-typha-59d75c5dd4-gbhfp              1/1     Running   0          38m     192.168.1.35     k8s-node02     <none>           <none>
coredns-coredns-c5c6d4d9b-bd829            1/1     Running   0          10m     172.25.92.65     k8s-master02   <none>           <none>
metrics-server-7c8b55c754-w7q8v            1/1     Running   0          3m56s   172.17.125.3     k8s-node01     <none>           <none>

# 進入busybox ping其他節點上的pod

kubectl exec -ti busybox -- sh
/ # ping 192.168.1.23
PING 192.168.1.23 (192.168.1.23): 56 data bytes
64 bytes from 192.168.1.23: seq=0 ttl=62 time=0.494 ms
64 bytes from 192.168.1.23: seq=1 ttl=62 time=0.342 ms
64 bytes from 192.168.1.23: seq=2 ttl=62 time=0.335 ms

# 可以連通證明這個pod是可以跨命名空間和跨主機通信的

創建三個副本,可以看到3個副本分佈在不同的節點上(用完可以刪了)

cat<<EOF | kubectl apply -f -
apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
  labels:
    app: nginx
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx
        ports:
        - containerPort: 80
EOF

kubectl  get pod 
NAME                               READY   STATUS    RESTARTS   AGE
busybox                            1/1     Running   0          6m25s
nginx-deployment-9456bbbf9-4bmvk   1/1     Running   0          8s
nginx-deployment-9456bbbf9-9rcdk   1/1     Running   0          8s
nginx-deployment-9456bbbf9-dqv8s   1/1     Running   0          8s

# 刪除nginx
[root@k8s-master01 ~]# kubectl delete deployments nginx-deployment 

安裝dashboard

# 添加源信息
helm repo add kubernetes-dashboard https://kubernetes.github.io/dashboard/


# 修改為國內源
helm pull kubernetes-dashboard/kubernetes-dashboard
tar xvf kubernetes-dashboard-*.tgz
cd kubernetes-dashboard
sed -i "s#docker.io/#jockerhub.com/#g" values.yaml

# 默認參數安裝
helm upgrade --install kubernetes-dashboard ./kubernetes-dashboard/  --create-namespace --namespace kube-system


# 我的集羣使用默認參數安裝 kubernetes-dashboard-kong 出現異常 8444 端口占用
# 使用下面的命令進行安裝,在安裝時關閉kong.tls功能
helm upgrade --install kubernetes-dashboard ./kubernetes-dashboard/ --namespace kube-system --set kong.admin.tls.enabled=false

更改dashboard的svc為NodePort,如果已是請忽略

kubectl edit svc  -n kube-system kubernetes-dashboard-kong-proxy
  type: NodePort

查看端口號

[root@k8s-master01 ~]# kubectl get svc kubernetes-dashboard-kong-proxy -n kube-system
NAME                              TYPE       CLUSTER-IP     EXTERNAL-IP   PORT(S)         AGE
kubernetes-dashboard-kong-proxy   NodePort   10.96.247.74   <none>        443:31495/TCP   2m29s
[root@k8s-master01 ~]# 

創建token

cat > dashboard-user.yaml << EOF
apiVersion: v1
kind: ServiceAccount
metadata:
  name: admin-user
  namespace: kube-system
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: admin-user
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: cluster-admin
subjects:
- kind: ServiceAccount
  name: admin-user
  namespace: kube-system
EOF

kubectl  apply -f dashboard-user.yaml

# 創建token
kubectl -n kube-system create token admin-user
eyJhbGciOiJSUzI1NiIsImtpZCI6IjVWNTNJSGFsNDhTLU1TNDVEZkZmeUlkbFpaUEVsVU8yOXZqQjJ0Rmk0eGcifQ.eyJhdWQiOlsiaHR0cHM6Ly9rdWJlcm5ldGVzLmRlZmF1bHQuc3ZjLmNsdXN0ZXIubG9jYWwiXSwiZXhwIjoxNzQyNzIyNTIxLCJpYXQiOjE3NDI3MTg5MjEsImlzcyI6Imh0dHBzOi8va3ViZXJuZXRlcy5kZWZhdWx0LnN2Yy5jbHVzdGVyLmxvY2FsIiwianRpIjoiMjJkZjBiODYtNTQwNS00ZGMwLThjMjgtOTlhM2RiODhjZjMzIiwia3ViZXJuZXRlcy5pbyI6eyJuYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsInNlcnZpY2VhY2NvdW50Ijp7Im5hbWUiOiJhZG1pbi11c2VyIiwidWlkIjoiNzBiMTI1MjEtNjJkMC00ZTA3LTkzNDYtM2IyYWYxMDY5MmUzIn19LCJuYmYiOjE3NDI3MTg5MjEsInN1YiI6InN5c3RlbTpzZXJ2aWNlYWNjb3VudDprdWJlLXN5c3RlbTphZG1pbi11c2VyIn0.OWIO-PR9EQ4ZUwmtKRQtzdhV4ycESyF6viDFR8yhnT3u9fB8QkSD5dA7pxp6zt_e-bHFU0nxz5DiHgy6xQmxW-6nhtviRk0KkXaQHGHdlo5TrcRTuE1zwAclPsPvuEhuF7z-IIemSy6CrBi_P_nRyeQSFKN_GhVz3-frgMHHkb6rV8HxGp1kIL2z2FakB-72XfhXRb--4lf41PfGMaMCOvPTYy4YhBkwtUKFPzQ3Ixr80naiFp4I2_M5mlnuNu_xHvIWl43zXTrvnrMZchqor9vLjrQcPcPzd6GH_YJcsCOLq4i1Qp2M6TwvbMa1Zd-kZHokIrEc8TCdiALIbS_2cg

創建長期token

cat > dashboard-user-token.yaml << EOF
apiVersion: v1
kind: Secret
metadata:
  name: admin-user
  namespace: kube-system
  annotations:
    kubernetes.io/service-account.name: "admin-user"   
type: kubernetes.io/service-account-token  
EOF

kubectl  apply -f dashboard-user-token.yaml

# 查看密碼
kubectl get secret admin-user -n kube-system -o jsonpath={".data.token"} | base64 -d

eyJhbGciOiJSUzI1NiIsImtpZCI6IjVWNTNJSGFsNDhTLU1TNDVEZkZmeUlkbFpaUEVsVU8yOXZqQjJ0Rmk0eGcifQ.eyJpc3MiOiJrdWJlcm5ldGVzL3NlcnZpY2VhY2NvdW50Iiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9uYW1lc3BhY2UiOiJrdWJlLXN5c3RlbSIsImt1YmVybmV0ZXMuaW8vc2VydmljZWFjY291bnQvc2VjcmV0Lm5hbWUiOiJhZG1pbi11c2VyIiwia3ViZXJuZXRlcy5pby9zZXJ2aWNlYWNjb3VudC9zZXJ2aWNlLWFjY291bnQubmFtZSI6ImFkbWluLXVzZXIiLCJrdWJlcm5ldGVzLmlvL3NlcnZpY2VhY2NvdW50L3NlcnZpY2UtYWNjb3VudC51aWQiOiI3MGIxMjUyMS02MmQwLTRlMDctOTM0Ni0zYjJhZjEwNjkyZTMiLCJzdWIiOiJzeXN0ZW06c2VydmljZWFjY291bnQ6a3ViZS1zeXN0ZW06YWRtaW4tdXNlciJ9.CWJmVeh3f0LHFqM7BXeMYytVN0tWITgVwCifDX8EqL_CkB7L0sZKzr35UgoB7_ByutpAAx7rN57wme1Kg3kHbXJGT5_C3biUhYX8o665QKDMYXjeWE8hBQb6hPS6S5GrZ8srmv4lOHNeso3q1X1znvm5Pe987Y74b4PMiTQZ0JzlapYCQSVgda6kxgaff-jwmF3uW_E8Le2DydLBRwILRtiQxUX3wMtMM9u_RgmqB1zKvQymm-EDPPYouEruz_8bbrXbMTgAqML7PydeXqB8Cd_t8Xiv2A19wd4VkLH1E-eN6esRSR2nCLsJn6vQfRV--mH1OH-DR6LCd4yUsDnqaQ

登錄dashboard

https://192.168.1.21:31495/

ingress安裝

執行部署

wget https://mirrors.chenby.cn/https://raw.githubusercontent.com/kubernetes/ingress-nginx/main/deploy/static/provider/cloud/deploy.yaml -O ingress.yaml

# 修改為國內源 docker源可選
sed -i "s#registry.k8s.io/ingress-nginx/#registry.aliyuncs.com/chenby/#g" ingress.yaml

cat > ingress-backend.yaml << EOF
apiVersion: apps/v1
kind: Deployment
metadata:
  name: default-http-backend
  labels:
    app.kubernetes.io/name: default-http-backend
  namespace: kube-system
spec:
  replicas: 1
  selector:
    matchLabels:
      app.kubernetes.io/name: default-http-backend
  template:
    metadata:
      labels:
        app.kubernetes.io/name: default-http-backend
    spec:
      terminationGracePeriodSeconds: 60
      containers:
      - name: default-http-backend
        image: registry.cn-hangzhou.aliyuncs.com/chenby/defaultbackend-amd64:1.5 
        livenessProbe:
          httpGet:
            path: /healthz
            port: 8080
            scheme: HTTP
          initialDelaySeconds: 30
          timeoutSeconds: 5
        ports:
        - containerPort: 8080
        resources:
          limits:
            cpu: 10m
            memory: 20Mi
          requests:
            cpu: 10m
            memory: 20Mi
---
apiVersion: v1
kind: Service
metadata:
  name: default-http-backend
  namespace: kube-system
  labels:
    app.kubernetes.io/name: default-http-backend
spec:
  ports:
  - port: 80
    targetPort: 8080
  selector:
    app.kubernetes.io/name: default-http-backend
EOF

kubectl  apply -f ingress.yaml 
kubectl  apply -f ingress-backend.yaml 


cat > ingress-demo-app.yaml << EOF
apiVersion: apps/v1
kind: Deployment
metadata:
  name: hello-server
spec:
  replicas: 2
  selector:
    matchLabels:
      app: hello-server
  template:
    metadata:
      labels:
        app: hello-server
    spec:
      containers:
      - name: hello-server
        image: registry.cn-hangzhou.aliyuncs.com/lfy_k8s_images/hello-server
        ports:
        - containerPort: 9000
---
apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: nginx-demo
  name: nginx-demo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: nginx-demo
  template:
    metadata:
      labels:
        app: nginx-demo
    spec:
      containers:
      - image: nginx
        name: nginx
---
apiVersion: v1
kind: Service
metadata:
  labels:
    app: nginx-demo
  name: nginx-demo
spec:
  selector:
    app: nginx-demo
  ports:
  - port: 8000
    protocol: TCP
    targetPort: 80
---
apiVersion: v1
kind: Service
metadata:
  labels:
    app: hello-server
  name: hello-server
spec:
  selector:
    app: hello-server
  ports:
  - port: 8000
    protocol: TCP
    targetPort: 9000
---
apiVersion: networking.k8s.io/v1
kind: Ingress  
metadata:
  name: ingress-host-bar
spec:
  ingressClassName: nginx
  rules:
  - host: "hello.chenby.cn"
    http:
      paths:
      - pathType: Prefix
        path: "/"
        backend:
          service:
            name: hello-server
            port:
              number: 8000
  - host: "demo.chenby.cn"
    http:
      paths:
      - pathType: Prefix
        path: "/nginx"  
        backend:
          service:
            name: nginx-demo
            port:
              number: 8000
EOF

# 等創建完成後在執行:
kubectl  apply -f ingress-demo-app.yaml 

kubectl  get ingress
NAME               CLASS   HOSTS                            ADDRESS     PORTS   AGE
ingress-host-bar   nginx   hello.chenby.cn,demo.chenby.cn   192.168.1.32   80      7s

過濾查看ingress端口

# 修改為nodeport
kubectl edit svc -n ingress-nginx   ingress-nginx-controller
type: NodePort

[root@hello ~/yaml]# kubectl  get svc -A | grep ingress
ingress-nginx          ingress-nginx-controller             NodePort    10.104.231.36    <none>        80:32636/TCP,443:30579/TCP   104s
ingress-nginx          ingress-nginx-controller-admission   ClusterIP   10.101.85.88     <none>        443/TCP                      105s
[root@hello ~/yaml]#

IPv6測試

#部署應用

cat<<EOF | kubectl apply -f -
apiVersion: apps/v1
kind: Deployment
metadata:
  name: chenby
spec:
  replicas: 1
  selector:
    matchLabels:
      app: chenby
  template:
    metadata:
      labels:
        app: chenby
    spec:
      hostNetwork: true
      containers:
      - name: chenby
        image: docker.io/library/nginx
        resources:
          limits:
            memory: "128Mi"
            cpu: "500m"
        ports:
        - containerPort: 80
---
apiVersion: v1
kind: Service
metadata:
  name: chenby
spec:
  ipFamilyPolicy: PreferDualStack
  ipFamilies:
  - IPv6
  - IPv4
  type: NodePort
  selector:
    app: chenby
  ports:
  - port: 80
    targetPort: 80
EOF


#查看端口
[root@k8s-master01 ~]# kubectl  get svc
NAME           TYPE        CLUSTER-IP            EXTERNAL-IP   PORT(S)        AGE
chenby         NodePort    fd00:1111::7c07       <none>        80:32386/TCP   5s
[root@k8s-master01 ~]# 

# 直接訪問POD地址
[root@k8s-master01 ~]# curl -I http://[fd00:1111::7c07]
HTTP/1.1 200 OK
Server: nginx/1.27.3
Date: Sun, 15 Dec 2024 10:56:49 GMT
Content-Type: text/html
Content-Length: 615
Last-Modified: Tue, 26 Nov 2024 15:55:00 GMT
Connection: keep-alive
ETag: "6745ef54-267"
Accept-Ranges: bytes


# 使用IPv4地址訪問測試
[root@k8s-master01 ~]# curl -I http://192.168.1.21:32386
HTTP/1.1 200 OK
Server: nginx/1.21.6
Date: Thu, 05 May 2022 10:20:59 GMT
Content-Type: text/html
Content-Length: 615
Last-Modified: Tue, 25 Jan 2022 15:03:52 GMT
Connection: keep-alive
ETag: "61f01158-267"
Accept-Ranges: bytes

# 使用主機的內網IPv6地址測試
[root@k8s-master01 ~]# curl -I http://[fc00::21]:32386
HTTP/1.1 200 OK
Server: nginx/1.21.6
Date: Thu, 05 May 2022 10:20:54 GMT
Content-Type: text/html
Content-Length: 615
Last-Modified: Tue, 25 Jan 2022 15:03:52 GMT
Connection: keep-alive
ETag: "61f01158-267"
Accept-Ranges: bytes

# 使用主機的公網IPv6地址測試
[root@k8s-master01 ~]# curl -I http://[2408:822a:736:c0d1::bad]:32386
HTTP/1.1 200 OK
Server: nginx/1.27.3
Date: Sun, 15 Dec 2024 10:54:16 GMT
Content-Type: text/html
Content-Length: 615
Last-Modified: Tue, 26 Nov 2024 15:55:00 GMT
Connection: keep-alive
ETag: "6745ef54-267"
Accept-Ranges: bytes

污點

# 查看當前污點狀態
[root@k8s-master01 ~]# kubectl describe node  | grep Taints
Taints:             node-role.kubernetes.io/master:PreferNoSchedule
Taints:             node-role.kubernetes.io/master:PreferNoSchedule
Taints:             node-role.kubernetes.io/master:PreferNoSchedule
Taints:             <none>
Taints:             <none>

# 設置污點 禁止調度 同時進行驅趕現有的POD
kubectl taint nodes k8s-master01 key1=value1:NoExecute
kubectl taint nodes k8s-master02 key1=value1:NoExecute
kubectl taint nodes k8s-master03 key1=value1:NoExecute

# 取消污點
kubectl taint nodes k8s-master01 key1=value1:NoExecute-
kubectl taint nodes k8s-master02 key1=value1:NoExecute-
kubectl taint nodes k8s-master03 key1=value1:NoExecute-

# 設置污點 禁止調度 不進行驅趕現有的POD
kubectl taint nodes k8s-master01 key1=value1:NoSchedule
kubectl taint nodes k8s-master02 key1=value1:NoSchedule
kubectl taint nodes k8s-master03 key1=value1:NoSchedule

# 取消污點
kubectl taint nodes k8s-master01 key1=value1:NoSchedule-
kubectl taint nodes k8s-master02 key1=value1:NoSchedule-
kubectl taint nodes k8s-master03 key1=value1:NoSchedule-

安裝命令行自動補全功能

yum install bash-completion -y
source /usr/share/bash-completion/bash_completion
source <(kubectl completion bash)
echo "source <(kubectl completion bash)" >> ~/.bashrc

附錄

# 鏡像加速器可以使用DaoCloud倉庫,替換規則如下

# 鏡像版本要自行查看,因為鏡像版本是隨時更新的,文檔無法做到實時更新

# docker pull 鏡像

docker pull registry.cn-hangzhou.aliyuncs.com/chenby/cni:master 

# docker 保存鏡像
docker save registry.cn-hangzhou.aliyuncs.com/chenby/cni:master -o cni.tar 

# 傳輸到各個節點
for NODE in k8s-master01 k8s-master02 k8s-master03 k8s-node01 k8s-node02; do scp -r images/  $NODE:/root/ ; done

# 創建命名空間
ctr ns create k8s.io
# 導入鏡像
ctr --namespace k8s.io image import images/cni.tar

# pull tar包 解壓後
helm pull cilium/cilium

# 查看鏡像版本
root@hello:~/cilium# cat values.yaml| grep tag: -C1
  repository: "quay.io/cilium/cilium"
  tag: "v1.12.6"
  pullPolicy: "IfNotPresent"
--
    repository: "quay.io/cilium/certgen"
    tag: "v0.1.8@sha256:4a456552a5f192992a6edcec2febb1c54870d665173a33dc7d876129b199ddbd"
    pullPolicy: "IfNotPresent"
--
      repository: "quay.io/cilium/hubble-relay"
      tag: "v1.12.6"
       # hubble-relay-digest

關於

https://www.oiox.cn/

https://www.oiox.cn/index.php/start-page.html

CSDN、GitHub、知乎、開源中國、思否、掘金、簡書、華為雲、阿里雲、騰訊雲、嗶哩嗶哩、今日頭條、新浪微博、個人博客

全網可搜《小陳運維》

user avatar coulthard Avatar wujingquan Avatar sysin Avatar waluna Avatar fanudekaixinguo Avatar mingtiaoiv Avatar phpercode Avatar leixue Avatar zhangfeidezhu Avatar tangzhangming Avatar yujiaao Avatar junxiudetuoba Avatar
Favorites 16 users favorite the story!
Favorites

Add a new Comments

Some HTML is okay.