@cdmonkey
2023-08-11T13:52:36.000000Z
字数 13246
阅读 149
Kubernetes
https://kubernetes.feisky.xyz/components/federation.html
http://rootsongjc.github.io/blogs/kubernetes-installation-on-centos
Binary: https://www.kubernetes.org.cn/4963.html
慕课网:
说明:
若是使用 kubeadm
工具进行部署,通常就是将功能部件部署为守护进程。
使用 kubeadm
进行安装,其优点是优雅、简单、支持高可用及升级方便;缺点是不易维护、文档简陋。
# /etc/hosts
172.16.142.51 k8s-master01
172.16.142.52 k8s-master02
172.16.142.53 k8s-master03
172.16.142.54 k8s-node01
172.16.142.55 k8s-node02
172.16.198.180 k8s-master-lb # 若不是高可用部署,则这个IP为 k8s-master01 IP地址
安装一些必要软件包:
yum install -y conntrack ipvsadm ipset jq sysstat curl iptables libseccomp net-tools telnet yum-utils \
device-mapper-persistent-data lvm2
所有主机上要关闭防火墙、NetworkManager、SELinux,禁用 swap 设备,并设置时间同步(必须要同步)。还要配置好 Hosts 文件,使得相互间能够识别主机名。另外不允许运行其他一切 DNS 服务。
setenforce 0
sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/selinux/config
sed -i 's#SELINUX=enforcing#SELINUX=disabled#g' /etc/sysconfig/selinux
# 其实这两个文件是同一个文件:
[root@k8s-node01 ~]# ll /etc/sysconfig/selinux
lrwxrwxrwx. 1 root root 17 Apr 21 2021 /etc/sysconfig/selinux -> ../selinux/config
关闭当前已启用的所有交换分区设备:
[root@k8s-master01 ~]# swapoff -a && sysctl -w vm.swappiness=0
[root@k8s-master01 ~]# free -m
total used free shared buff/cache available
Mem: 3951 108 3486 16 356 3595
Swap: 0 0 0
# 而后编辑 fstab 配置文件,注释掉用于挂载Swap设备的配置行:
[root@k8s-master01 ~]# sed -i '/swap/s/^\(.*\)$/#\1/g' /etc/fstab
systemctl stop firewalld && systemctl disable firewalld
# 清空防火墙规则:
iptables -F && iptables -X && iptables -F -t nat && iptables -X -t nat && iptables -P FORWARD ACCEPT
其他一些需要关闭并禁用的:
systemctl disable --now dnsmasq
systemctl disable --now firewalld
systemctl disable --now NetworkManager
注意:某些公有云需要使用 NetworkManager,若是这样就不要关闭。
若是要使用 ipvs 模型的 proxy,各个节点内核还需要载入 ipvs 相关各模块,否则只能使用 iptables。
必要软件包前面已经安装了。
所有节点配置 ipvs 模块:
cat > /etc/sysconfig/modules/ipvs.modules <<EOF
#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_wrr
modprobe -- ip_vs_sh
modprobe -- nf_conntrack
EOF
chmod 755 /etc/sysconfig/modules/ipvs.modules # 配置权限
bash /etc/sysconfig/modules/ipvs.modules # 载入模块
lsmod | grep -e ip_vs -e nf_conntrack # 检查模块载入情况
说明:若内核版本是
4.19
,则nf_conntrack_ipv4
变为了nf_conntrack
。
这一步我感觉并非必须。
cat > /etc/sysctl.d/kubernetes.conf <<EOF
net.bridge.bridge-nf-call-iptables=1
net.bridge.bridge-nf-call-ip6tables=1
net.ipv4.ip_forward=1
vm.swappiness=0
vm.overcommit_memory=1
vm.panic_on_oom=0
fs.inotify.max_user_watches=89100
EOF
# 生效配置文件:
sysctl -p /etc/sysctl.d/kubernetes.conf
前面两行是打开 Iptables 内生之桥接相关功能(干啥用的?)
若是有下面这个报错:
sysctl: cannot stat /proc/sys/net/bridge/bridge-nf-call-iptables: No such file or directory
sysctl: cannot stat /proc/sys/net/bridge/bridge-nf-call-ip6tables: No such file or directory
请执行:
modprobe br_netfilter
所有节点配置完内核后,重启服务器,保证重启后内核依旧载入。
reboot
lsmod | grep --color=auto -e ip_vs -e nf_conntrack
最后就是要配置软件源。除了普通的软件源及 epel 源外,还需要配置 docker、kubernetes 源。
# 首先是 docker 仓库:
wget https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo -O /etc/yum.repos.d/docker-ce.repo
# 而后还要手工生成 kubernetes 仓库配置文件:
cat <<EOF > /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=Kubernetes
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64/
enabled=1
gpgcheck=1
repo_gpgcheck=1
gpgkey=https://mirrors.aliyun.com/kubernetes/yum/doc/yum-key.gpg https://mirrors.aliyun.com/kubernetes/yum/doc/rpm-package-key.gpg
EOF
另外,可配置 Master01 免密登录其他主机,安装过程中生成配置文件及证书均于这台机器上进行,集群管理同样是于这台机器上进行。阿里云及 AWS 上通常都需要一台单独 kubectl 服务器。
[root@k8s-master01 ~]# ssh-keygen -t rsa
for i in k8s-master01 k8s-master02 k8s-master03 k8s-node01 k8s-node02; do ssh-copy-id -i ~/.ssh/id_rsa.pub root@$i;done
首先对除内核以外的进行升级:
# 暂时先不对内核进行升级。CentOS7 建议升级,而 CentOS8 可按需进行
yum update -y --exclude=kernel* && reboot
# 升级完成后查看系统版本:
[root@k8s-node02 ~]# cat /etc/redhat-release
CentOS Linux release 7.9.2009 (Core)
从大量生产实践看,一定要升级至 4.18 及其更高版本。这里我们升级至 4.19。
RPM 包下载地址:https://elrepo.org/linux/kernel
归档版本下载:https://www.kernel.org
能够看到,共涉及三个网段。实验中 Node network 使用了 172.16.142.0/24
这个段。
首先于所有节点上安装 Docker,安装前要确定 Kubernetes 版本及 Docker 版本。
要怎样确定 Kubernetes 版本及其需要使用之 Docker 版本呢?通常可查阅其源码更新日志:
https://github.com/kubernetes/kubernetes/tree/master/CHANGELOG
目前,1.18
版本更新日志中并未提及相关 docker 版本信息,但是 1.17
更新日志中有提及(于日志页面中直接搜索 docker):
Update the latest validated version of Docker to 19.03 (#84476, @neolit123)
因而这里使用了最新的 Kubernetes 1.18.7,而 Docker 版本需要选择 19.03。
# 查看可安装 docker 版本:
yum list docker-ce.x86_64 --showduplicates | sort -r
Loading mirror speeds from cached hostfile
Loaded plugins: fastestmirror
Installed Packages
...
docker-ce.x86_64 3:19.03.12-3.el7 docker-ce-stable
...
能够看到,最新版本就是 19.03
,因而直接安装就行了:
yum install -y docker-ce docker-ce-selinux
# Package docker-ce-selinux is obsoleted by docker-ce, trying to install 3:docker-ce-19.03.12-3.el7.x86_64 instead
# 因而直接执行下面这个指令就行:
yum install -y docker-ce
若是要安装指定版本,可使用命令:
# 注意: 版本号不包含冒号 : 与之前的数字
yum install -y --setopt=obsoletes=0 docker-ce-19.03.12-3.el7
最后于所有节点上安装三个集群必要工具:kubeadm、kubelet、kubectl
# 找到要安装的版本号:
yum list kubeadm --showduplicates | sort -r
# 安装指定版本,这里用的是 1.18.6
yum install -y kubeadm-1.18.6-0 kubelet-1.18.6-0 kubectl-1.18.6-0 --disableexcludes=kubernetes
# 若不指定版本,直接进行安装就行:
yum install -y kubeadm kubelet kubectl
# 其实只安装 kubeadm 就行,其他两个工具会作为依赖一并安装:
yum install -y kubeadm
# kubeadm: 部署集群用的命令
# kubelet: 于集群中每台机器上都要运行的组件,负责管理pod、容器生命周期
# kubectl: 集群管理工具。可选,只要于控制集群之节点上安装即可
目前看,
kubeadm
版本对应着所要安装的 Kubernetes 版本。——错误!
需要于所有节点上把 docker 服务启动起来。启动前,有些启动参数最好是配置上,但是属于可选操作。
# graph: 设置数据目录:选择比较大的分区。缺省为 /var/lib/docker
# exec-opts: 设置Cgroup driver。缺省是cgroupfs,推荐设置为systemd
# The recommended driver is "systemd". Please follow the guide at https://kubernetes.io/docs/setup/cri/
mkdir -pv /etc/docker
cat <<EOF > /etc/docker/daemon.json
{
"data-root": "/docker/data/path",
"registry-mirrors": [
"https://ip0q6hqs.mirror.aliyuncs.com"
],
"insecure-registries": ["0.0.0.0/0"],
"exec-opts": ["native.cgroupdriver=systemd"]
}
EOF
关于缺省存储路径配置,需要注意:
# docker 17.03.2 以前配置为 graph
# docker 17.04.x 以后配置为 data-root
根据 CRI installation 文档中的内容:
对于使用 systemd 作为 Init 的 Linux 发行版,使用 systemd 作为 docker 的 cgroup 驱动能够确保服务器节点于资源紧张之情况下更为稳定,因而这里修改各个节点 cgroup 驱动为 systemd。
若要通过默认 k8s.gcr.io 镜像仓库获得 K8s 系统组件相关镜像,需要于 docker Unit File 中指定代理信息:
# 这一步不执行目前没啥问题。
[root@k8s-master ~]# vim /usr/lib/systemd/system/docker.service
Environment="HTTPS_PROXY=PROTOCOL://HOST:PORT"
Environment="NO_PROXY=172.20.0.0/16,127.0.0.0/8"
老师曰:一旦使用了代理,则加速就没有必要了。
# 请于 [Service] 配置中 ExecStart=/usr/bin/dockerd 这一行后面新增一行:
# 这样能够使得 FORWARD 链其缺省策略重新设为 ACCEPT
ExecStartPost=/usr/sbin/iptables -P FORWARD ACCEPT
最后启动服务,并且使其开机自启动:
[root@k8s-master ~]# systemctl daemon-reload
[root@k8s-master ~]# systemctl start docker
[root@k8s-master ~]# systemctl enable docker
注意:这部分操作需要于 Master 节点上执行。同时还要了解 Master 上需要安装的控制平面组件:
kube-apiserver
kube-scheduler 作用是调度 pods 分配到那个 node 里,简单来说就是资源调度。
kube-controller-manager
关于 kubeadm
工具,请参见:
https://kubernetes.io/zh/docs/reference/setup-tools/kubeadm/kubeadm
首先可查看一下缺省初始化配置信息:
[root@k8s-master ~]# kubeadm config print init-defaults
...
imageRepository: k8s.gcr.io # 能够看到,缺省镜像仓库是gcr.io,国内不能正常访问。
初始化操作会从互联网下载所需镜像,过程比较漫长。运行初始化命令之前先运行这个命令,从而先行获得相关镜像文件,而后再执行初始化,感觉就好多了。
# 可先查看所需镜像:
[root@rust-master01 ~]# kubeadm config images list
W0821 13:56:31.902895 30984 configset.go:202] WARNING: kubeadm cannot validate component configs for API groups [kubelet.config.k8s.io kubeproxy.config.k8s.io]
k8s.gcr.io/kube-apiserver:v1.18.8
k8s.gcr.io/kube-controller-manager:v1.18.8
k8s.gcr.io/kube-scheduler:v1.18.8
k8s.gcr.io/kube-proxy:v1.18.8
k8s.gcr.io/pause:3.2
k8s.gcr.io/etcd:3.4.3-0
k8s.gcr.io/coredns:1.6.7
# 获得镜像:
kubeadm config images pull
肯定是下载不了。可使用这个脚本:
还有一个问题需要注意,阿里云上可能没有 1.18.8
这个较新版本之镜像,目前只有 1.18.6
这个版本。因而这里将获得之官方 1.18.8
镜像推送至阿里云私有仓库,所以脚本修改为:
[root@k8s-master ~]# cat pull_k8s_images.sh
#!/bin/bash
for i in `kubeadm config images list`; do
imageName=${i#k8s.gcr.io/}
aliyun_registry="registry.cn-beijing.aliyuncs.com/cdmonkey_k8s"
docker pull ${aliyun_registry}/$imageName
docker tag ${aliyun_registry}/$imageName k8s.gcr.io/$imageName
docker rmi ${aliyun_registry}/$imageName
done
执行脚本之前需要进行登录:
docker login --username=cdmonkey2019 registry.cn-beijing.aliyuncs.com
查看下载好的镜像:
[root@rust-master01 ~]# docker image list
REPOSITORY TAG IMAGE ID CREATED SIZE
k8s.gcr.io/kube-proxy v1.18.8 0fb7201f92d0 7 days ago 117MB
k8s.gcr.io/kube-apiserver v1.18.8 92d040a0dca7 7 days ago 173MB
k8s.gcr.io/kube-controller-manager v1.18.8 6a979351fe5e 7 days ago 162MB
k8s.gcr.io/kube-scheduler v1.18.8 6f7135fb47e0 7 days ago 95.3MB
k8s.gcr.io/pause 3.2 80d28bedfe5d 6 months ago 683kB
k8s.gcr.io/coredns 1.6.7 67da37a9a360 6 months ago 43.8MB
k8s.gcr.io/etcd 3.4.3-0 303ce5db0e90 10 months ago 288MB
注意:Node 节点只需要准备好 kube-proxy、pause 这两个镜像就行了。
至此,相关镜像准备妥当完毕了。
vim /etc/sysconfig/kubelet
KUBELET_EXTRA_ARGS=--cgroup-driver=systemd # 这里一定要同 Docker 相应配置保持一致
注意,到这里还不能直接启动 kubelet 服务,会有报错,需要执行完初始化才行。请见:
https://github.com/kubernetes/kubernetes/issues/65863
请确保这两个指令执行过了,省得初始化完成后抛出相关警告信息。
systemctl enable docker.service
systemctl enable kubelet.service
最后执行初始化指令:
kubeadm init --kubernetes-version=v1.16.7 --pod-network-cidr=10.244.0.0/16 --service-cidr=10.96.0.0/12 --ignore-preflight-errors=Swap
# 版本号需要准确指定。
# 若是没啥问题就能看到最后的成功信息:
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
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/
Then you can join any number of worker nodes by running the following on each as root:
kubeadm join 172.16.138.11:6443 --token glqmmh.q0pqn2m48bx58tx9 \
--discovery-token-ca-cert-hash sha256:07d5cfc2d45de9756e664126d9dcaef004b7b9e016c8389c8b4029193562826d
# 一定要备份最后给出了将节点加入集群的命令。
注意:若是使用 Calico,建议使用
--pod-network-cidr=10.224.0.0/16
而不是244
。
若是初始化时卡在某一步不能继续下去时,可使用
journalctl -xeu kubelet # 查看初始化日志,找到错误原因
相关参数说明:
--kubernetes-version # 指定 kubeadm 版本
--pod-network-cidr # 指定 Pod 所属网段。
# 因为是选择 flannel 作为 Pod 网络插件,因而指定 –pod-network-cidr=10.244.0.0/16
--service-cidr # 指定 Service 所属网段
--ignore-preflight-errors=Swap # 忽略 Swap 报错
--upload-certs #
这些参数可通过命令行直接配置,还可写入专门的 kubeadm 配置文件,并使用 --config
进行引用。若是需要修改 kubernetes 服务配置选项,就必须指定这个配置文件。
# Generate the configuration file:
[root@master01 tools]# kubeadm config print init-defaults > kubeadm-init.yaml
使用配置文件的好处是方便变更配置,像是镜像仓库地址啥的。
后续操作这里直接使用根用户。
[root@k8s-master ~]# mkdir -p $HOME/.kube
[root@k8s-master ~]# cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
至此,第一个 Master 节点初始化完成。这时可访问健康状态检查的地址:
curl -k https://localhost:6443/healthz # 返回一个 ok 就对了
集群初始化若是遇有问题,可使用下面的命令进行清理:
kubeadm reset
ifconfig cni0 down
ip link delete cni0
ifconfig flannel.1 down
ip link delete flannel.1
rm -rf /var/lib/cni/
kubectl
指令是 API Server 客户端命令行工具。
这个指令实现了除集群部署外几乎全部管理操作,是 k8s 管理员最常用命令之一。
# 其实就是初始化完成后要执行的那两条指令。前面执行过了,这里就不用再执行了。
[root@k8s-master ~]# mkdir .kube
[root@k8s-master ~]# cp /etc/kubernetes/admin.conf .kube/config
而后,可使用 kubectl
指令进行客户端命令检测,同时了解集群组件当前状态:
[root@k8s-master ~]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
k8s-master NotReady master 17h v1.14.0
# 还可使用:
[root@k8s-master ~]# kubectl get pods --all-namespaces
[root@k8s-master ~]# kubectl get componentstatus
NAME STATUS MESSAGE ERROR
scheduler Healthy ok
controller-manager Healthy ok
etcd-0 Healthy {"health":"true"}
只需要于 Master 节点执行安装操作就行,但是所有节点必须要准备好镜像。
首先需要手动下载镜像:
docker pull quay.azk8s.cn/coreos/flannel:v0.11.0-amd64
docker tag quay.azk8s.cn/coreos/flannel:v0.11.0-amd64 quay.io/coreos/flannel:v0.11.0-amd64
docker rmi quay.azk8s.cn/coreos/flannel:v0.11.0-amd64
进行安装:
[root@master01 ~]# mkdir -pv /etc/kubernetes/flannel
[root@master01 ~]# cd /etc/kubernetes/flannel
wget https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
# 可能需要翻墙下载
[root@master01 flannel]# kubectl apply -f kube-flannel.yml
而后使用命令确认其输出结果中 Pod 状态为 Running
[root@master01 flannel]# kubectl get pods -n kube-system
NAME READY STATUS RESTARTS AGE
coredns-5644d7b6d9-f85ms 1/1 Running 0 3h44m
coredns-5644d7b6d9-tjdzd 1/1 Running 0 3h44m
etcd-master01 1/1 Running 0 3h43m
kube-apiserver-master01 1/1 Running 0 3h43m
kube-controller-manager-master01 1/1 Running 0 3h43m
...
注意:只有 Running 才是就绪状态,显示别的都不是就绪状态。
还可查看 Pod 具体情况:
# kubectl describe pod <Pod Name>
kubectl describe pod kube-flannel-ds-amd64-jqh9z --namespace=kube-system
# 输出内容很多,于最后面能够看到是镜像获取失败。
# 我们可耐心等待,因为 K8s 会进行重试,还可直接执行 docker pull 下载这个镜像。
这里有一个小工具可供使用,用于获取镜像。
docker-get quay.io/coreos/flannel:v0.11.0-amd64
全部显示为 Running 后再次查看节点信息:
[root@k8s-master ~]# kubectl get node
NAME STATUS ROLES AGE VERSION
k8s-master Ready master 19h v1.14.0 # 能够看到,Master节点已变为就绪状态。
请参见相关文档。
若未禁用 Swap 设备,编辑 kubelet 配置文件,设置其忽略 Swap 启用的状态错误:
# 提示:若是节点上已禁用了所有 Swap 设备,则无须执行这个步骤。
[root@k8s-node1 ~]# vim /etc/sysconfig/kubelet
KUBELET_EXTRA_ARGS="--fail-swap-on=false"
而后要使用 master 节点初始化过程中记录的 kubeadm join
指令新增节点。
kubeadm join 172.16.138.11:6443 --token glqmmh.q0pqn2m48bx58tx9 \
--discovery-token-ca-cert-hash sha256:07d5cfc2d45de9756e664126d9dcaef004b7b9e016c8389c8b4029193562826d
# 注意:这条命令一定保存好,因为后期没法重现!
...
This node has joined the cluster:
* Certificate signing request was sent to apiserver and a response was received.
* The Kubelet was informed of the new secure connection details.
Run 'kubectl get nodes' on the control-plane to see this node join the cluster.
执行完 join
指令后查看各节点状态信息:
[root@master01 flannel]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
master01 Ready master 3h40m v1.16.7
worker01 Ready <none> 3h34m v1.16.7
worker02 Ready <none> 3h33m v1.16.7
使用 Kubeadm
工具搭建的 K8s 集群,已经缺省集成了安全策略,因而要将 Master 节点 PKI 目录下所有文件拷贝至所有 node 节点上。
scp -r /etc/kubernetes/pki/* root@k8s-node1:/etc/kubernetes/pki
若需要每个节点均能够执行 kubectl
指令,就需要于每个节点上执行这个指令的初始化操作:
# 首先每个节点上创建相关目录:
[root@k8s-node1 ~]# mkdir .kube
# 从主节点拷贝配置文件:
scp /etc/kubernetes/admin.conf root@k8s-node1:~/.kube/config
参考内容:
https://blog.frognew.com/2019/04/kubeadm-install-kubernetes-1.14.html
https://jicki.me/kubernetes/2019/05/09/kubeadm-1.14.1
官方文档:
https://kubernetes.io/docs/setup/production-environment/tools/kubeadm/create-cluster-kubeadm