为什么选择 CephFS NFS

方案一

选用 manila generic 驱动

manila generic 驱动还需要在配置文件中另外配置 neutron,nova,cinder 等,因为此驱动下创建 share 时,首先需要创建一个 share-network,然后会在此 share-network 下创建一个 share-server,然后会调用 cinder API 创建一个 volume,挂载到 share-server 上并格式化最后以 NFS 的形式暴露出来。

方案二

选用 cephfs native 驱动

cephfs native 驱动不需要额外的 share-network 和 share-server 便能创建 share,只需要能同 CephFS 通信即可,但是需要租户虚机能直接连接 CephFS 集群,这样可能存在安全问题。

方案三

选用 cephfs nfs 驱动

cephfs nfs 驱动同 native 驱动一样也不需要 share-network 和 share-server 便能创建 share,借助 nfs-Ganesha 解决了网络安全性问题,避免 ceph 在公网直接暴露。Ganesha 为协议转换层,FSAL_CEPH 把 guest vm 的 NFS 协议调用 libcephfs 将 NFS 转义为 Cephfs 协议再存入到 Ceph 中,这样可以隐藏后端 ceph 集群,更适合云的业务场景。

对比

方案一

generic 驱动虽然也能使用 ceph 后端存储,但是只能通过调用 cinder API 创建 volume 进而实现使用 cinder 配置的 ceph 的 RBD 存储,同时还需要使用额外的计算资源和网络资源创建一台 share-server 专门用于 NFS 导出挂载的 volume,具体架构如下图。

1541554777467

如上图所示,简单说来使用 generic 驱动创建 share 时会创建一个 Nova 实例,通过 Cinder 的 Volume 来提供 NFS/CIFS 共享服务。

  • 每个 Share Network 创建一个 Nova 实例
  • 连接到已存在 Neutron 网络及子网中
  • 创建 Nova 实例使用的 Nova 的 flavor、Glance 的 image、SSH Keypair 均是 Manila 配置的
  • Manila 通过 SSH 对 Nova 实例进行配置

相对于使用 cephfs 的两种方案来说,资源耗费太大,每一个 share-network 都需要创建一台 share-server,而且容易因 share-network 和 share-server 出现问题而导致 share 创建不成功,所以在能使用 CephFS 的情况下,此方案不做考虑使用。

CephFS 架构

CephFS 的架构如下图所示:

architecture

最底层还是基础的 OSDs 和 Monitors,添加了 MDSs,上层是支持客户端的 CephFS kernel object,CephFS FUSE,CephFS Library 等。

CephFS 组件间通信

component communication

如上图所示,CephFS 各个组件间通信如下:

  1. Client <–> MDS

元数据操作和 capalities

  1. Client <–> OSD

数据 IO

  1. Client <–> Monitor

认证,集群 map 信息等

  1. MDS <–> Monitor

心跳,集群 map 信息等

  1. MDS <–> OSD

元数据 IO

  1. Monitor <–> OSD

心跳,集群 map 信息等

Client 端访问 CepFS 的步骤如下:

  1. client 端与 MDS 节点通讯,获取 metadata 信息(metadata 也存在 osd 上)
  2. client 直接写数据到 OSD

方案二

使用 cephfs native 驱动创建的 share,只能通过 ceph-fuse 客户端或者 CephFS kernel client 进行挂载,但是在进行用户虚机访问授权的时候会稍微比 cephfs nfs 驱动麻烦点,在进行挂载的时候也需要单独加上 cephx 认证信息,而且需要指定 ceph 集群的 IP 作为挂载点,这就需要用户虚机能与 ceph 集群直连,在生产环境难以推行,所以相比于 cephfs nfs 驱动,此方案也不做考虑。

Ceph FUSE 的 IO Path 较长,会先从用户态调用到内核态,再返回到用户态使用 CephFS FUSE 模块访问 Ceph 集群,架构如下图所示:

fuse arch

方案三

使用 cephfs nfs 驱动创建的 share 会通过 nfs-ganesha 导出为 NFS,可以通过内核中自带的 NFS 客户端进行挂载,无需安装额外的 ceph-fuse 客户端,而且在授权用户虚机访问控制只需要使用用户虚机 IP 即可,在进行挂载时也只需要像挂载普通的 NFS 即可,挂载点就是指定的 nfs-ganesha 服务器所在位置,不会暴露 ceph 的公网地址,更好的隐藏了 ceph 集群,适用于当前云服务的场景,所以综合各方面来看,此方案可能是 manila 驱动目前较好的选择。

如下图所示,是使用 cephfs nfs 驱动的架构:

1541559296724

用户态的 nfs-ganesha 直接把 CephFS 导出作为 NFS 服务器,因此 NFS 客户端读数据的 IO 流为:内核态的 RPC 模块先接收到 NFS 客户端的数据访问请求,经过解析,调用运行在用户态 ganesha.nfsd 模块中对文件系统抽象层中的数据访问接口,最后通过 libcephfs 访问 CephFS 集群。在这里 libfsalceph 库处理文件的读写、目录的处理和 ceph-fuse 的功能是一致的,但本方案并不需要通过 FUSE 打交道。

总结

对于 MDS 来说:

  • 单 MDS 的情况下,短暂的 MDS crush 并不会影响客户端对一个 file 的读写

  • 单 MDS 的情况下,MDS crush 后,client 端对没有缓存过 caps 的文件操作会 hang 住

  • 主从 MDS 的情况下,只要有一个 MDS 正常,cephfs 的服务就不会中断

  • 主从 MDS 的情况下,两个 MDS 都 crush 后,影响与单 MDS 的一致

在生产环境中,建议配置主从 MDS 的模式,提高 cephfs 的高可用性。

对于 CephFS 总结来说有以下几点:

  • CephFS 是 production ready 的,能满足基本生产环境对文件存储的需求
  • CephFS 的主从 MDS 是稳定的,优于单 MDS 配置
  • 生成环境使用 CephFS 时,独立机器上配置 MDS,调大“mds_cache_size”
  • 使用 CephFS 时,避免单个目录下包含超级多文件(more than millions)
  • CephFS 能跑满整个 ceph 集群的性能
  • 默认 stripe 模式下(stripe unit=4M, stripe count=1, object size=4M), CephFS 的性能就挺好
  • 小文件的应用场景下,尝试配置小的 stripe unit,对比默认 stripe 的性能

选择 cephfs nfs 驱动

总的说来,generic 驱动无论是从配置、性能、稳定、性能和使用便捷性上来说,对比 CephFS 驱动可能都有所不足,而 CephFS 所对应的两种驱动中, cephfs nfs 驱动对比 cephfs native 驱动在配置、性能、安全、适用性和使用便捷性上要更胜一筹,所以在目前几种备选方案中,选择 cephfs nfs 驱动作为生产环境方案是最为合适的。