文章文字比较多,请耐心的阅读,你会受益匪浅!
你必须问一个问题“我如何设置 Kubernetes 集群?”你最终可能会从不同的搜索结果中得到不同的答案,这对初学者来说可能是压倒性的。Kubernetes 是一个复杂的系统,安装并妥善管理它并非易事。
然而,随着 Kubernetes 社区的扩展和成熟,出现了越来越多的用户友好工具。截至今天,根据您的要求,有很多选项可供选择:
- 如果您使用的是物理(裸机)服务器或虚拟机 (VM),Kubeadm 非常适合。
- 如果你在云环境中运行,kops 和 Kubespray 可以简化 Kubernetes 的安装,以及与云提供商的集成。
- 如果你想减轻管理 Kubernetes 控制平面的负担,几乎所有的云提供商都有他们的 Kubernetes 托管服务,例如 Google Kubernetes Engine (GKE)、Amazon Elastic Kubernetes Service (EKS)、Azure Kubernetes Service (AKS) 和 IBM Kubernetes Service (IKS)。
- 如果你只是想要一个学习 Kubernetes 的游乐场,Minikube 和 Kind 可以帮助你在几分钟内启动一个 Kubernetes 集群。
因此,正如您所看到的,您有很多选项可供选择来部署您的第一个 Kubernetes 集群。我将介绍使用 kubeadm 在 CentOS 8 服务器上安装 Kubernetes CLuster 的步骤。
【中篇】【中篇】【中篇】【中篇】【中篇】
【中篇】【中篇】【中篇】【中篇】【中篇】
使用 kubeadm 构建多节点 Kubernetes 集群
在本节中,我们将安装一个具有多个节点的 Kubernetes 集群。我将通过Oracle VirtualBox运行虚拟机中的节点,但您也可以使用不同的虚拟化工具或裸机。要同时设置主节点和工作节点,我们将使用该工具。kubeadm
我们计划做什么
在我们继续安装之前,让我简要概述一下我们将在本节中执行的操作,以便您对后续步骤有一个基本的了解。如果你已经阅读了我之前的教程,那么你一定熟悉 Kubernetes 集群的架构,我将再次放置图像供您参考:
您可以看到主节点和工作节点上安装了不同的组件,现在手动安装这些组件,修改配置文件等可能是一项非常繁琐的任务。这就是我们使用的原因,因为它将简化构建 Kubernetes 集群并在相应节点上启动所有组件的过程。kubeadm
以下是简要涉及的步骤(图中从下到上):
- 创建 VM 或安排裸机服务器来设置群集
- 在所有主机上安装操作系统
- 在所有主机上安装容器运行时,以便我们可以在所有主机上运行容器,我们将使用 Docker
- 在所有节点上安装 kubeadm
- 初始化主服务器,在此过程中,所有必需的组件都在主服务器上安装和配置
- Kubernetes 需要在主节点和工作节点之间建立一个特殊的网络,即 Pod 网络或集群网络。
- 将主节点加入工作节点
实践环境
我将拥有单个控制器或主节点和两个工作节点。
Resources | controller | worker-1 | worker-2 |
操作系统 | CentOS 8 | CentOS 8 | CentOS 8 |
主机名 | 控制器 | worker-1 | worker-2 |
域名(FQDN) | controller.example.com | worker-1.example.com | worker-2.example.com |
存储 | 20GB | 20GB | 20GB |
虚拟处理器 | 2 | 2 | 2 |
内存 | 6GB | 6GB | 6GB |
IP | 192.168.43.48 | 192.168.43.49 | 192.168.43.50 |
我在我的环境中使用两个不同的接口,这不是必需的。我有适配器-1作为NAT,我用于SSH端口转发(您可以忽略这一点)。在本教程中,我们将仅使用配置桥接适配器的适配器-2。您可以在Oracle VirtualBox中了解有关不同网络选项的更多信息以获取更多详细信息。
下面是我的 VM 网络设置之一的代码片段
先决条件
安装 Oracle VirtualBox
您可以从他们的官方存储库下载VirtualBox软件。我写了另一篇文章来安装Oracle Virtual Box,它在Windows上很安静。只需双击下载的软件并按照说明进行操作,将所有设置保留为默认值。
安装 CentOS 8
我将使用 CentOS 8 来设置我的 Kubernetes 集群,您可以按照分步说明在您的 VM 上安装 CentOS。如果你不熟悉 CentOS 8 的安装步骤,而想选择简单的方法,那么你可以从
https://www.osboxes.org/centos/ 下载 CentOS 8 映像,你只需要在 VirtualBox 中部署下载的文件,你就会有一个预安装的虚拟机启动并运行,无需任何手动步骤。
更新 /etc/hosts
如果您没有 DNS 服务器来解析主机名,则必须使用所有节点上所有群集节点的主机名和 IP 信息更新 /etc/hosts 文件,下面是我的一个群集节点的示例输出:
禁用交换
必须禁用交换内存才能正常工作。在所有群集节点上执行以下步骤。kubelet
首先检查 Linux 服务器上交换内存的可用性:
[root@controller ~]# free -m
total used free shared buff/cache available
Mem: 6144 454 5207 9 472 3100
Swap: 2046 0 2046
所以我们有一个 2 GB 的交换,要禁用交换,我们将使用命令swapoff
[root@controller ~]# swapoff -a
接下来重新验证分配的交换内存:
[root@controller ~]# free -m
total used free shared buff/cache available
Mem: 3781 454 2855 9 471 3101
Swap: 0 0 0
完成后,我们还需要确保在节点重新启动后不会重新分配交换,因此请注释掉 交换文件系统条目。以下是我的设置中的示例:/etc/fstab
#/dev/mapper/rhel-swap swap swap defaults 0 0
在所有群集节点上重复相同的步骤。
禁用 SELinux
您必须在所有群集节点上禁用 selinux 或将其更改为宽松模式。这是允许容器访问主机文件系统所必需的,这是 Pod 网络所需要的。您必须执行此操作,直到 中的 SELinux 支持得到改进。kubelet
[root@controller ~]# setenforce 0
检查 SELinux 的状态
[root@controller ~]# getenforce
Permissive
要使更改在重新启动后持久存在,请执行以下命令:
[root@controller ~]# sed -i --follow-symlinks 's/SELINUX=enforcing/SELINUX=disabled/g' /etc/sysconfig/selinux
在所有群集节点上重复相同的步骤。
启用防火墙
接下来,我们需要在主节点和工作节点上启用某些预定义端口。需要在主节点上打开以下端口,我们将用于打开这些端口firewalld
端口范围 | 目的 |
6443 | 这些端口用于 Kubernetes API 访问。 |
2379-2380 | 这些端口用于 etcd 服务器客户端 API。 |
10250 | 此端口用于 Kubelet API |
10251 | 此端口用于 kube-scheduler |
10252 | 此端口用于 kube-controller-manager |
在控制器节点上启用相应的防火墙端口:
[root@controller ~]# firewall-cmd --add-port 6443/tcp --add-port 2379-2380/tcp --add-port 10250-10252/tcp --permanent
[root@controller ~]# firewall-cmd --reload
[root@controller ~]# firewall-cmd --list-ports
6443/tcp 2379-2380/tcp 10250-10252/tcp
所有工作器节点上都需要允许以下端口:
端口范围 | 目的 |
10250 | 此端口用于 Kubelet API |
30000-32767 | 节点端口服务 |
在所有工作器节点上启用相应的防火墙端口:
[root@worker-1 ~]# firewall-cmd --add-port 10250/tcp --add-port 30000-32767/tcp --permanent
[root@worker-1 ~]# firewall-cmd --reload
[root@worker-1 ~]# firewall-cmd --list-ports
10250/tcp 30000-32767/tcp
[root@worker-2 ~]# firewall-cmd --add-port 10250/tcp --add-port 30000-32767/tcp --permanent
[root@worker-2 ~]# firewall-cmd --reload
[root@worker-2 ~]# firewall-cmd --list-ports
10250/tcp 30000-32767/tcp
配置网络
如果您有多个网络适配器,并且您的 Kubernetes 组件在默认路由上无法访问,我们建议您添加 IP 路由,以便 Kubernetes 集群地址通过相应的适配器。
在我的设置中,默认路由是为桥接网络配置的,而仅主机模式网络将仅用于内部路由:
确保模块已加载。这可以通过运行来完成br_netfilter
# lsmod | grep br_netfilter
由于未处于加载状态,我将手动加载此模块:br_netfilter
[root@controller ~]# modprobe br_netfilter
现在重新验证模块状态:
[root@controller ~]# lsmod | grep br_netfilter
br_netfilter 24576 0
bridge 188416 1 br_netfilter
作为 Linux 节点的 iptables 正确查看桥接流量的要求,您应该确保在配置中设置为 1
net.bridge.bridge-nf-call-iptablessysctl
[root@controller ~]# sysctl -a | grep net.bridge.bridge-nf-call-iptables
net.bridge.bridge-nf-call-iptables = 1
默认情况下启用它,但为了安全起见,我们还将创建一个配置文件并为IPv4和IPv6添加此配置文件:sysctl
[root@controller ~]# cat <
激活新添加的更改:
[root@controller ~]# sysctl --system
安装容器运行时 (Docker CE)
您需要在集群中的每个节点中安装容器运行时,以便 Pod 可以在那里运行。有多个容器运行时,例如:
- 码头工人:/var/run/docker.sock
- 集装箱:/run/containerd/containerd.sock
- CRI-O:/var/run/crio/crio.sock
如果同时检测到 和,则 Docker 优先。在本教程中,我们将使用 Docker 作为所有节点上的运行时。首先,我们需要安装一些依赖包:Dockercontainerd
~]# dnf install -y yum-utils device-mapper-persistent-data lvm2
添加 docker 存储库以便能够在所有节点上安装 docker:
~]# yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
Adding repo from: https://download.docker.com/linux/centos/docker-ce.repo
在所有节点上安装 Docker CE 软件包:
~]# dnf install containerd.io docker-ce docker-ce-cli -y
在所有节点上创建一个新目录:
[root@controller ~]# mkdir -p /etc/docker
通过创建新文件并在此文件中添加以下内容,在所有节点上设置 Docker 守护程序:/etc/docker/daemon.json
[root@controller ~]# cat /etc/docker/daemon.json
{
"exec-opts": ["native.cgroupdriver=systemd"],
"log-driver": "json-file",
"log-opts": {
"max-size": "100m"
},
"storage-driver": "overlay2",
"storage-opts": [
"overlay2.override_kernel_check=true"
]
}
我们都完成了配置,是时候在所有节点上启动(重新启动)我们的 docker 守护进程了:
[root@controller ~]# systemctl daemon-reload
[root@controller ~]# systemctl enable docker --now
[root@worker-1 ~]# systemctl daemon-reload
[root@worker-1 ~]# systemctl enable docker --now
[root@worker-2 ~]# systemctl daemon-reload
[root@worker-2 ~]# systemctl enable docker --now
提示:
启动 docker 服务时,我收到“”错误,要解决此问题,我们需要使用”containerd: symbol lookup error: /usr/bin/containerd: undefined symbol:
seccomp_api_selibseccompdnf update libseccomp -y"
检查所有节点上使用的 docker 服务的状态,以确保 docker 已启动并正常运行:systemctl status docker
安装 Kubernetes 组件(kubelet、kubectl 和 kubeadm)
您将在所有计算机上安装这些软件包:
- kubeadm:引导集群的命令。
- kubelet:在集群中的所有计算机上运行的组件,并执行诸如启动 Pod 和容器之类的操作。
- kubectl:与集群通信的命令行工具。
重要提示:
kubeadm不会为您安装或管理,因此您需要确保它们与您要为您安装的 Kubernetes 控制平面的版本相匹配。kubeletkubectlkubeadm
在所有节点上创建 kubernetes 存储库文件,该文件将用于下载软件包:
~]# cat <
在所有节点上使用包管理器安装 Kubernetes 组件包:
~]# dnf install -y kubelet kubeadm kubectl --disableexcludes=kubernetes
在此阶段,我们不会启动服务,因为这将自动完成kubelet
- 初始化控制节点时在控制器节点上
- 在主节点上以及当我们将工作节点加入主节点时
初始化控制节点
控制平面节点是运行控制平面组件的计算机,包括(群集数据库)和 API 服务器(命令行工具与之通信)。etcdkubectl
提示:
kubeadm使用与默认网关关联的网络接口为此特定控制平面节点的 API 服务器设置通告地址。或者,您也可以将参数指定为 kubeadm init。
--apiserver-advertise-address=
[root@controller ~]# kubeadm init
W1127 23:05:26.412480 7525 configset.go:348] WARNING: kubeadm cannot validate component configs for API groups [kubelet.config.k8s.io kubeproxy.config.k8s.io]
[init] Using Kubernetes version: v1.19.4
[preflight] Running pre-flight checks
[WARNING Firewalld]: firewalld is active, please ensure ports [6443 10250] are open or your cluster may not function correctly
[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 in beforehand using 'kubeadm config images pull'
[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 [controller.example.com kubernetes kubernetes.default kubernetes.default.svc kubernetes.default.svc.cluster.local] and IPs [10.96.0.1 192.168.43.48]
[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 [controller.example.com localhost] and IPs [192.168.43.48 127.0.0.1 ::1]
[certs] Generating "etcd/peer" certificate and key
[certs] etcd/peer serving cert is signed for DNS names [controller.example.com localhost] and IPs [192.168.43.48 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"
[kubeconfig] Writing "admin.conf" kubeconfig file
[kubeconfig] Writing "kubelet.conf" kubeconfig file
[kubeconfig] Writing "controller-manager.conf" kubeconfig file
[kubeconfig] Writing "scheduler.conf" kubeconfig file
[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
[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"
[etcd] Creating static Pod manifest for local etcd in "/etc/kubernetes/manifests"
[wait-control-plane] Waiting for the kubelet to boot up the control plane as static Pods from directory "/etc/kubernetes/manifests". This can take up to 4m0s
[apiclient] All control plane components are healthy after 18.507221 seconds
[upload-config] Storing the configuration used in ConfigMap "kubeadm-config" in the "kube-system" Namespace
[kubelet] Creating a ConfigMap "kubelet-config-1.19" 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 controller.example.com as control-plane by adding the label "node-role.kubernetes.io/master=''"
[mark-control-plane] Marking the node controller.example.com as control-plane by adding the taints [node-role.kubernetes.io/master:NoSchedule]
[bootstrap-token] Using token: rdet9b.4pugjes5hwq3aynk
[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
[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
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 192.168.43.48:6443 --token rdet9b.4pugjes5hwq3aynk \
--discovery-token-ca-cert-hash sha256:d2408f85e478b5a9927f1fafd89630fb71a1ce07d5e26e0cf4c7ff4320d433a2
重要提示:
请务必保存上述输出中的命令,因为稍后需要它来加入工作节点。kubeadm join
初始化已成功完成。如果您注意到上一个命令中突出显示的输出,则如果您以普通用户身份执行了上述命令,则必须执行某些步骤。但是由于我们使用的是 root 用户,我们必须执行以下命令:
export KUBECONFIG=/etc/kubernetes/admin.conf
并将其添加到您的/etc/profile
[root@controller ~]# echo "export KUBECONFIG=/etc/kubernetes/admin.conf" >> ~/.bash_profile
使用以下方法检查服务状态:kubeletsystemctl status kubelet
检查集群信息:
[root@controller ~]# kubectl cluster-info
Kubernetes master is running at https://192.168.43.48:6443
KubeDNS is running at https://192.168.43.48:6443/api/v1/namespaces/kube-system/services/kube-dns:dns/proxy
To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.
获取群集中的节点列表
[root@controller ~]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
controller.example.com NotReady master 63m v1.19.3
在这个阶段,我们有单个节点,它也处于 NotReady 状态,我们将在下一章中修复。
【中篇】【中篇】【中篇】【中篇】【中篇】
【中篇】【中篇】【中篇】【中篇】【中篇】
欢迎各位小伙伴关注、点赞、评论、转发,你的关注和转发是我最大的动力!