• 沒有找到結果。

一个新Pod创建后,Service就能立即选择到它,并会把请求转发给Pod,那问题就来 了,通常一个Pod启动是需要时间的,如果Pod还没准备好(可能需要时间来加载配置 或数据,或者可能需要执行 一个预热程序之类),这时把请求转给Pod的话,Pod也无 法处理,造成请求失败。

Kubernetes中解决这个问题的方法就是给Pod加一个业务就绪探针Readiness Probe,

当检测到Pod就绪后才允许Service请求转给Pod。

Readiness Probe同样是周期性的检测Pod,然后根据响应来判断Pod是否就绪,与存 活探针(liveness probe)相同,云容器实例中也支持两种类型的Readiness Probe。

● HTTP GET:往容器的IP:Port发送HTTP GET请求,如果probe收到2xx或3xx,说 明已经就绪。

● Exec:probe执行容器中的命令并检查命令退出的状态码,如果状态码为0则说明 已经就绪。

Readiness Probe 的工作原理

如果调用kubectl describe命令查看Service的信息,您会看下如下信息。

$ kubectl describe svc nginx -n $namespace_name Name: nginx

...

Endpoints: 192.168.113.81:80,192.168.165.64:80,192.168.198.10:80 ...

可以看到一个Endpoints,Endpoints同样也是Kubernetes的一种资源对象,可以查询 得到。

$ kubectl get endpoints -n $namespace_name

NAME ENDPOINTS AGE

nginx 192.168.113.81:80,192.168.165.64:80,192.168.198.10:80 14m

这里的192.168.113.81:80是Pod的IP:Port,通过如下命令可以查看到Pod的IP,与上面 的IP一致。

# kubectl get pods -o wide -n $namespace_name

NAME READY STATUS RESTARTS AGE IP

nginx-55c54cc5c7-49chn 1/1 Running 0 1m 192.168.198.10 nginx-55c54cc5c7-x87lb 1/1 Running 0 1m 192.168.165.64 nginx-55c54cc5c7-xp4c5 1/1 Running 0 1m 192.168.113.81

通过Endpoints就可以实现Readiness Probe的效果,当Pod还未就绪时,将Pod的 IP:Port在Endpoints中删除,Pod就绪后再加入到Endpoints中,如下图所示。

7-7 Readiness Probe 的实现原理

Exec

Exec方式与HTTP GET方式一致,如下所示,这个探针执行ls /ready命令,如果这个文 件存在,则返回0,说明Pod就绪了,否则返回其他状态码。

apiVersion: apps/v1 kind: Deployment metadata:

name: nginx spec:

replicas: 3 selector:

matchLabels:

app: nginx template:

metadata:

开发指南 7 使用 Service 和 Ingress 管理网络访问

labels:

# kubectl delete deploy nginx -n $namespace_name deployment.apps "nginx" deleted

# kubectl create -f deploy-read.yaml -n $namespace_name deployment.apps/nginx created

这里由于nginx镜像不包含 /ready 这个文件,所以在创建完成后容器不在Ready状态,

如下所示,注意READY这一列的值为0/1,表示容器没有Ready。

# kubectl get po -n $namespace_name

NAME READY STATUS RESTARTS AGE nginx-7955fd7786-686hp 0/1 Running 0 7s nginx-7955fd7786-9tgwq 0/1 Running 0 7s nginx-7955fd7786-bqsbj 0/1 Running 0 7s

再次查看Service,发现Endpoints一行的值为空,表示没有Endpoints。

$ kubectl describe svc nginx -n $namespace_name Name: nginx

...

Endpoints:

...

如果此时给容器中创建一个 /ready 的文件,让Readiness Probe成功,则容器会处于 Ready状态。再查看Pod和Endpoints,发现创建了/ready文件的容器已经Ready,

Endpoints也已经添加。

# kubectl exec -n $namespace_name nginx-7955fd7786-686hp -- touch /ready

# kubectl get po -o wide -n $namespace_name

NAME READY STATUS RESTARTS AGE IP

nginx-7955fd7786-686hp 1/1 Running 0 10m 192.168.93.169 nginx-7955fd7786-9tgwq 0/1 Running 0 10m 192.168.166.130 nginx-7955fd7786-bqsbj 0/1 Running 0 10m 192.168.252.160

# kubectl get endpoints -n $namespace_name NAME ENDPOINTS AGE

nginx 192.168.93.169:80 14d

HTTP GET

Readiness Probe的配置与存活探针(livness probe)一样,都是在 Pod Template 的 containers 里面,如下所示,这个Readiness Probe向Pod发送HTTP请求,当Probe收 到2xx或3xx返回时,说明Pod已经就绪,这

apiVersion: apps/v1

Readiness Probe 高级配置

与Liveness Probe相同,Readiness Probe也有同样的高级配置选项,上面nginx Pod的 describe命令回显有中有如下行。

Readiness: exec [ls /var/ready] delay=0s timeout=1s period=10s #success=1 #failure=3

这一行表示readiness probe的具体参数配置,其含义如下:

● delay=0s 表示容器启动后立即开始探测,没有延迟时间

● timeout=1s 表示容器必须在1s内做出相应反馈给probe,否则视为探测失败

● period=10s 表示每10s探测一次

● #success=1 表示探测连续1次成功表示成功

● #failure=3 表示探测连续3次失败后会重启容器

这些是创建时默认设置的,您也可以手动配置,如下所示。

8 使用 PersistentVolumeClaim 申请持久化存

云容器实例当前支持在容器中使用如下三种持久化存储。

● 云硬盘(Elastic Volume Service,EVS),EVS是一种块存储服务,提供高I/O

(sas)、超高I/O(ssd)和普通I/O(sata)三种类型云硬盘。

● 弹性文件服务(Scalable File Service,SFS),SFS提供共享的文件存储,支持标

准文件协议类型(nfs-rw)。SFS提供了SFS和SFS Turbo两种类型的文件系统。

– SFS为用户提供一个完全托管的共享文件存储,能够弹性伸缩至PB规模,具 备高可用性和持久性,为海量数据、高带宽型应用提供有力支持。适用于多 种应用场景,包括HPC、媒体处理、文件共享、内容管理和Web服务等。

– SFS Turbo为用户提供一个完全托管的共享文件存储,能够弹性伸缩至320TB 规模,具备高可用性和持久性,为海量的小文件、低延迟高IOPS型应用提供 有力支持。适用于多种应用场景,包括高性能网站、日志存储、压缩解压、

DevOps、企业办公、容器应用等。

● 对象存储服务(Object Storage Service,OBS),OBS是一个基于对象的海量存

储服务,为客户提供海量、安全、高可靠、低成本的数据存储能力。

上面三种存储中,OBS的使用方式最为直接,云容器实例当前支持直接以SDK方式使用 对象存储服务(OBS)。您可以在应用程序中使用SDK方式使用OBS,将应用程序打包 成容器镜像,在云容器实例中使用镜像创建负载。OBS的SDK的下载及使用方法请参见

https://developer.huaweicloud.com/sdk?OBS。

EVS和SFS的使用有个挂载的过程,下面将介绍如何使用EVS和SFS。

PersistentVolumeClaim(PVC)

Kubernetes提供PVC专门用于持久化存储的申请,PVC可以让您无需关心底层存储资源 如何创建、释放等动作,而只需要申明您需要何种类型的存储资源、多大的存储空 间。

在实际使用中,您可以通过Pod中的Volume来关联PVC,通过PVC使用持久化存储,

如图8-1所示。

8-1 使用持久化存储

namespace: namespaces-test annotations: {

paas.storage.io/cryptKeyId: ee9b610c-e356-11e9-aadc-d0efc1b3bb6b }spec:

accessModes:

- ReadWriteMany resources:

requests:

storage: 100Gi storageClassName: sata

accessModes为存储访问模式,支持如下3种模式:

namespace: namespace-test annotations: {

paas.storage.io/cryptKeyId: ee9b610c-e356-11e9-aadc-d0efc1b3bb6b paas.storage.io/cryptAlias: sfs/default

paas.storage.io/cryptDomainId: d6912480-c3d6-4e9e-8c70-38afeea434c3 volume.beta.kubernetes.io/storage-provisioner: flexvolume-huawei.com/fuxinfs }spec:

accessModes:

- ReadWriteMany resources:

开发指南 8 使用 PersistentVolumeClaim 申请持久化存储

requests:

storage: 100Gi storageClassName: nfs-rw

使用 PVC

containers:

- image: nginx:latest name: container-0

- mountPath: "/tmp/volume0" # 将PVC挂载到容器的/tmp/volume0路径 name: pvc-test-example # Volume的名称

volumes: # 定义Volume,关联PVC - name: pvc-test-example

persistentVolumeClaim:

claimName: pvc-test # PVC的名称 imagePullSecrets:

- name: imagepull-secret

● 写入上面申请的文件存储(storageClassName设置为nfs-rw型)中。

containers:

- image: nginx:latest name: container-0

- mountPath: "/tmp/volume0" # 将PVC挂载到容器的/tmp/volume0路径

subPath: "abc" # 文件存储根路径下子路径,如果不存在会自动在文件存储中创建。该子路径 必须为相对路径。

name: pvc-test-example # Volume的名称 volumes: # 定义Volume,关联PVC

- name: pvc-test-example persistentVolumeClaim:

claimName: pvc-test # PVC的名称 imagePullSecrets:

- name: imagepull-secret

开发指南 8 使用 PersistentVolumeClaim 申请持久化存储

9 使用 ConfigMap 和 Secret 提高配置灵活性

相關文件