nfs-provisioner · 集群默认的 NFS 动态存储供应器

集群把存储分成两类:NFS Provisioner(PVE3 提供的 1TB NVMe)与节点本地的 local-path。本组件是前者的实现,运行 registry.k8s.io/sig-storage/nfs-subdir-external-provisioner,监听 PVC 请求并在 NFS 共享上为每个卷自动创建子目录、回填对应的 PV。

它对外暴露的 provisioner 名是 nfs-storage,集群内的 PVC 通过 storageClassName: nfs-client 申领它供应的卷(如 loki、grafana、vault、gitea、kafka、zookeeper、DNF 各服务等都用它)。因为后端是单一 NFS 导出目录,这些卷天然支持 RWX(多 Pod 共享读写)——CLAUDE.md 中提到 DNF 游戏服正是依赖 nfs-client 的 RWX 特性,所以扩缩容时要用单 Pod delete 而非滚动重启以避免 split-brain。

部署形态

  • Name
    命名空间
    Description
    nfs-provisioner(独立 Namespace,带 finalizer kubernetes)
  • Name
    工作负载
    Description
    Deployment nfs-client-provisioner,replicas: 1,更新策略 Recreate
  • Name
    镜像
    Description
    registry.k8s.io/sig-storage/nfs-subdir-external-provisioner:v4.0.2
  • Name
    调度
    Description
    nodeSelector workload: infra(落在 worker3,集群唯一的 infra 节点)
  • Name
    资源
    Description
    requests 100m CPU / 128Mi,limits 500m CPU / 512Mi
  • Name
    卷挂载
    Description
    NFS 卷直接挂到容器 /persistentvolumes(server 192.168.88.68,path /srv/nfs)
  • Name
    ServiceAccount
    Description
    nfs-client-provisioner

副本固定为 1:Deployment 配了 leader-locking Role(对 endpoints 的 get/list/watch/create/update/patch),是 provisioner 的领导者选举锁,而非多副本高可用。Recreate 策略保证升级时不会出现两个实例同时持有同一 NFS 挂载。

配置与依赖

所有配置通过容器 env 注入,没有 ConfigMap,也没有 ExternalSecret(不涉及任何密钥)。关键三项:

env含义
PROVISIONER_NAMEnfs-storage供应器标识,PVC/StorageClass 通过它绑定
NFS_SERVER192.168.88.68后端 NFS 服务器(PVE3,1TB NVMe,定时备份到 NAS)
NFS_PATH/srv/nfsNFS 导出根目录,每个 PV 在其下建子目录

核心外部依赖是 PVE3 上的 NFS 服务(192.168.88.68:/srv/nfs)。该 NFS 服务器是单点——它不可用时,依赖 nfs-client 的所有 PVC 都会受影响。StorageClass nfs-client 本身不在本仓库中以 manifest 形式定义(集群里被大量 PVC 引用,例如 loki、grafana、vault、gitea),本组件只提供其后端 provisioner。

访问与网络

本组件不对外提供 Service,没有 Ingress、ServiceMonitor、PrometheusRule,也没有 HPA/VPA/PDB——它是后台 controller,只与 kube-apiserver 和 NFS 服务器通信。命名空间内有一组 NetworkPolicy 收紧流量:

  • default-deny-ingress:默认拒绝所有入站。
  • allow-same-namespace:放行同命名空间内 Pod 间入站。
  • allow-dns-egress:放行到 kube-system 的 53/UDP+TCP(DNS 解析)。
  • allow-kube-api-access:放行到 kube-apiserver 的出站——覆盖 apiserver Pod(443)、API ClusterIP 10.43.0.1/32(443)、以及 master 节点段 192.168.88.0/24(6443)。

RBAC 方面只有一个命名空间内的 leader-locking Role + RoleBinding(绑定到 nfs-client-provisioner ServiceAccount),用于领导者选举,没有 ClusterRole。

命名空间约束

命名空间配了 ResourceQuota 与 LimitRange 做硬约束:

  • Name
    ResourceQuota
    Description
    pods 上限 5;requests 400m CPU / 768Mi;limits 1 CPU / 1536Mi
  • Name
    LimitRange (Container)
    Description
    default 200m/256Mi,defaultRequest 50m/64Mi,max 500m/768Mi,min 10m/16Mi
  • Name
    LimitRange (Pod)
    Description
    max 1 CPU / 1536Mi,min 100m/128Mi

这些配额给一个只跑单副本 controller 的命名空间留了余量,同时防止它意外膨胀挤占 infra 节点资源。

返回 Storage 总览

评论