Juicedata 合伙人:云上文件系统有何不同,看 JuiceFS 如何做?
JuiceFS 是为云设计的分布式文件系统,该项目创立于 2017 年,初始阶段是在全球十几家不同的公有云上发布全托管服务。到 2021 年的时候,我们向社区发布了一个开源的社区版本。
开源之初,我们先选择了 AGPLV3 许可证,在经过一年的发展之后,JuiceFS很快受到了来自全球社区的响应,很多人开始用起来,我们的用户群里也变得挺热闹。在这个过程中,我们也发现在 AGPLv3 许可的选择不够开放。所以开源一年之后,我们发布第一个 LTS 版本 v1. 0 的时候,同时把许可证也改成了Apache2。
希望在整个数据生态,上下游生态,还有一些其他的合作伙伴做集成的时候,都能基于Apache 许可做得更加的轻松和开放。
JuiceFS已开源满两年,目前每天从我们能看到的部分数据,在全球已经有接近 2000 的活跃集群在使用。在 GitHub 上有7700+颗Star。在全球的分布式文件系统里,JuiceFS已经成长到第四的位置,应该是过去这两年间成长最快的一个项目了。
上述做了项目的介绍,今天主要想讲一下JuiceFS项目的一些设计的理念和故事。本期分享主要会以三个部分展开。
首先会简单介绍一下什么是文件存储,它与我们经常听说的 S3 对象存储会有什么差别。也会带大家回顾一下文件存储的发展过程,然后介绍JuiceFS 在设计过程中的一些理念、思考,以及我们最终在工程上的实践。
分享概要:1.回顾文件存储的发展,以及当下的痛点与挑战2.JuiceFS 的设计理念与方法3.JuiceFS 在业务中的应用与收益
先搞清楚什么是文件系统
文件系统,是一个计算机领域很基础的概念,它基础到往往会被我们日常使用的时候忽视。在 Wikipedia 上的介绍,文件系统是一种用目录来组织数据的方法和数据结构。它为了让我们的数据可以更方便地存储和访问,所以更直观一点看文件系统里我们会接触到的概念,一般会有文件,文件夹(也叫目录),还有像权限、时间戳、软链接、硬链接,还有锁这些概念。我们最常见的肯定是单机文件系统,比如 Linux 里有ext4、XFS, Windows 有FAT32、NTFS, macOS 也有自己的文件系统。它们的作用是把我们买回来的一块硬盘,通过文件系统定义的数据结构去格式化,在硬盘上就占用一小块空间,里面是一个分区表,分区表中的数据管理了整块硬盘上文件与目录的组织形式。文件存储和对象存储之间到底有何差别
有些开发者并不清楚文件系统和对象存储二者之间到底有何差别,我举一个例子。
这张图上列出来了一个文件系统,它以目录树的形式。可以看到在根目录上有一个名字为 /foo的目录。在目录下又有多层的子目录。如果将类似的结构展示在对象存储里是什么样?
大家可以看到,在对象存储里没有目录结构,我们所有的文件或者叫做对象都是以扁平的方式存放。在 S3或者所有的对象存储里都有一个最基本的概念,叫做 bucket(桶)。这个桶相当于我们文件系统里的 volume(卷)。比如 Linux 中,我们可以挂载一块硬盘,它就是一个卷,且可以挂载多个卷。
同样 S3里也你也可以创建多桶。但是在这一个桶里,它是不分上下左右层次的,所有的文件或者数据都是对象,都往桶里扔,它们在桶里是没有层次结构的管理。但是为了方便自己的记忆,每一个对象有一个key,相当于一个 ID 标识符。所以我们可以将之前文件系统中多层的目录结构,用路径风格的写法作为对象 key 的名字。比如 /foo/a/aaa等,看起来也是一个路径,但是在对象存储里并没有对应的数据结构,它就是一个字符串。
从用户的角度看,数据都存进去了。甚至我们在对象存储的控制台里,也能看到文件夹的概念,还能一层一层点进去,这是桌面工具通过这种路径风格的 key 帮助我们做的转换,提供了一个接近本地文件系统使用的用户体验,它其实和对象存储原生的目录结构是不一样的。其差异会体现在哪?
举一个例子。我们要将最顶层的附文件夹改名为 bar。
在 Linux操作里,我写的 Shell 的指令 mv /foo /bar,在文件系统里执行之后,因为有原生目录的数据结构,所以每一层目录之间是一个类似链表的结构。我修改顶层 /foo的目录名,就是一个原子操作,只要找到目录对应的数据结构,将其中的名字改掉即可。所以是原子操作,瞬间完成,也不会影响到数据的一致性。
但是在对象存储里,我们这些对象之间没有数据结构的关联,所以每一个对象都是独立的。我们要想把 /foo的根目录改名,实际上在对象存储里就是要找到所有以 /foo为前缀的 key 对应的对象,这意味着我们要对所有的对象做一次搜索。
在对象存储内部的实现里,它通常会对所有的 key 做一个索引。为了方便我们做查找,将 /foo开头的所有 key 都找出来了,可能是几个、几万个,也可能几百万个。
做改名的时候,根据对象存储自己的设计架构,key 的名字通常会通过哈希算法指定 key 对应的数据要被存放在哪一个节点上,这意味着key 的名字只要改变,数据会被重新分配到另一个存储节点上,所以不能直接对 key 做改名的。
在对象存储里,要想执行 rename 操作,通常需要先做全局的搜索把需要的对象都找出来,做一次数据拷贝,再用新的名字复制一份新的数据出来。假设我们有几万个对象命中,则需要对它们用新名字拷贝一遍。有了上图中右边这一列,同时还要更新 key 的索引,其后再删掉所有旧的 key 和数据。结合上述所言即可知道一个简单的 rename要分为几个步骤,而且在各步骤之间没有事务保障,需要一步一步地执行完成。一来有可能在中间失败;二来如果在这个过程中,有其他的进程访问数据,得到的结果也是中间状态,也就是说数据没有强一致性保障。客户端可能得到了中间状态的数据,会给上层应用带来一些正确性和稳定性的影响。这也是面向对象存储编程时需要特别注意的。
当然,我们去看 S3标准API 是没有 rename 这样的 API 的,S3 的设计是希望我们的数据一次写进来,要么保留,要么删掉,不会做更新。这也是与文件系统的不同。所以如果我们的数据是需要一次写入,多次访问,只读,甚至可能是通过CDN 要做分发,是非常适合对象存储的一个场景。
如果你的数据需要经常更新,需要读取目录中所有文件做分析训练,比如在大数据和 AI 的这些场景里,对象存储的设计是不适合这些业务场景的,文件存储会更加适合。文件存储的发展
下文介绍一下文件存储的发展过程,文件存储的发展比对象存储要早得多。在最早的时候,大概在上世纪八九十年代的时候就有了最初的文件存储产品,当时是硬件一体机的形态。在上述三个能力之下,它也牺牲了一些其他能力,比如文件系统的语义丰富度,在 S3中做了大幅的裁剪,满足UGC需求是完全没问题的,不过后来因为成本低,扩展能力强,用户在云上的大数据和 AI 等场景,大家也希望能够用这样的存储服务,但也逐渐发现了对象存储在这些复杂的计算分析场景上的不足。我们自己也是遇到了 S3在复杂计算场景上的不足,到 2016、2017 年有了构思一个新产品的想法。JuiceFS 也是在 2017 年开始,我们希望能够为云环境设计一个新的分布式文件系统。
分布式文件存储
上文提到的第一代软件定义的分布式文件系统,此处列了一个列表,现在有一半以上仍然在大量使用,比如GPFS已经是一九九几年的项目了。云上文件系统要如何设计?
在云上去设计的时候,我们应该如何做?云之声,他们是做声音领域的一家AI 科技企业,他们在自己的超算平台里使用 JuiceFS,替代了以前 Ceph的使用,解决大量小文件的管理,同时简化了运维投入。
乾象投资是一家快速成长的量化私募基金,他们将自己的量化策略研究构建在云上,JuiceFS 为弹性算力提供了足够的吞吐能力,尤其是访问热点数据所需的吞吐。 深势科技是一家做 AI for Science,为新药研发领域服务的科技企业,他们也会利用JuiceFS 去做多云上面的存储统一。 理想汽车把他们新能源汽车的数据分析平台,由原来的 HDFS 迁移到JuiceFS上使用,可以使其在云上更方便地扩展,支持业务的快速成长。 一面数据是隶属于英国的一家传媒公司旗下的针对电商快消领域分析咨询的公司。他们会关注全网的电商数据,所以数据平台于他们而言是非常重要的一个环节。最初是在机房里建设数据平台,后来借助JuiceFS 帮助他们平滑地迁移、上云,转变为混合云架构,算力继续使用机房资源,存储构建在云上,数据平台也变为存储计算分离架构,更容易做扩缩容,让自己的资源利用率也更加的灵活高效。 东南亚的电商Shopee,他们使用JuiceFS实现了 ClickHouse 的数据冷热分层存储,在用户无感的情况下实现了客观的成本优化。 火山引擎把JuiceFS 用在了自己边缘云上。
|嘉宾介绍|
苏锐
JuiceFS 社区Juicedata 合伙人
作为 1 号成员参与创建 JuiceFS,一直深度参与在开源社区中支持开发者使用 JuiceFS。