![再也不踩坑的kubernetes实战指南](https://wfqqreader-1252317822.image.myqcloud.com/cover/323/27563323/b_27563323.jpg)
3.1 安装GFS到K8S集群中
在集群中,我们可以使用GFS、CEPH、NFS等为Pod提供动态持久化存储。本节动态存储主要介绍GFS的使用,静态存储方式采用NFS,其他类型的存储配置类似。
3.1.1 准备工作
为了保证Pod能够正常使用GFS作为后端存储,需要每台运行Pod的节点上提前安装GFS的客户端工具,其他存储方式也类似。
所有节点安装GFS客户端:
yum install glusterfs glusterfs-fuse -y
给需要作为GFS节点提供存储的节点打上标签:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P151_58249.jpg?sign=1738895711-mdQSHYnznmkgv1cnOq3nVIblfT5sjVez-0-c4c2ad495e084779b75f4d2a89d71602)
所有节点加载对应模块:
[root@K8S-master01 ~]# modprobe dm_snapshot [root@K8S-master01 ~]# modprobe dm_mirror [root@K8S-master01 ~]# modprobe dm_thin_pool
3.1.2 创建GFS集群
这里采用容器化方式部署GFS集群,同样也可以使用传统模式部署,在生产环境中,GFS集群最好是独立于集群之外进行部署,之后只需创建对应的EndPoints即可。
本例部署采用DaemonSet方式,同时保证已经打上标签的节点上都运行一个GFS服务,并且均有提供存储的磁盘。
下载相关安装文件:
wget https://github.com/heketi/heketi/releases/download/v7.0.0/ heketi-client-v7.0.0.linux.amd64.tar.gz
创建集群:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P152_58254.jpg?sign=1738895711-ixlf3GKzO663VAUYFripyD8Dr7gpebCU-0-fdb986db4089a91fde6034937eef35b9)
注意1:此处采用的是默认的挂载方式,可使用其他磁盘作为GFS的工作目录。
注意2:此处创建的Namespace为default,可按需更改。
注意3:可使用gluster/gluster-centos:gluster3u12_centos7镜像。
查看GFS Pods:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P152_58255.jpg?sign=1738895711-A4ngzD7fJdqgOD69OYVl92SWYxoGhEEq-0-038ea94a2172a21e9e10185678c70841)
3.1.3 创建Heketi服务
Heketi是一个提供RESTful API管理GFS卷的框架,能够在Kubernetes、OpenShift、OpenStack等云平台上实现动态存储资源供应,支持GFS多集群管理,便于管理员对GFS进行操作,在Kubernetes集群中,Pod将存储的请求发送至Heketi,然后Heketi控制GFS集群创建对应的存储卷。
创建Heketi的ServiceAccount对象:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P153_58257.jpg?sign=1738895711-0EnyLjCUguMuvzruBOdAtfcHVTHqeptp-0-f72b60690ce5017eefe56279cdbe81ed)
创建Heketi对应的权限和Secret:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P153_58258.jpg?sign=1738895711-sB0NxhmiibPqTav5zxYtkzLlAncDGsDO-0-97f01d8edd2ecb360b084c7716f8e8b3)
初始化部署Heketi:
[root@K8S-master01 kubernetes]# kubectl create -f heketi-bootstrap.json secret/heketi-db-backup created service/heketi created deployment.extensions/heketi created [root@K8S-master01 kubernetes]# pwd /root/heketi-client/share/heketi/kubernetes
3.1.4 创建GFS集群
本节使用Heketi创建GFS集群,其管理方式更加简单和高效。
复制heketi-cli至/usr/local/bin:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P153_58260.jpg?sign=1738895711-OWI6CsPFLfeZfYUH3yr3tYcoZIepyXF8-0-ce31c617487c472d75e9dac37f7afacb)
修改topology-sample,manage为GFS管理服务的节点(Node)主机名,storage为节点的IP地址,devices为节点上的裸设备,也就是用于提供存储的磁盘最好使用裸设备:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P153_58262.jpg?sign=1738895711-vJC6B7i7ZdM01hdGutQILN2KAmAoaCBQ-0-ffa9e17943c820ea2aa41e4e065e5c97)
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P155_58267.jpg?sign=1738895711-feeJ3n9UtjlwakdOaGhXnCejeflGOPkE-0-aa01042ab35f3b9ecbe3585447100e44)
查看当前Heketi的ClusterIP:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P155_58268.jpg?sign=1738895711-qMxv7nDPILj98X58ESqYx3k2QxROC4Rf-0-d48bb3595ccdc94e985f5fa2bebbfc71)
使用Heketi创建GFS集群:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P155_58269.jpg?sign=1738895711-jcwkThUz3NO1h0IPLBQSWL9YlDHJ04ry-0-f9c0e7244711b66ea92cdc626a1174c6)
之前创建的Heketi未配置持久化卷,如果Heketi的Pod重启,可能会丢失之前的配置信息,所以现在创建Heketi持久化卷,对Heketi的数据进行持久化。该持久化方式采用GFS提供的动态存储,也可以采用其他方式进行持久化:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P155_58270.jpg?sign=1738895711-J4lS8lZrTe4nRJyL3lxQseupslgfYUSx-0-9f47225b2fcb75d0d38e507bf2378b4f)
如果出现如下报错信息,就在所有节点执行modprobe dm_thin_pool,重新执行此命令即可:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P155_58271.jpg?sign=1738895711-ViavEbTIewioQ31LVsVgKLbqyRFu7ZKJ-0-14fa02077e903027c0855e033f6a13d5)
删除中间产物:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P156_58273.jpg?sign=1738895711-rrcmHbowmgoLNBj6mOSBrnpd4NXoL4cT-0-b5c55ac0e5c1d808cb98b33e56a7b653)
创建持久化Heketi,持久化方式也可以选择其他方式:
[root@K8S-master01 kubernetes]# kubectl create -f heketi-deployment.json service/heketi created deployment.extensions/heketi created
待Pod全部启动,即表示创建成功:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P156_58275.jpg?sign=1738895711-flJfmsY1I8Z20IIP0Z73oRHWThd2erJi-0-271b58c64c360a4d0bdbaecdf14362c6)
查看最新部署的持久化Heketi的svc,并更改HEKETI_CLI_SERVER的值:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P156_58276.jpg?sign=1738895711-uFHwVtlPwwh57Vos8iuFqYTtGz0Cv8Q6-0-830660ad6bdab5f603620ba7d5e84e07)
查看GFS集群信息,其他操作可参考Heketi官方文档:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P156_58277.jpg?sign=1738895711-t6Yx1UfIiInCYg4XNe5Vyq5ryJ2SnuEd-0-34b362dc9bf15a201cd4ed18970da111)
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P157_58279.jpg?sign=1738895711-e64F1qqJz5KWa8clJRhgrPAk5E8nMMOC-0-73eddad9628505fae27a647db457e071)
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P158_58281.jpg?sign=1738895711-V5O6DCeMM3XDMnHOUxHX7i3Clztfoc0D-0-50cecaff6a4a20db5d66a48e5111a8dc)
3.1.5 创建StorageClass
提前创建StorageClass,然后Pod直接在StorageClass选项配置选择该StorageClass,即可通过该StorageClass创建对应的PV。
创建StorageClass文件如下:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P158_58282.jpg?sign=1738895711-bjbLOKvlaO7tAxOdrKlwq2181rZ9dQA5-0-1d80f4fec4aa21bf53160835595ebe69)
说明
Provisioner参数须设置为"kubernetes.io/glusterfs"。
resturl地址为API Server所在主机可以访问到的Heketi服务的某个地址。
其他详细参数可以参考2.2.12节。
3.1.6 测试使用GFS动态存储
创建一个Pod使用动态PV,在storageClassName指定之前创建的StorageClass的名字,即gluster-heketi:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P158_58285.jpg?sign=1738895711-y5Q5AU78v8MR7sUHrRta0Th7xxI2npQO-0-6c578009d012188a7290e5b079597ba0)
创建Pod:
[root@K8S-master01 gfs]# kubectl create -f pod-use-pvc.yaml pod/pod-use-pvc created
PVC定义一旦生成,系统便触发Heketi进行相应的操作,主要为在GFS集群上创建brick,再创建并启动一个卷(volume)。
创建的PV及PVC如下:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P159_58288.jpg?sign=1738895711-Xj5EXLQ2RPMOoTWsJdQLP62qVFUtjYw2-0-dbec2a75ee36ef3e35e57cfe9ac036a2)
3.1.7 测试数据
测试使用该PV的Pod之间能否共享数据。
进入到Pod并创建文件:
[root@K8S-master01 /]# kubectl exec -ti pod-use-pvc -- /bin/sh / # cd /pv-data/ /pv-data # mkdir {1..10} /pv-data # ls {1..10}
查看创建的卷(volume):
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P160_58292.jpg?sign=1738895711-hA7uiMzrloGCkRSRq9XAdX1YhfuAhoxT-0-34af64f85c9d56686d53c8e9e3ec8507)
或者使用volume list查看:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P160_58293.jpg?sign=1738895711-yFfZXJsvlG3OZFhRkA0mnpyvVkPJd9Dc-0-caba2cbb299269c76c465a86d464abb9)
查看数据。其中vol_56d636b452d31a9d4cb523d752ad0891为卷名(Volume Name)挂载:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P160_58294.jpg?sign=1738895711-GgFvDkysNjxRwGPWlYjCjtMj66KwvUau-0-e84e6cfe8cce2de9d80263c508553723)
3.1.8 测试Deployment
测试在Deployment部署方式下是否能够正常使用StorageClass。
创建一个Nginx的Deployment如下:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P160_58295.jpg?sign=1738895711-BPfOID8WqxmybDygsCOxMOwmaOMoR0qJ-0-c2d5b0b2ab3a90848d34b3869081872c)
上述例子为了演示使用了两个PVC,实际环境可以使用subPath来区分conf和html,当然也可以直接指定卷,此时不单独创建PVC。
直接创建的方式如下:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P161_58298.jpg?sign=1738895711-0p5B9JydzTiaFwzsxhXJLoY6467FRgBd-0-75463204be2950427537493987a19a3a)
查看资源:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P162_58301.jpg?sign=1738895711-wdCnT5qOHwyMD8gW3NsCY1qWhXVPhE33-0-678f1e7dc54d2d9ac10376cca235369f)
查看挂载情况:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P162_58302.jpg?sign=1738895711-HTIHwUwy8JqVmJp8sTYDzjZmmH8WdTJl-0-08b1ad868232b993ac48f1ec4e2c0d42)
宿主机挂载并创建index.html:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P162_58303.jpg?sign=1738895711-uj4dk20cMDx30OIFeJuDTj7Bkzg1S1s1-0-2eddd71225d1ff7e80db5bec57aa59b6)
扩容Nginx,查看是否能正常挂载目录:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P162_58304.jpg?sign=1738895711-ReHR4RVx1A0czKDEp09pA79mbhz1n6hM-0-128accd7dcf8711368f1a758b02f9e56)
查看文件内容:
![](https://epubservercos.yuewen.com/62A1DF/15825992304144506/epubprivate/OEBPS/Images/Figure-P163_58307.jpg?sign=1738895711-TYHBMTUR3CttLA8aEyooVXNLt12uj4lw-0-ef8e20fb1c2c9971ba1f717bb3626e1f)