K8s集群部署心得:如何使用Kubeadm一次搞定安装Kubernetes?
相信很多朋友在学习K8s入门的时候遇到的第一块绊脚石,就是安装以及部署kubernetes了。网络上的教程又多又杂,而且因为设备环境不同等等诸多问题的存在,导致很多朋友就算照着教程一步一步来,也还是不知道怎么回事就报错,导致前功尽弃。作者也深受其害。为了帮助各位因安装k8s而焦头烂额的各位朋友快速解决问题,也为了记录本人在入门运维之路上踩过的坑,作者特地写下这篇基于Kubeadm安装部署K8s集.
相信很多朋友在学习K8s入门的时候遇到的第一块绊脚石,就是安装以及部署kubernetes了。网络上的教程又多又杂,而且因为设备环境不同等等诸多问题的存在,导致很多朋友就算照着教程一步一步来,也还是不知道怎么回事就报错,导致前功尽弃。作者也深受其害。
为了帮助各位因安装k8s而焦头烂额的各位朋友快速解决问题,也为了记录本人在入门运维之路上踩过的坑,作者特地写下这篇基于Kubeadm安装部署K8s集群的教程,并详细记录了本人遇到的报错经过以及解决措施。
一. 准备虚拟机
首先我们要准备三台虚拟机。一台作为Master节点,两台作为Node节点,完成效果如下图所示。(为演示方便,本例只演示一台Master和一台Node的部署)
1.1 配置Master节点
首先我们打开主页的“创建新的虚拟机”,创造一个Master节点。这里选“典型(推荐)”即可。
设置用户名和密码。随意设置即可。
设置虚拟主机名称。随意即可。这里我们将其设置为“Master01”。
这里记得要选将此盘存储为单个文件”,以便快速打开。
这里注意了,我们虽然大体上设置了这台master节点的账户信息,但是硬件部分我们依然有很多需要解决。点击下方“自定义硬件”。
首先我们要确保Master节点的CPU是两核的,不然启动时会报错。并且最好把虚拟化引擎全部打开,这将大大减少我们的启动时间。
之后,我们需要添加一个网络适配器。
一台设置为桥接模式,一台设为自定义(VMnet1),最终效果如下图所示。
然后,我们需要打开“编辑”中的“虚拟网络编辑器”,并选择桥接模式中的“Realtek PCIe GBE Family Controller”,最后点击“确定”保存退出。
点击“完成”。至此,我们终于算是迈出了安装k8s的一小步。接下来的10分钟,我们等CentOS系统初始化就行了。
系统终于安装好了。首先咱们来改改咱们的主机名。
# sudo hostnamectl set-hostname master.example.com
输入hostname
看一眼,如果是这样滴就代表我们更改主机名成功了。
我们打开终端,输入:ifconfig
,来看看我们的网络能不能正常连接。
# ifconfig
eno16777736: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 192.168.1.108 netmask 255.255.255.0 broadcast 192.168.1.255
inet6 fe80::20c:29ff:feef:fb27 prefixlen 64 scopeid 0x20<link>
ether 00:0c:29:ef:fb:27 txqueuelen 1000 (Ethernet)
RX packets 862161 bytes 1266491294 (1.1 GiB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 396136 bytes 27828165 (26.5 MiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
eno33554960: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500
inet 192.168.217.142 netmask 255.255.255.0 broadcast 192.168.217.255
inet6 fe80::20c:29ff:feef:fb31 prefixlen 64 scopeid 0x20<link>
ether 00:0c:29:ef:fb:31 txqueuelen 1000 (Ethernet)
RX packets 215 bytes 35054 (34.2 KiB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 94 bytes 16812 (16.4 KiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
lo: flags=73<UP,LOOPBACK,RUNNING> mtu 65536
inet 127.0.0.1 netmask 255.0.0.0
inet6 ::1 prefixlen 128 scopeid 0x10<host>
loop txqueuelen 0 (Local Loopback)
RX packets 570 bytes 49266 (48.1 KiB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 570 bytes 49266 (48.1 KiB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
我们可以看到,正常的连接状态是这样的,我们需要记住我们Master节点的ip地址是192.168.1.108(不是下边的那个192.168.217.142!只有一个ip是不对的!)。这个IP地址接下来会经常用到。
接着我们需要测试一下我们的网络是否和外界连通。
# ping www.baidu.com
成功连接外网。
至此,我们算是完成了第一台Master节点的物理配置。
(另外两台Node节点的配置方式和本节方法基本一致,在此不再赘述。)
坑1:网络配置
有朋友之前的网络配置有问题,八成是你没按步骤来,建议一步一步检查。
解决方法:
# dhclient
之后重启一下虚拟机,再次输入ifconfig
查看网络状态。
二. Kubeadm配置Master节点
- 首先我们要禁用防火墙。
# systemctl stop firewalld
# systemctl disable firewalld
- 之后我们要禁用SELINUX。
# vim /etc/sysconfig/selinux
我们可以通过更改selinux配置文件的方式来禁用selinux。如图所示,把下边的enforcing改为disabled即可。
别忘了使它生效。
# setenforce 0
- 创建/etc/sysctl.d/k8s.conf文件,添加如下内容.
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
vm.swappiness=0
net.ipv4.ip_forward = 1
执行sysctl -p /etc/sysctl.d/k8s.conf使修改生效。
执行命令使修改生效.
# modprobe br_netfilter
# sysctl -p /etc/sysctl.d/k8s.conf
- 禁用swap,关闭系统的Swap方法如下:
# swapoff -a
修改 /etc/fstab 文件,注释掉 SWAP 的自动挂载
UUID=37417d9b-de8d-4d91-bd86-4dfd46e89128 / xfs defaults 1 1
UUID=db9ade39-3952-4ff1-9aeb-3d95ea4dac59 /boot xfs defaults 1 2
UUID=4ee6483c-6a9a-43f8-be86-70046c996a96 /home xfs defaults 1 2
#UUID=6072c1ae-6d61-45dc-9d24-c4ad78ec4445 swap swap defaults 0 0
- 添加主机名
# vim /etc/hosts
以作者为例,如果要添加一台主机和一台节点,那么就在k8s.conf中添加这么两行。其中,IP地址为我们执行ifconfig
所获得的地址。
各节点安装Docker
Kubernetes从1.6开始使用CRI(Container Runtime Interface)容器运行时接口。默认的容器运行时仍然是Docker,使用的是kubelet中内置dockershim CRI实现。关于如何安装Docker我已经记录了,如果遇到问题欢迎移步我的博客。
安装docker的yum源:
# yum install -y xfsprogs yum-utils device-mapper-persistent-data lvm2
# yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
查看最新的Docker版本:
[root@master01~]# yum list docker-ce.x86_64 --showduplicates |sort -r
已加载插件:fastestmirror, langpacks
已安装的软件包
可安装的软件包
* updates: ftp.cuhk.edu.hk
Loading mirror speeds from cached hostfile
* extras: ftp.cuhk.edu.hk
docker-ce.x86_64 3:18.09.0-3.el7 docker-ce-stable
docker-ce.x86_64 18.06.1.ce-3.el7 docker-ce-stable
docker-ce.x86_64 18.06.1.ce-3.el7 @docker-ce-stable
docker-ce.x86_64 18.06.0.ce-3.el7 docker-ce-stable
docker-ce.x86_64 18.03.1.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 18.03.0.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.12.1.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.12.0.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.09.1.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.09.0.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.06.2.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.06.1.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.06.0.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.03.3.ce-1.el7 docker-ce-stable
docker-ce.x86_64 17.03.2.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.03.1.ce-1.el7.centos docker-ce-stable
docker-ce.x86_64 17.03.0.ce-1.el7.centos docker-ce-stable
在各节点安装docker的18.06.1版本
# yum makecache fast
# yum install -y --setopt=obsoletes=0 docker-ce-18.06.1.ce-3.el7
# systemctl start docker
# systemctl enable docker
坑3. Docker启动时报错
可能是因为Docker默认selinux开启。我们在配置文件中修改即可。
在enabled后边加=false
即可。
# vim /etc/sysconfig/docker
使用kubeadm部署Kubernetes
各节点安装kubeadm和kubelet
下面在各节点安装kubeadm和kubelet:
cat <<EOF > /etc/yum.repos.d/kubernetes.repo
[kubernetes]
name=Kubernetes
baseurl=https://packages.cloud.google.com/yum/repos/kubernetes-el7-x86_64
enabled=1
gpgcheck=1
repo_gpgcheck=1
gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg
https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg
EOF
测试网络是否可用
curl https://packages.cloud.google.com/yum/repos/kubernetes-el7-x86_64
更新源
yum makecache fast
yum install -y kubelet kubeadm kubectl
…
已安装:
kubeadm.x86_64 0:1.13.0-0 kubectl.x86_64 0:1.13.0-0 kubelet.x86_64 0:1.13.0-0
作为依赖被安装:
cri-tools.x86_64 0:1.12.0-0 kubernetes-cni.x86_64 0:0.6.0-0 socat.x86_64 0:1.7.3.2-2.el7
完毕!
从安装结果可以看出还安装了cri-tools, kubernetes-cni, socat三个依赖:
官方从Kubernetes 1.9开始就将cni依赖升级到了0.6.0版本,在当前1.13中仍然是这个版本
socat是kubelet的依赖。cri-tools是CRI(Container Runtime Interface)容器运行时接口的命令行工具
使用kubeadm init初始化集群
在各节点开机启动kubelet服务:
systemctl enable kubelet.service
接下来使用kubeadm初始化集群,选择k8s-node1作为Master Node,在node1上执行下面的命令:
kubeadm init --kubernetes-version=v1.13.0 --pod-network-cidr=10.244.0.0/16 --apiserver-advertise-address=192.168.112.38
因为我们选择flannel作为Pod网络插件,所以上面的命令指定–pod-network-cidr=10.244.0.0/16。
运行结果如下。
[init] Using Kubernetes version: v1.13.0
[preflight] Running pre-flight checks
[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'
[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] Activating the kubelet service
[certs] Using certificateDir folder "/etc/kubernetes/pki"
[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 [k8s-node1 localhost] and IPs [192.168.112.38 127.0.0.1 ::1]
[certs] Generating "etcd/peer" certificate and key
[certs] etcd/peer serving cert is signed for DNS names [k8s-node1 localhost] and IPs [192.168.112.38 127.0.0.1 ::1]
[certs] Generating "etcd/healthcheck-client" certificate and key
[certs] Generating "apiserver-etcd-client" certificate and key
[certs] Generating "ca" certificate and key
[certs] Generating "apiserver" certificate and key
[certs] apiserver serving cert is signed for DNS names [k8s-node1 kubernetes kubernetes.default kubernetes.default.svc kubernetes.default.svc.cluster.local] and IPs [10.96.0.1 192.168.112.38]
[certs] Generating "apiserver-kubelet-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
[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 28.002313 seconds
[uploadconfig] storing the configuration used in ConfigMap "kubeadm-config" in the "kube-system" Namespace
[kubelet] Creating a ConfigMap "kubelet-config-1.13" in namespace kube-system with the configuration for the kubelets in the cluster
[patchnode] Uploading the CRI Socket information "/var/run/dockershim.sock" to the Node API object "k8s-node1" as an annotation
[mark-control-plane] Marking the node k8s-node1 as control-plane by adding the label "node-role.kubernetes.io/master=''"
[mark-control-plane] Marking the node k8s-node1 as control-plane by adding the taints [node-role.kubernetes.io/master:NoSchedule]
[bootstrap-token] Using token: lauqjh.zhdjhnwldjnjd2qm
[bootstrap-token] Configuring bootstrap tokens, cluster-info ConfigMap, RBAC Roles
[bootstraptoken] configured RBAC rules to allow Node Bootstrap tokens to post CSRs in order for nodes to get long term certificate credentials
[bootstraptoken] configured RBAC rules to allow the csrapprover controller automatically approve CSRs from a Node Bootstrap Token
[bootstraptoken] configured RBAC rules to allow certificate rotation for all node client certificates in the cluster
[bootstraptoken] creating the "cluster-info" ConfigMap in the "kube-public" namespace
[addons] Applied essential addon: CoreDNS
[addons] Applied essential addon: kube-proxy
Your Kubernetes master 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/
You can now join any number of machines by running the following on each node
as root:
kubeadm join 192.168.1.108:6443 --token vgghhv.qjsvzv1wjbm1k631 --discovery-token-ca-cert-hash sha256:0688289f3b27978cd7ac91290d822d837c93595de09bad7ba4b99b24a8f56f0c
如果出现这么个结果,代表我们已经成功地完成了master节点的部署。那么我们要记住下边这一句将节点加入集群的命令,待会还要用到。
kubeadm join 192.168.1.108:6443 --token vgghhv.qjsvzv1wjbm1k631 --discovery-token-ca-cert-hash sha256:0688289f3b27978cd7ac91290d822d837c93595de09bad7ba4b99b24a8f56f0c
PS:查看集群状态
# kubectl get nodes -n namespace
# kubectl get cs
NAME STATUS MESSAGE ERROR
scheduler Healthy ok
controller-manager Healthy ok
etcd-0 Healthy {"health": "true"}
添加node节点
至此master节点已经初步部署完成,接下来我们进行node1的添加
前面的步骤和master节点一致,于是我们可以用脚本进行完成,节省时间
#停止firewalld服务
systemctl stop firewalld && systemctl disable firewalld
#关闭selinux
sed -i 's/^SELINUX=enforing$/SELINUX=disabled' /etc/selinux/config && setenforce 0
#关闭swap设置
swapoff -a
yes | cp /etc/fstab /etc/fstab_bak
cat /etc/fstab_bak |grep -v swap > /etc/fstab
#解决流量路径不正确问题
cat <<EOF > /etc/sysctl.d/k8s.conf
vm.swappiness = 0
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward = 1
EOF
#使配置生效
modprobe br_netfilter
sysctl -p /etc/sysctl.d/k8s.conf
#更改hosts文件
cat >> /etc/hosts <<EOF
192.168.1.108 master.example.com
192.168.1.107 node1.example.com
EOF
#安装docker
yum -y install docker
systemctl enable docker && systemctl start docker
配置阿里k8s源
cat >> /etc/yum.repos.d/k8s.repo <<EOF
[kubernetes]
name=kubernetes repo
baseurl=https://mirrors.aliyun.com/kubernetes/yum/repos/kubernetes-el7-x86_64/
gpgcheck=0
EOF
#安装kubelet/kubeadm/kubectl
#这里需要注意,如果你直接运行指令yum -y install kubelet kubeadm kubectl,这里将会自动为你下载最新版本,我们这里为了和视频教程保持一致采用低版本(1.13.0)进行安装(因为随后进行的镜像拉取为低版本镜像)
yum -y install kubelet-1.13.0 kubeadm-1.13.0 kubernetes-cni-0.6.0 kubectl-1.13.0
systemctl enable kubelet && systemctl start kubelet
将上述代码写入一个init.sh文件中,然后sh init.sh进行脚本运行即可。
随后进行Docker镜像拉取(与master节点操作相同)。
拉取镜像完成之后,我们可以将之前的整句token输入,用于使node节点加入集群中。
# kubeadm join 192.168.1.108:6443 --token vgghhv.qjsvzv1wjbm1k631 --discovery-token-ca-cert-hash sha256:0688289f3b27978cd7ac91290d822d837c93595de09bad7ba4b99b24a8f56f0c`
(如果忘记可在master终端输入kubeadm token list
查看)
kubeadm token list
TOKEN TTL EXPIRES USAGES DESCRIPTION EXTRA GROUPS
ifq7qv.3beevw9jgs73c049 22h 2019-07-26T14:27:56+08:00 authentication,signing The default bootstrap token generated by 'kubeadm init'. system:bootstrappers:kubeadm:default-node-token
随后进行安装kube-flannel,重启docker即可(与master节点操作一致)
这样当你在master节点中查看时就已经完成添加了
# kubectl get nodes
NAME STATUS ROLES AGE VERSION
master.example.com Ready master 91m v1.13.0
node1.example.com Ready <none> 7m55s v1.13.0
到此我们的部署便已经初步完成了。
更多推荐
所有评论(0)