二、k8s快速入门之docker+Kubernetes平台搭建
centos | master | 192.168.100.10 |
---|---|---|
centos | node1 | 192.168.100.20 |
centos | node2 | 192.168.100.30 |
除特殊说明命令都需要在三台都执行
⭐️ k8s 的指令:
- kubeadm:用来初始化集群的指令
- kubelet: 在集群中的每个节点上用来启动Pod和容器
- kubectl: 用来与集群通信的命令行工具
⭐️ kubeadm 不能帮你安装或者管理 kubelet 或 kubectl, 所以你需要确保它们与通过 kubeadm 安装的控制平面的版本相匹配。 如果不这样做,则存在发生版本偏差的风险,可能会导致一些预料之外的错误和问题。 然而,控制平面与 kubelet 之间可以存在一个次要版本的偏差,但 kubelet 的版本不可以超过 API 服务器的版本。 例如,1.7.0 版本的 kubelet 可以完全兼容 1.8.0 版本的 API 服务器,反之则不可以
初始化设置–三台
systemctl stop firewalld
systemctl disable firewalld
setenforce 0 ####想要永久关闭请自己设置
swapoff -a ##想要永久关闭请自己设置
free
iptables -F
iptables -X
iptables -Z
修改名字
hostname set-hostname master
hostname set-hostname node1
hostname set-hostname node2
编辑hosts文件
[root@master ~]# cat /etc/hosts
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.100.10 master
192.168.100.20 node1
192.168.100.30 node2
把源换为阿里源
wget -O /etc/yum.repos.d/CentOS-Base.repo https://mirrors.aliyun.com/repo/Centos-7.repo
下载需要的组件
yum install -y conntrack ipvsadm ipset jq iptables curl sysstat libseccomp wget vim net-tools git
有些组件非必须
调整内核参数
vim /etc/sysctl.d/kubernetes.conf
##必须 开启ipv4桥接
net.bridge.bridge-nf-call-iptables=1
##必须 开启ipv6桥接
net.bridge.bridge-nf-call-ip6tables=1
##开启TCP连接中TIME-WAIT sockets的快速回收
net.ipv4.tcp_tw_recycle=0
#禁止使用swap空间,只有当系统00M时才允许使用它
vm.swappiness=0
#不检查物理内存是否够用
vm.overcommit_memory=1
#开启00M
vm.panic_on_oom=0
##表示同一用户同时最大可以创建的 inotify(通知) 实例 (每个实例可以有很多 watch(值班))
fs.inotify.max_user_instances=8192
## 表示同一用户同时可以添加的watch数目(watch一般是针对目录,决定了同时同一用户可以监控的目录数量)
##默认值 8192 在容器场景下偏小,在某些情况下可能会导致 inotify watch 数量耗尽,
##使得创建 Pod 不成功或者 kubelet 无法启动成功,
fs.inotify.max_user_watches=1048576
##max-file 表示系统级别的能够打开的文件句柄的数量, 一般如果遇到文件句柄达到上限时,
##会碰到 Too many open files 或者 Socket/File: Can’t open so many files 等错误
fs.file-max=52706963
##单个进程可分配的最大文件数
fs.nr_open=52706963
##禁用ipv6
net.ipv6.conf.all.disable_ipv6=1
##设置最大查看限制
net.netfilter.nf_conntrack_max=2310720
## 载入ip_conntrack模块
[root@master ~]# modprobe ip_conntrack
## 载入桥接模式防火墙
[root@master ~]# modprobe br_netfilter
###这里可以直接载入/etc/sysconfig/modules 中
cat > /etc/sysconfig/modules/ipvs.modules <
#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_wrr
modprobe -- ip_vs_sh
modprobe -- br_netfilter
modprobe -- ip_conntrack
EOF
[root@master ~]# sysctl -p /etc/sysctl.d/kubernetes.conf
net.bridge.bridge-nf-call-iptables = 1
net.bridge.bridge-nf-call-ip6tables = 1
net.ipv4.ip_forward = 1
net.ipv4.tcp_tw_recycle = 0
vm.swappiness = 0
vm.overcommit_memory = 1
vm.panic_on_oom = 0
fs.inotify.max_user_instances = 8192
fs.inotify.max_user_watches = 1048576
fs.file-max = 52706963
fs.nr_open = 52706963
net.ipv6.conf.all.disable_ipv6 = 1
net.netfilter.nf_conntrack_max = 23107120
配置时间同步
⭐️ centos7.5
自带了chrony
无需下载
1️⃣ master
操作
[root@master ~]# vim /etc/chrony.conf
server master iburst ##其余的全部删掉加上这条
allow 192.168.100.0/24
local stratum 10
systemctl restart chronyd;systemctl enable chronyd
2️⃣ node1
和node2
vim /etc/chrony.conf
server master iburst ##其余的全部删掉加上这条
systemctl restart chronyd;systemctl enable chronyd
3️⃣ 查看时间同步
chronyc sources
⭐️升级内核版本–三台
rpm -Uvh http://www.elrepo.org/elrepo-release-7.0-3.el7.elrepo.noarch.rpm
yum --enablerepo=elrepo-kernel install -y kernel-lt
grub2-set-default 'CentOS Linux (4.4.189-1.e17.elrepo.x86_64) 7 (Core)'
reboot
安装Docker
⭐️ 由于LVS以及加入到linux内核,所以开启IPVS的前提需要加载内核模块
1️⃣在三个节点都执行,初始化操作
cat > /etc/sysconfig/modules/ipvs.modules <
#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_wrr
modprobe -- ip_vs_sh
EOF
chmod 755 /etc/sysconfig/modules/ipvs.modules && bash /etc/sysconfig/modules/ipvs.modules && lsmod | grep -e ip_vs -e nf_conntrack_ipv4
2️⃣ 安装docker
⭐️kuberntesv1.15.1 支持18.09版本的docker
# step 1: 安装必要的一些系统工具
sudo yum install -y yum-utils device-mapper-persistent-data lvm2
# Step 2: 添加软件源信息
sudo yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# Step 3
sudo sed -i 's+download.docker.com+mirrors.aliyun.com/docker-ce+' /etc/yum.repos.d/docker-ce.repo
# Step 4: 更新并安装Docker-CE
sudo yum makecache fast
sudo yum -y install docker-ce
# Step 4: 开启Docker服务
sudo service docker start
# 注意:
# 官方软件源默认启用了最新的软件,您可以通过编辑软件源的方式获取各个版本的软件包。例如官方并没有将测试版本的软件源置为可用,您可以通过以下方式开启。同理可以开启各种测试版本等。
# vim /etc/yum.repos.d/docker-ce.repo
# 将[docker-ce-test]下方的enabled=0修改为enabled=1
#
# 安装指定版本的Docker-CE:
# Step 1: 查找Docker-CE的版本:
# yum list docker-ce.x86_64 --showduplicates | sort -r
# Loading mirror speeds from cached hostfile
# Loaded plugins: branch, fastestmirror, langpacks
# docker-ce.x86_64 17.03.1.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
# Available Packages
# Step2: 安装指定版本的Docker-CE: (VERSION例如上面的17.03.0.ce.1-1.el7.centos)
# sudo yum -y install docker-ce-[VERSION]
添加daemon.json
文件
mkdir /etc/docker
cat > /etc/docker/daemon.json <<EOF
{
"exec-opts": ["native.cgroupdriver-systemd"], ##默认的cgroup组为systemd 默认情况下有两个cgroupFS一个式systemd
"log-driver": "json-file", ##改存储的日志的存储格式
"log-opts": {
"max-size": "100m"
}
}
EOF
systemctl start docker;systemctl enable docker
//或者
sudo mkdir -p /etc/docker
sudo tee /etc/docker/daemon.json <<-'EOF'
{
"exec-opts": ["native.cgroupdriver-systemd"],
"registry-mirrors": ["https://89fk096n.mirror.aliyuncs.com"]
}
EOF
sudo systemctl daemon-reload
sudo systemctl restart docker
Kubeadm安装配置
1️⃣ 配置好yum
源
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
yum install --nogpgcheck -y kubelet-1.15.1 kubeadm-1.15.1 kubectl-1.15.1
systemctl start kubelet
systemctl enable kubelet
2️⃣ 使用工具把kubaedm工具压缩包上传到master节点(这个如果是网络不好拉去镜像慢,可以直接用这个办法,如果没有这个包可以看后面的网络拉取)
[root@master ~]# ls
kubeadm-basic.images.tar.gz
##解压
tar zxvf kubeadm-basic.images.tar.gz
3️⃣ 然后将这些镜像导入docker,这里我直接写了给脚本导入–master
[root@master ~]# cat docker.sh
#!/bin/bash
ls /root/kubeadm-basic.images >> /root/images.txt
cd /root/kubeadm-basic.images
for i in $(cat /root/images.txt)
do
docker load < $i
done
[root@master ~]# chmod +x docker.sh
4️⃣执行脚本
[root@master ~]# bash docker.sh
fe9a8b4f1dcc: Loading layer 43.87MB/43.87MB
d1e1f61ac9f3: Loading layer 164.5MB/164.5MB
Loaded image: k8s.gcr.io/kube-apiserver:v1.15.1
fb61a074724d: Loading layer 479.7kB/479.7kB
c6a5fc8a3f01: Loading layer 40.05MB/40.05MB
Loaded image: k8s.gcr.io/coredns:1.3.1
8a788232037e: Loading layer 1.37MB/1.37MB
30796113fb51: Loading layer 232MB/232MB
6fbfb277289f: Loading layer 24.98MB/24.98MB
Loaded image: k8s.gcr.io/etcd:3.3.10
aa3154aa4a56: Loading layer 116.4MB/116.4MB
Loaded image: k8s.gcr.io/kube-controller-manager:v1.15.1
e17133b79956: Loading layer 744.4kB/744.4kB
Loaded image: k8s.gcr.io/pause:3.1
15c9248be8a9: Loading layer 3.403MB/3.403MB
00bb677df982: Loading layer 36.99MB/36.99MB
Loaded image: k8s.gcr.io/kube-proxy:v1.15.1
e8d95f5a4f50: Loading layer 38.79MB/38.79MB
Loaded image: k8s.gcr.io/kube-scheduler:v1.15.1
Loaded image: k8s.gcr.io/kube-apiserver:v1.15.1
Loaded image: k8s.gcr.io/coredns:1.3.1
Loaded image: k8s.gcr.io/etcd:3.3.10
Loaded image: k8s.gcr.io/kube-controller-manager:v1.15.1
Loaded image: k8s.gcr.io/pause:3.1
Loaded image: k8s.gcr.io/kube-proxy:v1.15.1
Loaded image: k8s.gcr.io/kube-scheduler:v1.15.1
4️⃣ 查看
[root@master ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
k8s.gcr.io/kube-apiserver v1.15.1 68c3eb07bfc3 2 years ago 207MB
k8s.gcr.io/kube-controller-manager v1.15.1 d75082f1d121 2 years ago 159MB
k8s.gcr.io/kube-proxy v1.15.1 89a062da739d 2 years ago 82.4MB
k8s.gcr.io/kube-scheduler v1.15.1 b0b3c4c404da 2 years ago 81.1MB
k8s.gcr.io/coredns 1.3.1 eb516548c180 2 years ago 40.3MB
k8s.gcr.io/etcd 3.3.10 2c4adeb21b4f 2 years ago 258MB
k8s.gcr.io/pause 3.1 da86e6ba6ca1 3 years ago 742kB
5️⃣在把脚本和解压后的镜像目录传输到node1,2节点在执行同样操作,我这里就不演示了
6️⃣在master
创建kubeadm
设置yaml
模板
kubeadm config print init-defaults > kubeadm-config.yaml
7️⃣ 修改它的配置参数
[root@master ~]# cat kubeadm-config.yaml
apiVersion: kubeadm.k8s.io/v1beta2
bootstrapTokens:
- groups:
- system:bootstrappers:kubeadm:default-node-token
token: abcdef.0123456789abcdef
ttl: 24h0m0s
usages:
- signing
- authentication
kind: InitConfiguration
localAPIEndpoint:
advertiseAddress: 192.168.100.10 ##这里修改为本机ip
bindPort: 6443
nodeRegistration:
criSocket: /var/run/dockershim.sock
name: master
taints:
- effect: NoSchedule
key: node-role.kubernetes.io/master
---
apiServer:
timeoutForControlPlane: 4m0s
apiVersion: kubeadm.k8s.io/v1beta2
certificatesDir: /etc/kubernetes/pki
clusterName: kubernetes
controllerManager: {}
dns:
type: CoreDNS
etcd:
local:
dataDir: /var/lib/etcd
imageRepository: k8s.gcr.io
kind: ClusterConfiguration
kubernetesVersion: v1.15.1 ##注意
networking:
dnsDomain: cluster.local
podSubnet: "10.244.0.0/16" ##这里添加ip地址,因为fannl的网络插件和这个一样
serviceSubnet: 10.96.0.0/12
scheduler: {}
##添加以下,把默认的调度改为ipvs
---
apiVersion: kubeproxy.config.k8s.io/v1alpha1
kind: KubeProxyConfiguration
featureGates :
SupportIPVSProxyMode: true
mode: ipvs
8️⃣ 初始化kubeadmn
kubeadm init --config=kubeadm-config.yaml --experimental-upload-certs | tee kubeadm-init.log
9️⃣ 下面是初始化介绍
**--config :指定文件**
--experimental-upload-certs: 自动颁发证书 1.13.8才有这个命令
初始化操作主要经历了下面 15 个步骤,每个阶段均输出均使用[步骤名称]作为开头:
[init]:指定版本进行初始化操作。
[preflight]:初始化前的检查和下载所需要的 Docker 镜像文。。
[kubelet-start]:生成 Kubelet 的配置文件/var/lib/kubelet/config.yaml,没有这个文件 Kubelet 无法启动,所以初始化之前的 Kubelet 实际上启动失败。
[certificates]:生成 Kubernetes 使用的证书,存放在/etc/kubernetes/pki 目录中。
[kubeconfig]:生成 KubeConfig 文件,存放在/etc/kubernetes 目录中,组件之间通信需 要使用对应文件。
[control-plane]:使用/etc/kubernetes/manifest 目录下的 YAML 文件,安装 Master 组件。
[etcd]:使用/etc/kubernetes/manifest/etcd.yaml 安装 Etcd 服务。
[wait-control-plane]:等待 control-plan 部署的 Master 组件启动。
[apiclient]:检查 Master 组件服务状态。
[uploadconfig]:更新配置。
[kubelet]:使用 configMap 配置 Kubelet。
[patchnode]:更新 CNI 信息到 Node 上,通过注释的方式记录。
[mark-control-plane]:为当前节点打标签,打了角色 Master,和不可调度标签,这样默 认就不会使用 Master 节点来运行 Pod。
[bootstrap-token]:生成的 Token 需要记录下来,后面使用 kubeadm join 命令往集群中 添加节点时会用到。
[addons]:安装附加组件 CoreDNS 和 kube-proxy。
网络拉取
1️⃣ 配置kubeadm
配置文件
[root@master ~]# kubeadm config print init-defaults > kubeadm.yaml
[root@master ~]# vim kubeadm.yaml
[root@master ~]# cat kubeadm.yaml
apiVersion: kubeadm.k8s.io/v1beta2
bootstrapTokens:
- groups:
- system:bootstrappers:kubeadm:default-node-token
token: abcdef.0123456789abcdef
ttl: 24h0m0s
usages:
- signing
- authentication
kind: InitConfiguration
localAPIEndpoint:
advertiseAddress: 192.168.200.10
bindPort: 6443
nodeRegistration:
criSocket: /var/run/dockershim.sock
name: master
taints:
- effect: NoSchedule
key: node-role.kubernetes.io/master
---
apiServer:
timeoutForControlPlane: 4m0s
apiVersion: kubeadm.k8s.io/v1beta2
certificatesDir: /etc/kubernetes/pki
clusterName: kubernetes
controllerManager: {}
dns:
type: CoreDNS
etcd:
local:
dataDir: /var/lib/etcd
imageRepository: registry.aliyuncs.com/google_containers ##修改拉取镜像仓库
kind: ClusterConfiguration
##版本号需要修改为15
kubernetesVersion: v1.15.0
networking:
dnsDomain: cluster.local
serviceSubnet: 10.96.0.0/12
podSubnet: "10.244.0.0/16"
scheduler: {}
---
apiVersion: kubeproxy.config.k8s.io/v1alpha1
kind: KubeProxyConfiguration
featureGates :
SupportIPVSProxyMode: true
mode: ipvs
2️⃣ 初始化kubeadmn
kubeadm init --config kubeadm.yaml
3️⃣ 假如初始化失败就用下面方法(加入节点失败也通用)
kubeadm reset
ifconfig cni0 down
ip link delete cni0
ifconfig flannel.1 down
ip link delete flannel.1
rm -rf /var/lib/cni/
后序操作
1️⃣ 按照提示复制创建kubelet和api的缓存文件(执行完成kubeadm init
操作后面会有这个直接复制即可)
mkdir -p $HOME/.kube
sudo cp -i /etc/kubernetes/admin.conf $HOME/.kube/config
sudo chown $(id -u):$(id -g) $HOME/.kube/config
2️⃣ 查看节点, 如果是NotReady
因为网络没有创建
[root@master ~]# kubectl get node
NAME STATUS ROLES AGE VERSION
master NotReady master 3m6s v1.15.1
3️⃣ 布置flannel
[root@master ~]# mkdir flannel
[root@master ~]# cd flannel
[root@master ~]# kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
podsecuritypolicy.policy/psp.flannel.unprivileged created
clusterrole.rbac.authorization.k8s.io/flannel created
clusterrolebinding.rbac.authorization.k8s.io/flannel created
serviceaccount/flannel created
configmap/kube-flannel-cfg created
daemonset.apps/kube-flannel-ds created
4️⃣ 查看flannel组件
[root@master ~]# kubectl get pod -n kube-system
NAME READY STATUS RESTARTS AGE
coredns-5c98db65d4-kvkbl 0/1 ContainerCreating 0 46m
coredns-5c98db65d4-qjhm2 0/1 ContainerCreating 0 46m
etcd-master 1/1 Running 0 45m
kube-apiserver-master 1/1 Running 0 45m
kube-controller-manager-master 1/1 Running 0 45m
kube-flannel-ds-bfw2x 1/1 Running 0 37m
kube-proxy-tvbgm 1/1 Running 0 46m
kube-scheduler-master 1/1 Running
5️⃣ 看网卡
ifconfig
flannel.1: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1450
inet 10.244.0.0 netmask 255.255.255.255 broadcast 10.244.0.0
ether 02:eb:0e:38:30:4e txqueuelen 0 (Ethernet)
RX packets 0 bytes 0 (0.0 B)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 0 bytes 0 (0.0 B)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
查看移除master节点污点
⭐️ 移除后就可以在master
节点启动pod
和存储镜像了
1️⃣ 查看
kubectl describe node master
Taints: node-role.kubernetes.io/master:NoSchedule ##NoSchedule就代表不可调度
NoSchedule :表示 k8s 将不会将 Pod 调度到具有该污点的 Node 上 PreferNoSchedule :表示 k8s 将尽量避免将 Pod 调度到具有该污点的 Node 上 NoExecute :表示 k8s 将不会将 Pod 调度到具有该污点的 Node 上,同时会将 Node 上已经存在的 Pod 驱逐出去
2️⃣ 修改
[root@master ~]# kubectl edit node master
spec:
podCIDR: 10.244.0.0/24
taints:
- effect: PreferNoSchedule ##原来是NoSchedule
key: node-role.kubernetes.io/master
3️⃣ 再次查看
kubectl describe node master
Taints: node-role.kubernetes.io/master:PreferNoSchedule
子节点加入
1️⃣ 查看加入命令,在各个node
中使用
[root@master ~]# kubeadm token create --print-join-command
kubeadm join 192.168.100.10:6443 --token 9nx4cb.2zjgaeo5ju98fnq3 --discovery-token-ca-cert-hash sha256:4d4eb15f1f4c36f1283b0a319f74b8e79110d263830d41d82c82b3c2dbe326b2
2️⃣ 查看
[root@master ~]# kubectl get node
NAME STATUS ROLES AGE VERSION
master Ready master 65m v1.15.1
node1 NotReady <none> 13s v1.15.1
node2 NotReady <none> 5s v1.15.1
3️⃣ 移除node
kubectl delete node [node名]
4️⃣ 查看加入节点命令
kubeadm token create --print-join-command