在树莓派上点亮你的 Kubernetes 集群
提到 raspberry pi 相信大家都不陌生, 简单来说它就是一台名片大小基于 ARM 架构的计算机. 经过几代的发展 raspberry pi 的硬件配置有了长足的进步. 在目前最新的 4b 版本上, raspberry pi 可以提供 4 核, 8GB RAM 的配置. 这也使得它的可玩性大大提高. 最近恰好在学习 Kubernetes, 所以就想到用 raspberry pi 来组一台 Kubernetes 集群. 对于这台集群我希望它拥有低功耗, 安静, 但最主要是可以稳定地运行多个服务. 这篇文章是这个系列的第一篇, 先来介绍如何在一台由4块 raspberry pi 4b 组成的硬件集群上搭建 kubernetes cluster.
硬件准备
我这次选择了 4 台 raspberry pi 4b 8GB 版本. 其中一台 master, 另外三台 node 节点. 树莓派默认需要一个 5V 3A 的 type c 电源以及一个千兆有线网口, 这样如果要部署一个 4 节点的集群就要准备 8 根线 ( 4 根电源线 + 4 根网线). 考虑到布线的简洁清爽, 我为树莓派加装了一个 POE 模块, 有了 POE 模块就可以用一根网线同时提供网络和供电功能, 这样只需要 4 根网线以及一台 POE 交换机/路由器即可解决所有的供电和网络需求. 另外每台树莓派配有一块 64GB 的 sdcard 用来安装系统.
具体使用到的清单如下:
软件准备
操作系统方面我们选择目前最新的 LTS 版本, Ubuntu 20.04 版. 我们使用 usbimager 将ubuntu 镜像刷入 sdcard. Kubernetes 安装最新的稳定版本 1.22.2. 需要用到的软件下载地址如下:
安装步骤
初步准备
usbimager 使用非常简单, 在界面中选择下载的20.04镜像并指定目标 sdcard 设备进行写入. 如果 sdcard 上存在其他系统或者分区, 建议可以将这些分区先删除后再进行系统刷入.
完成 4 台设备的系统刷入后, 将 sdcard 插入树莓派并连接到POE进行初步测试. 树莓派默认通过 DHCP 获取 IP 地址. 因此如果顺利的话, 可以在路由器的管理界面中看到树莓派分配的 IP 地址. 为了方便今后的使用, 我们可以在此时绑定 MAC 与 IP 地址的分配. 这样 4 台树莓派都获得了固定的 IP 地址. 在我的环境中 4 台树莓派的地址分配如下:
- master01: 172.16.0.1
- node01: 172.16.0.11
- node02: 172.16.0.12
- node03: 172.16.0.13
系统准备
在所有的树莓派
上完成以下准备工作:
更新系统:
sudo apt update && sudo apt dist-upgrade && apt-get install -y apt-transport-https
创建自定义用户:
sudo adduser manfred
给予该用户 sudo 权限:
sudo usermod -aG sudo manfred
设置主机名(注意每个node 的名字不同):
echo master01 | sudo tee /etc/hostname
为集群内所有节点添加 hosts 文件映射:
1
2
3
4
5
6# cat /etc/hosts
127.0.0.1 localhost
172.16.0.1 master01
172.16.0.11 node01
172.16.0.12 node02
172.16.0.13 node03编辑 /boot/firmware/cmdline.txt 并在行末添加:
1
cgroup_enable=cpuset cgroup_enable=memory cgroup_memory=1 swapaccount=1
重启:
sudo reboot
安装 docker:
curl -sSL get.docker.com | sudo sh
将自己的账号加入 docker 组:
sudo usermod -aG docker manfred
编辑 docker 配置文件并指定中文源:
sudo vi /etc/docker/daemon.json
1
2
3
4
5
6
7
8
9{
"exec-opts": ["native.cgroupdriver=systemd"],
"log-driver": "json-file",
"log-opts": {
"max-size": "100m"
},
"storage-driver": "overlay2",
"registry-mirrors": ["https://docker.mirrors.ustc.edu.cn"]
}应用上述配置:
sudo systemctl daemon-reload && sudo systemctl restart docker
开启路由:
sudo sed -i 's/#net.ipv4.ip_forward=1/net.ipv4.ip_forward=1/g' /etc/sysctl.conf
重启系统:
sudo reboot
重启后确定 docker 工作正常: docker run hello-world
完成以上步骤后, 下面开始进入 kubernetes 的安装过程.
Kubernetes 安装准备
在所有树莓派上执行以下步骤:
- 为Kubernetes 设置国内源:
1
2
3
4
5curl https://mirrors.aliyun.com/kubernetes/apt/doc/apt-key.gpg | sudo apt-key add -
cat <<EOF >/etc/apt/sources.list.d/kubernetes.list
deb https://mirrors.aliyun.com/kubernetes/apt/ kubernetes-xenial main
EOF
sudo apt-get update - 由于我们安装的版本 1.22.2 比较新, 所以可以手动下载这些镜像并用 tag 命令进行修正:
1
2
3
4
5
6sudo docker pull coredns/coredns:1.8.4
sudo docker tag coredns/coredns:1.8.4 registry.aliyuncs.com/google_containers/coredns:v1.8.4
sudo docker pull cjk2atmb/kube-controller-manager:v1.22.2
sudo docker tag cjk2atmb/kube-controller-manager:v1.22.2 registry.aliyuncs.com/google_containers/kube-controller-manager:v1.22.2 - 在上述准备工作完成后我们就可以开始安装:
sudo apt-get install -y kubelet kubeadm kubectl
master 节点
初始化 Kubernetes master 节点:
1
sudo kubeadm init --image-repository=registry.aliyuncs.com/google_containers --pod-network-cidr=10.244.0.0/16
如果一切正常的话在上述命令运行完后会看到如下提示. 将下面的 kubeadm join 命令保存好以备后续添加 node 节点时使用:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20Your 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/
Then you can join any number of worker nodes by running the following on each as root:
sudo kubeadm join 172.16.0.1:6443 --token xxxxxxx \
--discovery-token-ca-cert-hash sha256:xxxxx运行以下命令初始化 kubectl:
1
2
3
4mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
echo 'source <(kubectl completion bash)' >> ~/.bashrc安装 flannel 网络组件:
kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
最后确保所有镜像均可正常运行:
1
2
3
4
5
6
7
8
9
10
11
12NAMESPACE NAME READY STATUS RESTARTS AGE
default demoapp-79b7d5f68b-bp9z2 1/1 Running 0 30h
kube-system coredns-7f6cbbb7b8-kwsng 1/1 Running 1 (41h ago) 42h
kube-system coredns-7f6cbbb7b8-qbmdn 1/1 Running 1 (41h ago) 42h
kube-system etcd-master01 1/1 Running 5 (41h ago) 42h
kube-system kube-apiserver-master01 1/1 Running 5 (41h ago) 42h
kube-system kube-controller-manager-master01 1/1 Running 1 (41h ago) 42h
kube-system kube-flannel-ds-kghwp 1/1 Running 1 (41h ago) 41h
kube-system kube-flannel-ds-rcjfq 1/1 Running 1 (41h ago) 42h
kube-system kube-proxy-6mksg 1/1 Running 1 (41h ago) 42h
kube-system kube-proxy-w95hs 1/1 Running 1 (41h ago) 41h
kube-system kube-scheduler-master01 1/1 Running 5 (41h ago) 42h
node 节点
复制之前的 join 命令:
1
sudo kubeadm join 172.16.0.1:6443 --token xxxxxxx --discovery-token-ca-cert-hash sha256:xxxxx
如果 token 丢失或者过期可以重新生成:
kubeadm token create --print-join-command
安装完成后用 kubectl get nodes 查看安装情况. 如果 node 一直显示
Not Ready
, 可以尝试重启 node. 如果 node 没有 role, 可以自己给node 打role 标签:1
kubectl label node node01 node-role.kubernetes.io/worker=worker
这样基本完成了Kubernetes 集群的安装.