Kubernetes
1. 集群架构
Kubernetes 属于主从分布式架构,包括 Master 节点和 Node 节点,以及命令行工具 kubectl 和其它附加项。
节点 | 组件 | 功能 |
Master | API server | 资源操作的唯一入口,以 RESTful API 方式供客户端工具和其他组件调用 |
scheduler | 负责资源调度,将Pod绑定到Node节点 | |
controller-manager | 管理控制器,包括 Endpoint Controller,Replication Controller 等 | |
etcd | 高可用的键值存储数据库,用于存储集群的配置信息和各种资源状态信息 | |
Node | kubelet | 节点代理,Pod的生命周期管理并向Master报告Pod运行状态 |
kube-proxy | 网络代理和负载均衡,将service接收到的请求转发给Pod | |
docker | 容器引擎 |
2. 部署集群
Kubernetes 集群部署有3种方式:kubeadm、minikube和二进制包。
部署 Kubernetes cluster(单机版)最简单的方式是 minikube:安装 Docker;下载 kubectl;安装 minikube;启动 minikube。
$ kubectl get nodes
NAME STATUS ROLES AGE VERSION
minikube Ready master 44s v1.15.0
3. 部署应用
使用 Kubectl 创建和管理 deployment,deployment 负责创建和更新应用实例。创建 deployment 后,Master 会将 deployment 创建的应用实例调度到集群中的 Node 节点。
应用实例创建后,Deployment Controller 会持续监视这些实例。如果管理实例的 Node 节点被销毁,Deployment Controller 会创建新的应用实例,实现自我修复能力。
(1)使用 Kubectl 发送部署请求给 API Server;
(2)API Server 通知 Controller-manager 创建一个 deployment;
(3)Scheduler 执行调度任务,将 Pod 副本发送到 Node 节点;
(4)Node 节点上的 kubelet 创建并运行 Pod。
$ kubectl create deployment kubernetes-bootcamp --image=gcr.io/google-samples/kubernetes-bootcamp:v1
deployment.apps/kubernetes-bootcamp created
$ kubectl get deployments
NAME READY UP-TO-DATE AVAILABLE AGE
kubernetes-bootcamp 1/1 1 1 2m11s
4. 查看应用
(1)Pod 是 Kubernetes 中的最小单位,创建 deployment 时,会创建具有容器的 Pod,每个 Pod 将被绑定到 Node 节点上。Pod 是一个抽象化概念,包括:
- 共享存储,volume 卷
- 网络,唯一的集群 IP 地址
- 容器运行的信息
(2)Node 是 Kubernetes 中的工作节点,可以是虚拟机或物理机。Node 由 Master 管理,Node 上可以有多个 Pod。当一个 Node 节点销毁时,在该节点上运行的 Pod 也会销毁,然后通过 Replication Controller 动态创建新的 Pod。
每个 Node 上至少运行着:
- Kubelet,负责 Master 和 Node 之间的通信;管理 Node 上运行的 Pod 和 Container 容器。
- Container runtime,Docker 或其他容器。
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
kubernetes-bootcamp-5b48cfdcbd-d49wp 1/1 Running 0 16s
$ kubectl describe pods
$ export POD_NAME=$(kubectl get pods -o go-template --template '{{range .items}}{{.metadata.name}}{{"\n"}}{{end}}')
$ echo $POD_NAME
kubernetes-bootcamp-5b48cfdcbd-d49wp
$ kubectl logs $POD_NAME
$ kubectl exec -ti $POD_NAME bash
root@kubernetes-bootcamp-5b48cfdcbd-d49wp:/#
5. 发布应用
Service 是一个抽象的概念,它定义了一组逻辑的 Pod,应用可以方便的实现服务发现和负载均衡。使用 YAML 或 JSON 来定义 Service,Service 通过 Label Selector 来匹配一组 Pod。
Service 集成了负载均衡器,可以将网络流量分发到 deployment 暴露的所有 Pod。Service 使用 Endpoints 持续监控运行的 Pod,以确保将流量分配到可用的 Pod。
可以在 ServiceSpec 中通过 type 指定 Service 类型:
- ClusterIP 在集群内部的IP上暴露 Service,此类型只能在集群内访问。
- NodePort 通过每个 Node 上的 IP 和静态端口(NodePort)暴露 Service,集群外部通过 <NodeIP>:<NodePort> 方式访问。
- LoadBalancer 通过外部的负载均衡器暴露 Service。
- ExternalName 通过返回 CNAME 和它的值,可以将 Service 映射到 externalName 字段的内容,不使用代理。这种类型需要v1.7版本或更高版本 kube-dnsc 才支持。
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
kubernetes-bootcamp-5b48cfdcbd-6tmcr 1/1 Running 0 93s
$ kubectl expose deployment/kubernetes-bootcamp --type="NodePort" --port 8080
service/kubernetes-bootcamp exposed
$ kubectl get services
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 3m50s
kubernetes-bootcamp NodePort 10.111.106.144 <none> 8080:30216/TCP 5s
$ kubectl get services -l run=kubernetes-bootcamp
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes-bootcamp NodePort 10.111.106.144 <none> 8080:30216/TCP 2m9s
$ kubectl describe services/kubernetes-bootcamp
$ export NODE_PORT=$(kubectl get services/kubernetes-bootcamp -o go-template='{{(index .spec.ports 0).nodePort}}')
$ echo NODE_PORT=$NODE_PORT
NODE_PORT=30216
$ kubectl delete service -l run=kubernetes-bootcamp
service "kubernetes-bootcamp" deleted
6. 扩展应用
前面我们创建了一个 deployment,然后通过 Service 暴露,deployment 创建的 Pod 来运行应用。当流量增加时,我们需要对应用进行扩展。
通过更改 deployment 副本数实现对应用的扩展。
$ kubectl scale deployments/kubernetes-bootcamp --replicas=2
deployment.extensions/kubernetes-bootcamp scaled
$ kubectl get deployments
NAME READY UP-TO-DATE AVAILABLE AGE
kubernetes-bootcamp 2/2 2 2 44s
$ kubectl get pods -o wide
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
kubernetes-bootcamp-5b48cfdcbd-4d5w2 1/1 Running 0 23s 172.18.0.6 minikube <none> <none>
kubernetes-bootcamp-5b48cfdcbd-55b4g 1/1 Running 0 44s 172.18.0.5 minikube <none> <none>
7. 更新应用
滚动更新通过 deployment 实现应用实例在不停机情况下进行更新,新的 Pod 会逐步调度到可用的 Node 节点。
- 通过容器镜像的更新,更新应用的环境
- 回滚版本
- 不停机的持续集成和持续交付
$ kubectl get pods
NAME READY STATUS RESTARTS AGE
kubernetes-bootcamp-5b48cfdcbd-rwd82 1/1 Running 0 7m12s
kubernetes-bootcamp-5b48cfdcbd-w68tj 1/1 Running 0 7m12s
$ kubectl set image deployments/kubernetes-bootcamp kubernetes-bootcamp=jocatalin/kubernetes-bootcamp:v2
deployment.extensions/kubernetes-bootcamp image updated
$ kubectl rollout status deployments/kubernetes-bootcamp
deployment "kubernetes-bootcamp" successfully rolled out
$ kubectl rollout undo deployments/kubernetes-bootcamp
deployment.extensions/kubernetes-bootcamp rolled back