Volume
我们知道默认情况下容器的数据都是非持久化的,在容器消亡以后数据也跟着丢失,所以 Docker 提供了 Volume 机制以便将数据持久化存储。类似的,Kubernetes 提供了更强大的 Volume 机制和丰富的插件,解决了容器数据持久化和容器间共享数据的问题。
与 Docker 不同,Kubernetes Volume 的生命周期与 Pod 绑定
容器挂掉后 Kubelet 再次重启容器时,Volume 的数据依然还在
而 Pod 删除时,Volume 才会清理。数据是否丢失取决于具体的 Volume 类型,比如 emptyDir 的数据会丢失,而 PV 的数据则不会丢
Volume 类型
目前,Kubernetes 支持以下 Volume 类型:
emptyDir
hostPath
gcePersistentDisk
awsElasticBlockStore
nfs
iscsi
flocker
glusterfs
rbd
cephfs
gitRepo
secret
persistentVolumeClaim
downwardAPI
azureFileVolume
azureDisk
vsphereVolume
Quobyte
PortworxVolume
ScaleIO
FlexVolume
StorageOS
local
image
注意,这些 volume 并非全部都是持久化的,比如 emptyDir、secret、gitRepo 等,这些 volume 会随着 Pod 的消亡而消失。
API 版本对照表
v1.5+
core/v1
emptyDir
如果 Pod 设置了 emptyDir 类型 Volume, Pod 被分配到 Node 上时候,会创建 emptyDir,只要 Pod 运行在 Node 上,emptyDir 都会存在(容器挂掉不会导致 emptyDir 丢失数据),但是如果 Pod 从 Node 上被删除(Pod 被删除,或者 Pod 发生迁移),emptyDir 也会被删除,并且永久丢失。
hostPath
hostPath 允许挂载 Node 上的文件系统到 Pod 里面去。如果 Pod 需要使用 Node 上的文件,可以使用 hostPath。
NFS
NFS 是 Network File System 的缩写,即网络文件系统。Kubernetes 中通过简单地配置就可以挂载 NFS 到 Pod 中,而 NFS 中的数据是可以永久保存的,同时 NFS 支持同时写操作。
gcePersistentDisk
gcePersistentDisk 可以挂载 GCE 上的永久磁盘到容器,需要 Kubernetes 运行在 GCE 的 VM 中。
awsElasticBlockStore
awsElasticBlockStore 可以挂载 AWS 上的 EBS 盘到容器,需要 Kubernetes 运行在 AWS 的 EC2 上。
gitRepo
gitRepo volume 将 git 代码下拉到指定的容器路径中
image
image volume 是 Kubernetes v1.33 中升级为 Beta 的新功能,允许将容器镜像作为 volume 挂载到 Pod 中。这个功能对于需要共享容器镜像内容或访问镜像中的静态文件非常有用。
主要特性
从 Alpha 升级为 Beta(需要开启
ImageVolume
特性开关)支持
subPath
和subPathExpr
挂载方式卷被挂载为只读,且具有
noexec
限制新增了 kubelet 指标来跟踪镜像卷的请求和挂载操作
使用示例
容器运行时支持
CRI-O 从 v1.31 开始支持此功能
containerd 正在开发完整的 Beta 支持
注意事项
需要开启
ImageVolume
特性开关检查容器运行时是否支持此功能
可以使用新的 kubelet 指标监控镜像卷性能
使用 subPath
Pod 的多个容器使用同一个 Volume 时,subPath 非常有用
FlexVolume
Projected Volume
Projected volume 将多个 Volume 源映射到同一个目录中,支持 secret、downwardAPI 和 configMap。
本地存储限额
v1.7 + 支持对基于本地存储(如 hostPath, emptyDir, gitRepo 等)的容量进行调度限额,可以通过 --feature-gates=LocalStorageCapacityIsolation=true
来开启这个特性。
为了支持这个特性,Kubernetes 将本地存储分为两类
storage.kubernetes.io/overlay
,即/var/lib/docker
的大小storage.kubernetes.io/scratch
,即/var/lib/kubelet
的大小
Kubernetes 根据 storage.kubernetes.io/scratch
的大小来调度本地存储空间,而根据 storage.kubernetes.io/overlay
来调度容器的存储。比如
为容器请求 64MB 的可写层存储空间
为 empty 请求 64MB 的存储空间
Mount 传递
HostToContainer:这是开启
MountPropagation=true
时的默认模式,等效于rslave
模式,即容器可以看到 Host 上面在该 volume 内的任何新 Mount 操作Bidirectional:等效于
rshared
模式,即 Host 和容器都可以看到对方在该 Volume 内的任何新 Mount 操作。该模式要求容器必须运行在特权模式(即securityContext.privileged=true
)
注意:
使用 Mount 传递需要开启
--feature-gates=MountPropagation=true
Volume 快照
TODO: 补充 Volume 快照的设计原理和示例。
Windows Volume
Windows 容器暂时只支持 local、emptyDir、hostPath、AzureDisk、AzureFile 以及 flexvolume。注意 Volume 的路径格式需要为 mountPath: "C:\\etc\\foo"
或者 mountPath: "C:/etc/foo"
。
卷数据填充器(Volume Populators,v1.33 GA)
卷数据填充器是 Kubernetes v1.33 正式稳定(GA)的特性,允许在创建 PersistentVolumeClaim 时使用自定义资源作为数据源来预填充卷的内容。
基本概念
卷数据填充器支持在 PVC 创建时指定自定义资源作为数据源,这些自定义资源可以包含初始化数据的相关信息,如备份位置、模板数据或其他数据源配置。
使用方式
通过在 PVC 中使用 dataSourceRef
字段指定自定义数据源:
主要特性
自定义数据源 - 支持任意类型的自定义资源作为数据源
灵活的初始化 - 可从备份、模板、或外部系统初始化数据
AnyVolumeDataSource 默认启用 - v1.33 中该特性门控默认开启
可选填充 Pod - 支持基于插件的填充方式,可选择性跳过创建填充 Pod
应用场景
数据库初始化 - 从备份恢复数据库到新的存储卷
应用模板 - 使用预配置的应用数据模板
开发环境 - 快速创建包含测试数据的开发环境
灾难恢复 - 从备份系统恢复数据到新集群
实现示例
注意事项
需要相应的卷填充器控制器来处理特定的自定义资源类型
数据填充过程可能需要时间,Pod 会等待填充完成后才能启动
确保自定义资源与 PVC 在相同的命名空间中
挂载传播
支持三种选项:
None:即私有挂载(private)
HostToContainer:即 Host 内在该目录中的新挂载都可以在容器中看到,等价于 Linux 内核的 rslave。
Bidirectional:即 Host 内在该目录中的新挂载都可以在容器中看到,同样容器内在该目录中的任何新挂载也都可以在 Host 中看到,等价于 Linux 内核的 rshared。仅特权容器(privileged)可以使用 Bidirectional 类型。
注意:
使用前需要开启 MountPropagation 特性
如未设置,则 v1.9 和 v1.10 中默认为私有挂载(
None
),而 v1.11 中默认为HostToContainer
Docker 服务的 systemd 配置文件中需要设置
MountFlags=shared
其他的 Volume 参考示例
最后更新于