使用云盘CDS
概述
容器引擎 CCE 支持通过创建 PV/PVC,并为工作负载挂载数据卷方式使用百度智能云磁盘CDS。本文将介绍如何在集群中动态和静态挂载云磁盘。
使用限制
- 集群 Kubernetes 版本需大于或等于 1.16。
- 挂载 CDS 的 Pod 只能在支持挂载云磁盘的节点上启动。
- 每个节点挂载的 CDS 数量由 CCE CSI CDS Plugin 组件配置参数及云服务器自身同时决定,更多信息请见创建服务器实例。
- 当前云盘只支持按量付费的方式进行挂载,不支持包年包月的付费方式创建。
前提条件
- 集群已安装块存储组件,更多信息请见 CCE CSI CDS Plugin 说明。
操作步骤
通过 PV/PVC 方式使用 CDS,具体分为两种方式:
方式 | 说明 | 注意事项 |
---|---|---|
静态挂载 | 需要用户提前在百度智能云中创建好 CDS(操作方法参考 CDS 文档),然后通过 CDS 的 volume id 在集群中创建 PV 和 PVC 资源。 |
|
动态挂载 | 用户在集群中声明 PVC 时,自动创建出按量付费 CDS 磁盘并且动态关联至 PV。 |
|
动态挂载块存储
方式一:通过 kubectl 命令行操作
1. 创建存储类 StorageClass
- 集群管理员可使用 StorageClass 为集群定义不同的存储类型。您可通过 StorageClass 配合 PVC 动态创建需要的存储资源。
- 本文介绍通过 Kubectl 方式创建并行文件存储 PFS 类型的 StorageClass,自定义并行文件存储使用所需的模板。
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: hp1 #StorageClass名称
provisioner: csi-cdsplugin
allowVolumeExpansion: true
volumeBindingMode: WaitForFirstConsumer
parameters:
paymentTiming: "Postpaid" #付费方式,Postpaid 表示按量付费,当前只支持按量付费
storageType: "hp1" #磁盘类型,支持cloud_hp1, hp1, hdd
recycle: "on" #云磁盘的删除回收策略,支持 on、off(on 表示删除时将云磁盘放入回收站,off 表示删除时云磁盘不放入回收站),仅当 reclaimPolicy 为 Delete 生效,默认值为 on
reclaimPolicy: Delete #云磁盘的删除策略,支持 Delete、Retain(Delete 表示删除 PVC 时,PV 和 云磁盘会一起删除,删除云磁盘默认放入回收站;Retain 表示删除 PVC 时,PV和云磁盘不会被删除,需要您手动删除),默认为 Delete
说明:
- storageType 用于设置动态创建的 CDS 盘的类型,支持:cloud_hp1 (通用型 SSD)、hp1 (高性能云磁盘)、hdd(通用型 HDD),更多信息参见 创建CDS云盘。
- 如果集群中存在使用动态方式挂载 CDS 的 Pod,且对应 StorageClass 中 reclaimPolicy 设置为 Delete,这部分 CDS 在集群删除集群时默认会保留,如果需要一同删除请在删除集群前手动停止相关 Pod 并删除对应 PVC。
2. 创建持久卷声明 PVC
注意 storageClassName 需要指定为上述部署 storageClass 时填写的 storageClass 名称。
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: csi-pvc-cds
spec:
accessModes:
- ReadWriteOnce
storageClassName: hp1
resources:
requests:
storage: 5Gi # 指定PVC存储空间大小
说明: 不同的磁盘类型,存储大小不同,如 hp1 : 5~32765GB,cloud_hp1 : 50~32765GB,hdd : 5~32765GB
3. 检查 PVC 状态为 Bound
$ kubectl get pvc csi-pvc-cds
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
csi-pvc-cds Bound pvc-1ab36e4d1d2711e9 50Gi RWX hp1 4s
说明:
如果指定了 volumeBindingMode 为
WaitForFirstConsumer
,则 PVC 此时处于 Pending 状态,会等待第一个挂载该 PVC 的 Pod 被创建后才进入 PV 创建和绑定流程。
4. 在 Pod 中挂载 PVC
Pod 和 PVC 需要在同一个 namespace 下。
apiVersion: v1
kind: Pod
metadata:
name: test-pvc-pod
labels:
app: test-pvc-pod
spec:
containers:
- name: test-pvc-pod
image: nginx
volumeMounts:
- name: cds-pvc
mountPath: "/cds-volume"
volumes:
- name: cds-pvc
persistentVolumeClaim:
claimName: csi-pvc-cds
Pod 创建后,可以读写容器内的 /cds-volume 路径来访问相应的 cds 存储上的内容。
方式二:通过控制台操作
- 登陆 CCE 控制台,点击集群名称进入集群详情页。
- 创建存储类 StorageClass。
a. 在左侧导航栏中选择存储配置 > 存储类,进入存储类列表页面。
b. 在存储类列表上方点击新建存储类。在文件模版中自定义相关配置。storageType 用于设置动态创建的 CDS 盘的类型,支持:cloud_hp1 (通用型 SSD)、hp1 (高性能云磁盘)、hdd(通用型 HDD)。
b. 点击确定,将为您创建存储类。
- 创建持久卷声明 PVC。
a. 在左侧导航栏选择存储配置 > 持久卷声明,进入持久卷声明列表。
b. 点击持久卷声明列表上方新建持久卷声明按钮,选择表单创建或 Yaml 创建。
c. 若选择表单创建则需填写相关参数,其中三种访问模式详情参见存储管理概述,点击确定后在确认配置弹窗中输入 storageClassName
的值,即存储类的名称。确认配置无误后点击确定。
d. 创建 PVC 后,在持久卷声明列表 > 持久卷列可以看见相应的 PV 自动创建,PVC 状态列显示为 Bound,即 PVC 已经与新创建的 PV 绑定。
- 创建应用并挂载 PVC,在 Pod spec 内指定相应的 PVC 名称,且 Pod 和 PVC 需要在同一个 namespace 下。Pod 创建后,可以读写容器内的 /cds-volume 路径来访问相应的 CDS 存储上的内容。
静态挂载块存储
方式一:通过 kubectl 命令行操作
1. 创建持久卷 PV
apiVersion: v1
kind: PersistentVolume
metadata:
name: pv-cds
namespace: "default"
spec:
accessModes:
- ReadWriteOnce
capacity:
storage: 5Gi
csi:
driver: "csi-cdsplugin"
volumeHandle: "v-xxxx" # 指定挂载的磁盘,格式为磁盘ID
fsType: "ext4"
nodeAffinity:
required:
nodeSelectorTerms:
- matchExpressions:
- key: failure-domain.beta.kubernetes.io/zone
operator: In
values:
- zoneA
persistentVolumeReclaimPolicy: Retain
说明:
- fsType 不填写时默认值为 ext4。Filesystem 模式下,若 fsType 与 cds 中实际文件系统类型不匹配,将导致挂载失败;若 cds 中尚无文件系统,则挂载时自动格式化 cds 为 fsType 指定的文件系统。
- nodeAffinity 中需要指定 cds 所在可用区,保证挂载该 cds 的 pod 只会被调度到与 cds 磁盘同可用区的 node 上。
2. 创建持久卷声明 PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: csi-cds-pvc
spec:
accessModes:
- ReadWriteOnce
resources:
requests:
storage: 5Gi
3. 检查 PVC 状态为 Bound,并且与对应的 PV 绑定
$ kubectl get pv
NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE
pv-cds 5Gi RWO Retain Bound default/csi-cds-pvc 4s
$ kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
csi-cds-pvc Bound pv-cds 5Gi RWO 36s
4. 在 Pod 中挂载 PVC
apiVersion: apps/v1
kind: Deployment
metadata:
name: web-server-deployment
labels:
test: ws
spec:
replicas: 1
selector:
matchLabels:
se: ws
template:
metadata:
labels:
se: ws
name: web-server
spec:
containers:
- name: web-server
image: nginx
volumeMounts:
- mountPath: /var/lib/www/html
name: csi-cds-pvc
volumes:
- name: csi-cds-pvc
persistentVolumeClaim:
claimName: csi-cds-pvc
Pod 创建后,可以读写容器内的 /var/lib/www/html 路径来访问相应的 CDS 存储上的内容。
由于创建 PV 和 PVC 时只支持 accessModes 为 ReadWriteOnce,该 PVC 可以被同一节点上所有 Pod 挂载读写。
方式二:通过控制台操作
- 登陆 CCE 控制台,单击集群名称进入集群详情页。
- 创建持久卷 PV。
a. 在左侧导航栏选择存储配置 > 持久卷,进入持久卷列表。
b. 点击持久卷列表上方新建持久卷按钮,选择表单创建或 Yaml 创建。
c. 若选择表单创建则需填写相关参数,根据需求设置存储容量,存储类型选择云盘 CDS,并输入云盘 ID。点击确定在二次弹窗中确认配置后点击确定创建 PV。云盘 ID 可前往 CDS 控制台 查看。
- 创建可以和持久卷 PV 绑定的持久卷声明 PVC。
a. 在左侧导航栏选择存储配置 > 持久卷声明,进入持久卷声明列表。
b. 点击持久卷列表上方新建持久卷声明按钮,选择表单创建或 Yaml 创建。
c. 根据之前创建的 PV 配置 PVC 的存储容量、访问模式、存储类(可选),点击确定创建 PVC。会查找现有的 PV 资源,寻找与 PVC 请求相匹配的 PV。
d. 绑定后,可以分别在持久卷列表和持久卷声明列表中看见 PV 和 PVC 的状态列变为 Bound。
- 创建应用并挂载 PVC,在 Pod spec 内指定相应的 PVC 名称即可。
应用场景
在 StatefuleSet 里通过 claimTemple 批量使用 PVC
- 创建 2 副本 StatefuleSet 并指定 volumeClaimTemplates,需要提前创建好相应 StorageClass:
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: web
spec:
serviceName: "nginx"
replicas: 2
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
name: web
volumeMounts:
- name: www
mountPath: /usr/share/nginx/html
volumeClaimTemplates:
- metadata:
name: www
spec:
accessModes: [ "ReadWriteOnce" ]
resources:
requests:
storage: 5Gi
storageClassName: hp1
- 查看 Pod 以及自动创建的 PVC。
$ kubectl get pod
NAME READY STATUS RESTARTS AGE
web-0 1/1 Running 0 3m
web-1 1/1 Running 0 2m
$ kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
www-web-0 Bound pvc-a1e885701d2f11e9 5Gi RWO hp1 6m
www-web-1 Bound pvc-c91edb891d2f11e9 5Gi RWO hp1 5m
多可用区集群挂载 CDS
目前 CDS 不支持跨可用区,如果 CCE 集群中有多个可用区的机器,动态挂载的方式可以通过设置 StorageClass 的 Volume Binding Mode 为 WaitForFirstConsumer 来自动根据 Pod 被调度节点所处的可用区创建 CDS 磁盘,或者通过设置 StorageClass 中 allowedTopologies 字段或 Pod 的节点亲和属性来指定可用区;使用已有 CDS 时,须指定 PV 的 nodeAffinity 参数实现可用区亲和性。
CCE 集群默认会为集群节点打上可用区标签:
$ kubectl get nodes --show-labels
NAME STATUS ROLES AGE VERSION LABELS
192.168.80.15 Ready <none> 13d v1.8.12 beta.kubernetes.io/arch=amd64,beta.kubernetes.io/instance-type=BCC,beta.kubernetes.io/os=linux,failure-domain.beta.kubernetes.io/region=bj,failure-domain.beta.kubernetes.io/zone=zoneC,kubernetes.io/hostname=192.168.80.15
其中 failure-domain.beta.kubernetes.io/zone=zoneC 标签说明该集群节点处于 C 可用区。
方式一:设置 StorageClass 的 Volume Binding Mode
通过指定 volumeBindingMode 为 WaitForFirstConsumer 来解决此问题。指定绑定模式为 WaitForFirstConsumer 时,先进行 Pod 的调度,随后根据调度结果对应的可用区创建 CDS。
使用示例
- 创建 StorageClass 指定
volumeBindingMode
为WaitForFirstConsumer
。
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: csi-cds
provisioner: csi-cdsplugin
allowVolumeExpansion: true
volumeBindingMode: WaitForFirstConsumer
parameters:
paymentTiming: "Postpaid"
storageType: "hp1"
reclaimPolicy: Delete
- 在 StatefulSet 中通过 claimTemple 使用 PVC:
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: web
spec:
serviceName: "nginx"
replicas: 1
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
name: web
volumeMounts:
- name: www
mountPath: /usr/share/nginx/html
volumeClaimTemplates:
- metadata:
name: www
spec:
accessModes: [ "ReadWriteOnce" ]
resources:
requests:
storage: 5Gi
storageClassName: csi-cds
方式二:通过 StorageClass 的 allowedTopologies 字段强制指定 zone
- 创建 StorageClass 并配置
allowedTopologies
为 参数。
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: hp1-zonec
provisioner: csi-cdsplugin
parameters:
paymentTiming: "Postpaid"
storageType: "hp1"
reclaimPolicy: Delete
volumeBindingMode: WaitForFirstConsumer
allowedTopologies:
- matchLabelExpressions:
- key: failure-domain.beta.kubernetes.io/zone
values:
- zoneC
- 在 StatefulSet 中通过 claimTemple 使用 PVC:
apiVersion: apps/v1
kind: StatefulSet
metadata:
name: sts-multi-zone
spec:
serviceName: "nginx"
replicas: 1
selector:
matchLabels:
app: nginx
template:
metadata:
labels:
app: nginx
spec:
containers:
- name: nginx
image: nginx
ports:
- containerPort: 80
name: web
volumeMounts:
- name: www
mountPath: /usr/share/nginx/html
volumeClaimTemplates:
- metadata:
name: www
spec:
accessModes: [ "ReadWriteOnce" ]
resources:
requests:
storage: 40Gi
storageClassName: hp1-zonec
扩容 CDS PV
扩容 CDS PV 需要集群 Kubernetes 版本为 1.16 及以上,同时只针对动态创建的 CDS PV 生效。
- 创建 storageClass 并添加
allowVolumeExpansion: true
配置
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: hp1
allowVolumeExpansion: true #允许磁盘扩容
...
- 修改与 PV 绑定的 PVC 中
spec.resources.requests
中的磁盘容量为目标容量,触发扩容
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
name: csi-pvc-cds
spec:
accessModes:
- ReadWriteOnce
storageClassName: hp1
resources:
requests:
storage: 8Gi #修改为目标磁盘大小
-
默认情况下 CDS CSI 插件仅支持离线扩容,即需要在 PVC 未被 Pod 挂载时才会执行实际扩容动作。完成 PVC 容量 request 修改后,如果此时该 PVC 未被任何 Pod 挂载,则会触发 CDS 磁盘扩容操作,否则会等待挂载该 PVC 的 Pod 停止后才开始扩容。具体扩容进度可以通过
kubectl describe pvc <pvcName>
查看对应的 Events 了解。
说明:
- 如果需要在 PVC 被 Pod 挂载状态下进行在线扩容,可以通过
kubectl -n kube-system edit deployment csi-cdsplugin-controller-server
,给csi-cdsplugin
容器的添加启动参数--enable-online-expansion`,来启用在线扩容功能。
- 但需要特别注意的是,同时进行磁盘读写和磁盘扩容可能导致数据损坏,非必要场景不建议开启在线扩容功能。