Kubernetes 介绍
Kubernetes 简介
Kubernetes 是 Google 在 2014 年 6 月开源的一个容器集群管理系统,使用 GO 语言开发,Kubernetes 简称 K8S。K8S 是 Google 内部一个叫 Borg 的容器集群管理系统衍生出来的,Borg已经在 Google 大规模生产运行十年之久。
K8S 主要用于自动化部署、扩展和管理容器应用,提供了资源调度、部署管理、服务发现、扩容缩容、监控等一整套功能。K8S 的目标是让部署容器化应用简单高效。2015 年 7月,Kubernetes v1.0 版本正式发布,最新版本详见Kubernetes官网
Kubernetes 主要功能
- 数据卷
Pod 中容器之间共享数据,可以使用数据卷。 - 应用程序监控检查
容器内服务可能进程阻塞无法处理请求,可以设置监控检查策略保证应用健壮性。 - 复制应用程序实例
控制器维护着 Pod 副本数量,保证一个 Pod 或一组同类的 Pod 数量始终可用。 - 弹性伸缩
根据设定的指标(CPU 利用率)自动缩放 Pod 副本数。 - 服务发现
使用环境变量或 DNS 服务插件保证容器中程序发现 Pod 入库访问地址。 - 负载均衡
一组 Pod 副本分配一个私有的集群 IP 地址,负载均衡转发请求到后端容器。在集群内部其他 Pod 可以通过这个 cluster IP 访问应用。 - 滚动更新
更新服务不中断,一次更新一个 Pod,而不是同时删除整个服务。类似于灰度发布。 - 服务编排
通过文件描述部署服务,使得应用程序部署变得更高效。 - 资源监控
node 节点组件集成 cAdvisor 资源收集工具,可通过 Heapster 汇总整个集群节点资源数据,然后存储到 InfluxDB 时序数据库,再由Grafana 展示。、 - 提供认证和授权
支持角色访问控制(RBAC 基于角色的权限访问控制 Role-Based Access Control)认证授权等策略。基本对象概念
- Pod
Pod 是最小部署单元,一个 Pod 由一个或多个容器组成,Pod 中容器共享存储和网络,
在同一台 docker 主机上运行。 - Service
Service 是一个应用服务抽象,定义了 Pod 逻辑集合和访问这个 Pod 集合的策略。
Service 代理 Pod 集合对外表现是为一个访问入口,分配一个集群 IP 地址,来自这个 IP的请求将负载均衡转发后端 Pod 中的容器。
Service 通过 Label Selector 选择一组 Pod 提供服务。 - Volume
数据卷,共享 Pod 中容器使用的数据。 - Namespace
命名空间将对象逻辑上分配到不同 namespace,可以是不同的项目、用户等区分管理,并设定控制策略,从而实现多租户。
命名空间也成为虚拟集群。 - Label
标签用户区分对象(如 Pod、Service),键/值对存在;每个对象可以有多个标签,通过标签关联对象。 - ReplicaSet(RS)
下一代 Replication Controller(RC)。确保任何给定时间制定的 Pod 副本数量,并提供声明式更新等功能。
RC 与 RS 唯一区别就是 label selector 支持不同,RS 支持新的基于集合的标签,RC 仅支持基于等式的标签。推荐使用 RS,后面 RC 将可能被淘汰。 - Deployment
Deployment 是一个更高层的 API 对象,它管理 ReplicaSets,意味着可能永远都不需要直接操作 RS 对象。 - StatefulSet
StatefulSet 适合持久性的应用程序,有唯一的网络标志符(IP),持久存储,有序的部署、扩展、删除和滚动更新。 - DaemonSet
DaemonSet 确保所有(或一些)节点运行同一个 Pod,当节点加入 Kubernetes 集群中,Pod 会被调度到该节点上运行,当节点从集群中移除时,DaemonSet 的 Pod 会被删除。删除DaemonSet 会清理它所有创建的 Pod。例如监控服务,可以使用 DaemonSet 对象管理。 - Job
一次性任务,运行完成后 Pod 销毁,不再重新启动新容器。还可以任务定时运行。系统架构及组件功能
Master 组件:
- kube-apiserver
Kubernetes API,集群的统一入口,各组件协调者,以 HTTP API 提供接口服务,所有对象资源的增删改查和监听操作都交给 APIServer 处理后再提交给 Etcd 存储。 - kube-controller-manager
处理集群中常规后台任务,一个资源对应一个控制器,而 ControllerManager 就是负责管理这些控制器的。 - kube-scheduler
根据调度算法为新创建的 Pod 选择一个 Node 节点。Node 组件:
- kubelet
kubelet 是 Master 在 Node 节点上的 Agent,管理本机运行容器的生命周期,比如创建容器、Pod 挂载数据卷、下载 secret、获取容器和节点状态等工作。kubelet 将每个 Pod 转换成一组容器。 - kube-proxy
在 Node 节点上实现 Pod 网络代理,维护网络规则和四层负载均衡工作,代理 iptables做防火墙策略。 - docker 或 rocket/rkt
运行容器。第三方服务:
- etcd
分布式键值存储系统,负责集群的持久化。
用于保持集群状态,比如 Pod、Service 等对象信息。使用 kubeadm 部署 kubenetes 集群
安装环境
[root@jjh ~]# cat /etc/hosts
192.168.0.36 jjh1
192.168.0.42 jjh2
192.168.0.43 jjh3安装 docker
将 docker 的镜像仓库改为国内的[root@jjh ~]# yum -y install yum-utils device-mapper-persistent-data lvm2
[root@jjh ~]# yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
[root@jjh ~]# yum -y install docker-ce
[root@jjh ~]# systemctl start docker
[root@jjh ~]# systemctl enable docker[root@jjh ~]# vim /etc/docker/daemon.json
{
"registry-mirrors": ["https://registry.docker-cn.com"]
}
[root@jjh ~]# systemctl restart docker关闭 swap
[root@jjh ~]# swapoff -a
[root@jjh ~]# echo "/usr/sbin/swapoff -a" >> /etc/rc.local
[root@jjh ~]# chmod +x /etc/rc.local配置内核参数
[root@jjh ~]# vim /etc/sysctl.d/k8s.conf
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.ipv4.ip_nonlocal_bind = 1
net.ipv4.ip_forward = 1
vm.swappiness=0
[root@jjh ~]# sysctl --system加载必要的内核模块
由于我们无法访问 kubeadm 官网上提供的源,所以选择阿里的镜像站[root@jjh ~]# vim /etc/sysconfig/modules/ipvs.modules
#!/bin/bash
modprobe -- ip_vs
modprobe -- ip_vs_rr
modprobe -- ip_vs_wrr
modprobe -- ip_vs_sh
modprobe -- nf_conntrack_ipv4
[root@jjh ~]# chmod +x /etc/sysconfig/modules/ipvs.modules
[root@jjh ~]# /etc/sysconfig/modules/ipvs.modules[root@jjh ~]# vim /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配置 master 节点
安装所需软件包
使用 kubeadm config print init-defaults > kubeadm-init.yaml 打印出默认配置,然后在根据自己的环境修改配置,尤其是镜像,在国外,默认的下不下来[root@jjh1 ~]# yum install kubeadm kubectl kubelet ipvsadm -y
[root@jjh1 ~]# kubeadm config print init-defaults > kubeadm-init.yaml
[root@jjh1 ~]# vim kubeadm-init.yamlapiVersion: 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.0.36 ## master内网IP
bindPort: 6443
nodeRegistration:
criSocket: /var/run/dockershim.sock
name: jjh1
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.cn-hangzhou.aliyuncs.com/google_containers ## 更改
kind: ClusterConfiguration
kubernetesVersion: v1.20.0
networking:
dnsDomain: cluster.local
serviceSubnet: 10.96.0.0/12
scheduler: {}
---
apiVersion: kubeproxy.config.k8s.io/v1alpha1 ## 添加
kind: KubeProxyConfiguration
mode: "ipvs"可以预下载镜像
[root@jjh1 ~]# kubeadm config images pull --config kubeadm-init.yaml
[root@jjh1 ~]# docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
registry.cn-hangzhou.aliyuncs.com/google_containers/kube-proxy v1.20.0 10cc881966cf 9 days ago 118MB
registry.cn-hangzhou.aliyuncs.com/google_containers/kube-apiserver v1.20.0 ca9843d3b545 9 days ago 122MB
registry.cn-hangzhou.aliyuncs.com/google_containers/kube-controller-manager v1.20.0 b9fa1895dcaa 9 days ago 116MB
registry.cn-hangzhou.aliyuncs.com/google_containers/kube-scheduler v1.20.0 3138b6e3d471 9 days ago 46.4MB
registry.cn-hangzhou.aliyuncs.com/google_containers/etcd 3.4.13-0 0369cf4303ff 3 months ago 253MB
registry.cn-hangzhou.aliyuncs.com/google_containers/coredns 1.7.0 bfe3a36ebd25 6 months ago 45.2MB
registry.cn-hangzhou.aliyuncs.com/google_containers/pause 3.2 80d28bedfe5d 10 months ago 683kB初始化 master 节点
//10.244.0.0/16 是 flannel 网络的默认网段[root@jjh1 ~]# systemctl start kubelet
[root@jjh1 ~]# systemctl enable kubelet
[root@jjh1 ~]# kubeadm init --pod-network-cidr=10.244.0.0/16 --image-repository=registry.cn-hangzhou.aliyuncs.com/google_containers
......
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.0.36:6443 --token xzdklu.nf4lx1djq61i2kdx \
--discovery-token-ca-cert-hash sha256:9cc9686dda3a41b283c7182fd13df1eb98992e5d74a7c7ac03bd25b0d63f90ce
kubeadm init 主要执行了以下操作:
[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
为 kubectl 准备 Kubeconfig 文件
kubectl 默认会在执行的用户家目录下面的.kube 目录下寻找 config 文件。这里是将在初始化时[kubeconfig]步骤生成的 admin.conf 拷到.kube/config
[root@jjh1 ~]# mkdir -p $HOME/.kube |
在该配置文件中,记录了 API Server 的访问地址,所以后面直接执行 kubectl 命令就可以正常连接到 API Server 中
验证 master 各组件运行状态
[root@jjh1 ~]# kubectl get cs |
出现报错,解决思路:
注释掉/etc/kubernetes/manifests下的kube-controller-manager.yaml和kube-scheduler.yaml的- – port=0
确认kube-scheduler和kube-controller-manager组件配置是否禁用了非安全端口
[root@jjh1 ~]# cd /etc/kubernetes/manifests |
重新验证一下
[root@jjh1 ~]# kubectl get cs |
配置 node 节点
[root@jjh2 ~]# yum install kubeadm kubectl kubelet ipvsadm -y |
看见这段话表示成功:
This node has joined the cluster:
- Certificate signing request was sent to apiserver and a response was received.
- The Kubelet was informed of the new secure connection details.
Run ‘kubectl get nodes’ on the control-plane to see this node join the cluster.
回到 master 节点看看 node 信息[root@jjh1 ~]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
jjh1 NotReady control-plane,master 5m21s v1.20.0
jjh2 NotReady <none> 23s v1.20.0
jjh3 NotReady <none> 21s v1.20.0部署网络插件 flannel
Master 节点 NotReady 的原因就是因为没有使用任何的网络插件,此时 Node 和 Master的连接还不正常。目前最流行的 Kubernetes 网络插件有 Flannel、Calico、Canal、Weave 这里选择使用 flannel。
在 master 节点上都有执行,执行完成后需要等 flannel 的 pods 运行起来,这需要点时间:外网无法访问,就直接下到本地安装好了[root@jjh1 ~]# kubectl apply -f https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml
The connection to the server raw.githubusercontent.com was refused - did you specify the right host or port?
链接: https://pan.baidu.com/s/13NwlWF24TUpDm23uj66V5Q
提取码: here现在重新 get 验证一下,看看是否安装成功[root@jjh1 ~]# ls
flannel.yaml kubeadm-init.yaml
[root@jjh1 ~]# kubectl apply -f flannel.yaml
podsecuritypolicy.policy/psp.flannel.unprivileged created
Warning: rbac.authorization.k8s.io/v1beta1 ClusterRole is deprecated in v1.17+, unavailable in v1.22+; use rbac.authorization.k8s.io/v1 ClusterRole
clusterrole.rbac.authorization.k8s.io/flannel created
Warning: rbac.authorization.k8s.io/v1beta1 ClusterRoleBinding is deprecated in v1.17+, unavailable in v1.22+; use rbac.authorization.k8s.io/v1 ClusterRoleBinding
clusterrolebinding.rbac.authorization.k8s.io/flannel created
serviceaccount/flannel created
configmap/kube-flannel-cfg created
daemonset.apps/kube-flannel-ds-amd64 created
daemonset.apps/kube-flannel-ds-arm64 created
daemonset.apps/kube-flannel-ds-arm created
daemonset.apps/kube-flannel-ds-ppc64le created
daemonset.apps/kube-flannel-ds-s390x created到此K8S基本安装完成[root@jjh1 ~]# kubectl get nodes
NAME STATUS ROLES AGE VERSION
jjh1 Ready control-plane,master 35m v1.20.0
jjh2 Ready <none> 7m43s v1.20.0
jjh3 Ready <none> 7m44s v1.20.0
[root@jjh1 ~]# kubectl get pods -n kube-system
NAME READY STATUS RESTARTS AGE
coredns-54d67798b7-lfzwm 1/1 Running 0 9m6s
coredns-54d67798b7-n2k5n 1/1 Running 0 9m6s
etcd-jjh1 1/1 Running 0 9m21s
kube-apiserver-jjh1 1/1 Running 0 9m21s
kube-controller-manager-jjh1 1/1 Running 0 7m30s
kube-flannel-ds-amd64-7x9v6 1/1 Running 0 117s
kube-flannel-ds-amd64-8pxgf 1/1 Running 0 117s
kube-flannel-ds-amd64-jfpxb 1/1 Running 0 117s
kube-proxy-679sb 1/1 Running 0 4m24s
kube-proxy-8xm25 1/1 Running 0 4m26s
kube-proxy-k2wwb 1/1 Running 0 9m6s
kube-scheduler-jjh1 1/1 Running 0 7m15s