单台主机搭建kubernetes多master高可用集群

使用家里闲置的单台家用台式机搭建kubernetes高可用多master集群环境

硬件介绍

cpu i5-10600KF六核心 十二线程
内存:8G*2 、16G*2 总共48G
磁盘:SSD480G*2 SSD250G*2 HDD2T*1

资源规划

主机:win10专业版
虚拟机:vmware:wmware16 por

centos7虚拟机总共9个,名称和资源划分如下

9台centos7虚拟机中5台用于k8s集群,3台用于数据存储,1台用于测试
k8s集群包含3个master节点、2个node节点。3台master所在虚拟机安装nginx、Keepalived、ipvs实现高可用
数据存储包含一个mysql集群和一个gluster文件系统

centos7安装和环境配置

假设已经使用vmware安装一台centos7虚拟机,进去虚拟机,进行如下设置

1关闭防火墙和NetworkManager
systemctl stop NetworkManager && systemctl disable NetworkManager
systemctl stop firewalld && systemctl disable firewalld 
2永久关闭selinux
setenforce 0
sed -i 's/SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config;cat /etc/selinux/config 
3修改主机名
hostnamectl set-hostname master-1
4修改hosts文件
cat >> /etc/hosts << EOF
192.168.2.191    master-1
192.168.2.192    master-2
192.168.2.193    master-3
192.168.2.194    node-1  
192.168.2.195    node-2  
EOF
5禁用swap
swapoff -a
sed -i.bak '/swap/s/^/#/' /etc/fstab
6内核参数修改
cat <<EOF >  /etc/sysctl.d/k8s.conf
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_forward=1
EOF

立即生效:
sysctl -p /etc/sysctl.d/k8s.conf
7新增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

##########################
    [] 中括号中的是repository id,唯一,用来标识不同仓库
    name 仓库名称,自定义
    baseurl 仓库地址
    enable 是否启用该仓库,默认为1表示启用
    gpgcheck 是否验证从该仓库获得程序包的合法性,1为验证
    repo_gpgcheck 是否验证元数据的合法性 元数据就是程序包列表,1为验证
    gpgkey=URL 数字签名的公钥文件所在位置,如果gpgcheck值为1,此处就需要指定gpgkey文件的位置,如果gpgcheck值为0就不需要此项了
8更新缓存
yum clean all
yum -y makecache
9安装命令补全
1 安装bash-completion
yum -y install bash-completion

2 加载bash-completion
source /etc/profile.d/bash_completion.sh
10安装docker
1安装依赖包
    yum install -y yum-utils   device-mapper-persistent-data   lvm2

2设置Docker源
	#推荐使用国内的
    yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo


3安装Docker CE
    docker可安装版本查看
    yum list docker-ce --showduplicates | sort -r

安装docker
    yum install docker-ce-20.10.9 docker-ce-cli-20.10.9 containerd.io -y

4启动Docker并开机自启
	systemctl start docker
	systemctl enable docker


5配置镜像加速
    由于Docker Hub的服务器在国外,下载镜像会比较慢,可以配置镜像加速器提速

    配置daemon.json文件:
    mkdir -p /etc/docker
    vim /etc/docker/daemon.json
    {
    "registry-mirrors": ["https://23h04een.mirror.aliyuncs.com"]
    }


6修改Cgroup Driver
    修改daemon.json 新增‘”exec-opts”: [“native.cgroupdriver=systemd”’
    修改cgroupdriver是为了消除告警:
      [WARNING IsDockerSystemdCheck]: detected “cgroupfs” as the Docker cgroup driver...

    vim /etc/docker/daemon.json 
    {
      "registry-mirrors": ["https://23h04een.mirror.aliyuncs.com"],
      "exec-opts": ["native.cgroupdriver=systemd"]
    }

7重启docker
    systemctl daemon-reload
    systemctl restart docker
11安装iptables

ipvs

1安装iptables
  yum install iptables-services -y

2禁用iptables
  systemctl disable iptables && systemctl stop iptables

3清空防火墙规则
  iptables -F

4创建ipvs.modules文件
  vim /etc/sysconfig/modules/ipvs.modules
    #!/bin/bash
    ipvs_modules="ip_vs ip_vs_lc ip_vs_wlc ip_vs_rr ip_vs_wrr ip_vs_lblc ip_vs_lblcr ip_vs_dh ip_vs_sh ip_vs_nq ip_vs_sed ip_vs_ftp nf_conntrack"
    for kernel_module in ${ipvs_modules}; do
     /sbin/modinfo -F filename ${kernel_module} > /dev/null 2>&1
     if [ 0 -eq 0 ]; then
     /sbin/modprobe ${kernel_module}
     fi
    done

5执行脚本
 bash /etc/sysconfig/modules/ipvs.modules && lsmod | grep ip_vs
 #不开启ipvs将会使用iptables进行数据包转发,但是效率低,所以官网推荐需要开通ipvs
12安装其他必要软件
yum install -y yum-utils device-mapper-persistent-data lvm2 wget net-tools nfs-utils lrzsz gcc gcc-c++ make cmake libxml2-devel openssl-devel curl curl-devel unzip sudo ntp libaio-devel wget vim ncurses-devel autoconf automake zlib-devel  python-devel epel-release openssh-server socat  ipvsadm conntrack ntpdate telnet rsync

centos7虚拟机快速创建

1.关闭上虚拟机
2.使用vmware的导出OVF功能,导出OVF
3.使用导出的OVF文件快速创建多个虚拟机
4.修改每台虚拟机的hostname和网络配置,指定不同的内网ip,重启网络,即可xshell远程连接

部署nginx、keepalived

在所有master节点部署nginx及keepalived
如下步骤仅需在master1、master2、master3三台虚拟机执行

安装nginx、keepalived
rpm -Uvh  http://nginx.org/packages/centos/7/noarch/RPMS/nginx-release-centos-7-0.el7.ngx.noarch.rpm
yum install nginx keepalived -y

编辑ngin配置文件
vim /etc/nginx/nginx.conf
  user nginx;
  worker_processes auto;
  error_log /var/log/nginx/error.log;
  pid /run/nginx.pid;

  include /usr/share/nginx/modules/*.conf;

  events {
      worker_connections 1024;
  }

  # 四层负载均衡,为两台Master apiserver组件提供负载均衡
  stream {

      log_format  main  '$remote_addr $upstream_addr - [$time_local] $status $upstream_bytes_sent';

      access_log  /var/log/nginx/k8s-access.log  main;

      upstream k8s-apiserver {
         server 192.168.2.191:6443;   # centos7-1-master1 APISERVER IP:PORT
         server 192.168.2.192:6443;   # centos7-1-master2 APISERVER IP:PORT
         server 192.168.2.193:6443;   # centos7-1-master3 APISERVER IP:PORT
      }
      
      server {
         listen 64430; # 由于nginx与master节点复用,这个监听端口不能是6443,否则会冲突
         proxy_pass k8s-apiserver;
      }
  }

  http {
      log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
                        '$status $body_bytes_sent "$http_referer" '
                        '"$http_user_agent" "$http_x_forwarded_for"';

      access_log  /var/log/nginx/access.log  main;

      sendfile            on;
      tcp_nopush          on;
      tcp_nodelay         on;
      keepalive_timeout   65;
      types_hash_max_size 2048;

      include             /etc/nginx/mime.types;
      default_type        application/octet-stream;

      server {
          listen       8000 default_server;
          server_name  _;

          location / {
          }
      }
  }

启动nginx
systemctl start nginx &&  systemctl enable nginx

编辑keepalive配置文件
>注意每台虚拟机keepalived.conf的带#注释部分需设置不一样的

mv  /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.bak
vim /etc/keepalived/keepalived.conf
   global_defs { 
     notification_email { 
       acassen@firewall.loc 
       failover@firewall.loc 
       sysadmin@firewall.loc 
     } 
     notification_email_from Alexandre.Cassen@firewall.loc  
     smtp_server 127.0.0.1 
     smtp_connect_timeout 30 
     router_id NGINX_MASTER
  } 

  vrrp_script check_nginx {
      script "/etc/keepalived/check_nginx.sh"
  }

  vrrp_instance VI_1 { 
      state BACKUP 
      interface ens33  # 修改为实际网卡名,根据实际网卡名字设置
      virtual_router_id 192 # VRRP 路由 ID实例,每个实例是唯一的 ,三台虚拟机设置成不一样
      priority 100    # 优先级,三台虚拟机设置成不一样 
      advert_int 1    # 指定VRRP 心跳包通告间隔时间,默认1秒 
      authentication { 
          auth_type PASS      
          auth_pass 1111 
      }  
      # 虚拟IP
      virtual_ipaddress { 
          192.168.2.100/24
      } 
      track_script {
          check_nginx
      } 
  }

创建keepalived用的判断故障脚本
vim /etc/keepalived/check_nginx.sh 
  #!/bin/bash
  count=$(ps -ef |grep nginx | grep sbin | egrep -cv "grep|$$")
  if [ "$count" -eq 0 ];then
      systemctl stop keepalived
  fi
  [root@k8s-master2 ~]# chmod +x /etc/keepalived/check_nginx.sh
  #注:keepalived根据脚本返回状态码(0为工作正常,非0不正常)判断是否故障转移。  

启动keepalived
systemctl start keepalived && systemctl enable keepalived

测试
...

安装k8s

通过上一步操作得到5台虚拟机
在每一台虚拟机执行如下操作

1可安装版本查看
yum list kubelet --showduplicates | sort -r
2安装kubelet、kubeadm和kubectl
1 安装
    yum install -y kubelet-1.23.5 kubeadm-1.23.5 kubectl-1.23.5
      #kubelet 运行在集群所有节点上,用于启动Pod和容器等对象的工具
      #kubeadm 用于初始化集群,启动集群的命令工具
      #kubectl 用于和集群通信的命令行,通过kubectl可以部署和管理应用,查看各种资源,创建、删除和更新各种组件

2 启动kubelet并设置开机启动
    systemctl enable kubelet && systemctl start kubelet

3 kubectl命令补全
    echo "source <(kubectl completion bash)" >> ~/.bash_profile
    source .bash_profile 
3准备kubernete必要容器镜像

Kubernetes几乎所有的安装组件和Docker镜像都放在goolge自己的网站上,直接访问可能会有网络问题
解决办法:
从阿里云镜像仓库下载镜像,拉取到本地以后改回默认的镜像tag。使用如下脚本实现。

1 镜像下载的脚本
  cat image.sh 
        #!/bin/bash
        url=registry.aliyuncs.com/google_containers
        version=v1.23.5
        images=(`kubeadm config images list --kubernetes-version=$version|awk -F '/' '{print $2}'`)
        for imagename in ${images[@]} ; do
        docker pull $url/$imagename
        docker tag $url/$imagename k8s.gcr.io/$imagename
        docker rmi -f $url/$imagename
        done
        #url为阿里云镜像仓库地址,version为安装的kubernetes版本。

        docker pull registry.aliyuncs.com/google_containers/coredns:1.8.6 && docker tag registry.aliyuncs.com/google_containers/coredns:1.8.6 k8s.gcr.io/coredns/coredns:v1.8.6
        #coredns镜像可能要手动pull,kubeadm执行初始化时需要

2 运行脚本image.sh下载镜像
    sh image.sh
    # 注意 :每个节点都要执行,否则部分k8s必要的容器创建不成功
4初始化Master

任选一个master节点执行本部分操作(此处选的master-1)。

kubeadm init --apiserver-advertise-address=192.168.2.191 --kubernetes-version v1.23.5 --service-cidr=10.96.0.0/12 --pod-network-cidr=10.244.0.0/16 --upload-certs  --control-plane-endpoint 192.168.2.100:64430
# 192.168.2.100 是vip
#记录上述面命令安装成功后的输出,后面需要这个命令将node节点和其他master节点加入集群中。
#注意master节点加入和node节点加入使用的参数是不一样的,如下图,上面一条是master用的、下面一条是node用的

如果初始化失败,可执行kubeadm reset后重新初始化
  kubeadm reset
  rm -rf $HOME/.kube/config

加载环境变量,否则执行kubectl get node 会报错The connection to the server localhost:8080 was refused
  echo "export KUBECONFIG=/etc/kubernetes/admin.conf" >> ~/.bash_profile
  source .bash_profile
拷贝证书(忘了是否必要执行次步骤以及何时执行)-----------------------------------?????
  scp  root@192.168.2.191:/etc/kubernetes/pki/ca.crt  /etc/kubernetes/pki/ca.crt 
  scp  root@192.168.2.191:/etc/kubernetes/pki/ca.key  /etc/kubernetes/pki/ca.key 
  scp  root@192.168.2.191:/etc/kubernetes/pki/sa.key  /etc/kubernetes/pki/sa.key 
  scp  root@192.168.2.191:/etc/kubernetes/pki/sa.pub  /etc/kubernetes/pki/sa.pub 
  scp  root@192.168.2.191:/etc/kubernetes/pki/front-proxy-ca.crt  /etc/kubernetes/pki/front-proxy-ca.crt 
  scp  root@192.168.2.191:/etc/kubernetes/pki/front-proxy-ca.key  /etc/kubernetes/pki/front-proxy-ca.key 
  scp  root@192.168.2.191:/etc/kubernetes/pki/etcd/ca.crt  /etc/kubernetes/pki/etcd/ca.crt 
  scp  root@192.168.2.191:/etc/kubernetes/pki/etcd/ca.key  /etc/kubernetes/pki/etcd/ca.key 
  scp  root@192.168.2.191:/etc/kubernetes/admin.conf  /etc/kubernetes/admin.conf 
加入集群

在加入集群前先关闭nginx ,预防访问192.168.2.100:64430被路由到master-2、master-2上导致添加失败
因为有监控脚本,当nginx关闭后,对应主机上的vip也会关闭
等所有节点都成功加入集群,再启动nginx

在master-2、master-3 执行:  
  kubeadm join 192.168.2.100:64430 --token o0l7ya.8sr0b70ywafxe1m9 \
--discovery-token-ca-cert-hash sha256:xxx \
--control-plane --certificate-key xxx

  echo "export KUBECONFIG=/etc/kubernetes/admin.conf" >> /etc/profile
  source /etc/profile

在node-1、node-2 执行:
  kubeadm join 192.168.2.100:64430 --token o0l7ya.8sr0b70ywafxe1m9 \
--discovery-token-ca-cert-hash sha256:xxx 

添加成功会提示如下信息:

在master-1查看所有节点状态:

  #图示所有的节点状态正常
安装calico网络

为什么不用flannel,好像安装时遇到过问题搞不好,就用了calico

在任意主节点下载calico.yaml
  wget https://docs.projectcalico.org/manifests/calico.yaml --no-check-certificate

修改calico.yaml (忽略此步骤)
  ...
  #当使用kubeadm时,PodIP的范围应该与kubeadm init的清单文件中的"podSubnet"字段或者"--pod-network-cidr"选项填写的值相

查看calico.yaml用了哪些容器,并在所有节点上pull容器
  docker pull docker.io/calico/cni:v3.23.1
  docker pull docker.io/calico/kube-controllers:v3.23.1
  docker pull docker.io/calico/node:v3.23.1

在该主节点执行安装
  kubectl apply -f calico.yaml

查看pod状态
  kubectl get pods --all-namespaces
  #状态应当全部是running

在k8s安装Dashboard

Dashboard提供了可以实现集群管理、工作负载、服务发现和负载均衡、存储、字典配置、日志视图等功能。

下载yaml
  dashboard:v2.5.1已支持k8s:1.23.x
  wget https://raw.githubusercontent.com/kubernetes/dashboard/v2.5.1/aio/deploy/recommended.yaml

修改yaml(镜像可以支持下载忽略此步骤)
  #修改镜像地址(由于默认的镜像仓库网络访问不通,故改成阿里镜像)
  #sed -i 's/kubernetesui/registry.cn-hangzhou.aliyuncs.com\/loong576/g' recommended.yaml

  token失效较快,可设置参数延长失效时间- --token-ttl=432000,位置如下

映射到主机端口
  sed -i '/targetPort: 8443/a\ \ \ \ \ \ nodePort: 30001\n\ \ type: NodePort' recommended.yaml
  #配置NodePort,外部通过https://NodeIp:NodePort 访问Dashboard,此时端口为30001

部署
  kubectl apply -f recommended.yaml

状态查看
  kubectl get all -n kubernetes-dashboard 

令牌生成
  创建service accou  nt并绑定默认cluster-admin管理员集群角色:

创建用户
kubectl create serviceaccount dashboard-admin -n kube-system

用户授权
kubectl create clusterrolebinding dashboard-admin --clusterrole=cluster-admin --serviceaccount=kube-system:dashboard-admin

令牌查看
kubectl describe secrets -n kube-system $(kubectl -n kube-system get secret | awk '/dashboard-admin/{print $1}')

访问测试
  外部通过https://NodeIp:NodePort 访问Dashboard,此时端口为30001,默认运行在3个master任意一节点上,需要手动查看哪个机子开启了30001端口
  选择token方式登录,输入“3.4 令牌查看” 获得的token,即可进入页面

注意:
  默认情况下只能使用https访问,但chrome可能会提示不安全,此时在浏览器当前页面下键盘敲击thisisunsafe可继续访问,
  火狐浏览器可正常进入,不会提示不安全。

未完

posted @ 2022-04-13 22:57  tangshow  阅读(899)  评论(0编辑  收藏  举报