暂无图片
暂无图片
暂无图片
暂无图片
暂无图片

分布式文件系统

Lord Lean Notes 2021-07-01
739
近期在思考分布式文件系统,于是去查阅了一些资料,在吸收完之后,照猫画虎写下几篇文章,来作为自己对分布式文件系统的理解。
首先作为一个分布式文件系统,要先思考一个文件系统怎么设计,在设计中可能会遇到哪些问题,并采用怎样的解决方案?所以我们可以先从怎样设计一个文件系统思考。
一个文件系统

首先要考虑的是文件上传的情况,文件上传的方式有多种,比如表单上传、简单上传、追加上传、断点续传和分片上传。我们这种情况可以采取追加上传和断点续传的方式来完成大文件上传。追加上传可以应用于文件初次上传的场景,而断点续传则可以应用于文件上传过程中失败,再次上传的场景。

在文件系统中,尤其是存储文件大小几百M到几G的这种场景。当文件写入成功之后,如果涉及到对文件的修改操作,并且修改内容较多的情况,采用在文件尾部追加数据的方式,而不是采用随机写的方式,以此来减少磁盘I/O的阻塞。

读取操作提供流式读取和小规模读取两种操作。小规模的读取操作是在文件中读取几kb的内容,如果小规模读取操作对性能较为关注,可以将多个读取操作合并为一个顺序操作,减少在文件中移动位置的操作。

流式读取文件的方式采用顺序读+页缓存的方式,来加快读取文件的效率。并且还可以对操作系统的Block Size进行设置,增加每次读取内容的大小,Block Size的作用是操作系统每次从文件中读取字节的大小。

分布式文件系统

当一个系统涉及到分布式的场景时,就需要通过许多节点来保证系统的正常运行,并且系统也要支持多客户端并行追加到同一个文件中的场景。

系统中也需要通过快照以较低的成本来创建某个文件或目录树的拷贝,还要提供原子的记录追加操作,这样来保证多个客户端的追加操作的原子性。

分布式文件系统中高性能的网络带宽要比低延迟重要的多,所以系统应能够高效率、大批量的处理数据,不需要对响应时间做严格的要求。

文件系统架构

一个文件系统集群包含一个Master节点、多台Chunk服务器,并且可以被多个客户端访问,如图1所示。文件系统存储的文件被分割为固定大小的Chunk。在Chunk创建时,Master会为Chunk分配一个唯一的标识,而Chunk服务器会将Chunk以Linux文件的形式保存在硬盘中,并根据指定的Chunk的字节表示读写块数据。

Master节点管理文件系统的元数据,这些元数据包括名字空间、访问控制信息、文件和Chunk的映射信息以及当前Chunk的位置信息。Master还会使用心跳信息和每个Chunk服务器通讯,发送指令到每个Chunk服务器并接收Chunk服务器的状态信息。

客户端和Chunk服务器都不需要缓存文件数据,简化了整个系统的设计与实现。但是客户端会缓存存储在Master节点的元数据,Chunk服务器将文件数据以本地文件的方式保存,在Linux的文件系统会把经常访问的数据放在内存中。

Master节点可以通过全局的信息精确定位Chunk的位置并进行复制。而且客户端通过减少对Master节点的访问以及通过Master节点进行读写操作,而是直接操作Chunk服务器上的Chunk,避免Master节点成为系统瓶颈。

Chunk尺寸

Chunk尺寸的大小也是一个关键因素,这个参数的大小尽量设置为4的n次幂,并且会远远大于一般文件系统的Block Size。Chunk文件的大小只有在需要的时候才会扩大,惰性空间分配的策略避免了因内存碎片而造成的空间浪费。

Chunk选择一个较大的尺寸可以减少客户端与Master节点的通信,在获取一个Chunk的位置信息后,可以对这个Chunk写入多次,以此来降低系统的负载。即使是小规模的随机读取,采用较大的Chunk尺寸,客户端可以轻易的缓存数TB数据集的Chunk位置信息,还可以对一个块进行多次操作,这样可以通过与Chunk服务器保持长时间的TCP链接来降低网络负载。还可以减少Master节点元数据的保存量,这样可以占用较少的内存。

Chunk选择一个较大的尺寸也是有缺陷的,当小文件包含多个Chunk或只有一个Chunk时,当许多的客户端访问这个Chunk文件时,就会出现热点问题。导致存储Chunk文件的Chunkfuwuq局部负载严重。对于这种问题,只能说增加集群机器,来提升服务器的负载能力,针对集群中机器的节点可以采用人工管理的形式。

一致性模型

文件系统对于命名空间的创建和修改是原子性的,其是由Master节点的命名空间锁保证了原子性和正确性,通过操作记录的日志来保证顺序的。

系统交互

上图是文件系统的租约机制和数据变更顺序图,客户机在操作数据时,会先向Master节点询问哪个Chunk持有租约,没有则选出一个。然后主Chunk对数据进行序列化,所有的副本在遵循这个序列进行操作,主Chunk会给离自己最近的副本传递这个序列。当所有的副本都收到数据之后,客户机会向主Chunk服务器发送写请求,这是主Chunk服务器会对自己缓冲的请求进行排序,按照顺序把操作应用到自己本地的状态上。

主Chunk服务器再把写请求发送到所有的副本,副本按照请求的顺序执行一次。当所有的副本恢复之后,其完成操作。

如果一些写入的数据较多,跨越多个Chunk块,则会拆解成多个写请求来进行操作。

数据的流向是怎样的呢?

数据是以管道的方式,每台服务器会选择离自己最近、没有在接受数据的一台服务器进行数据的传输。这样可以充分利用每台机器的带宽,来快速的传输数据,还可以避免出现网络瓶颈和高延迟的情况。

怎样保证操作的文件中原子的记录追加呢?

使用记录追加,客户机只要指定要写入的数据,文件系统保证至少有一次的原子写入操作执行成功,之后返回写入数据的偏移量给客户机。记录追加的引用是为了解决分布式情况下多个客户端并行对同份数据写入的同步机制的开销。

快照

客户端发起快照请求时,会对文件或目录树做一次拷贝。文件系统可以采用copy-on-write的技术来实现快照。收到快照请求时,Master并没有立即对指定Chunk拷贝,而只拷贝其元数据并对指定Chunk的引用计数增1。等到客户端需要对指定Chunk块修改时,再在本地复制,并确保新Chunk拥有租约。

Master命名空间锁

很多针对Master的操作可能会执行较长的时间,比如一个快照操作可能要回收快照所覆盖的Chunk块所在的ChunkServer所在的令牌,但是我们不希望操作期间,阻塞Master的其他操作。所以使用Master命名空间锁来允许多个操作同时进行。

Master是将每个文件的命名管理在元数据中,并通过压缩前缀的方式使其能在内存中保存,每个文件的命名都会有一个对应的读写锁。通过读写锁的方式可以防止读的时候文件被修改和在同一个目录下允许并发修改。

Chunk的重新复制、重新均衡

当Chunk副本的数量小于用户指定的数量后,会重新尝试复制一个Chunk副本。在重新复制时会选择活跃文件的Chunk,减少对应用程序的影响。

并且Master节点会定期进行均衡副本,将副本调整到更好的磁盘和负载分布,平衡磁盘空间的使用。

垃圾回收

当文件删除后,并不会立即归还可用的物理空间,而是将文件改为一个隐藏文件,并且包含了一个时间戳。在Master命名空间的常规检查中,会移出这些超过3天的隐藏文件,但是文件依旧可以通过新的、特别的名字读取,并可以通过改名退出删除状态。当隐藏文件从命名空间中移除后,在Master内存中的元数据也会删除,这时ChunkServer在常规心跳信息中会发现此Chunk已成为孤岛,随即释放占用的物理空间

Chunk过期副本删除

Chunk文件的副本可能会因为ChunkServer的失效时间导致丢失了Chunk的变动而导致过期,Master通过正常的垃圾回收机制来删除过期副本,同时采用Chunk版本号,来确保每次操作都是最新的版本。

文章转载自Lord Lean Notes,如果涉嫌侵权,请发送邮件至:contact@modb.pro进行举报,并提供相关证据,一经查实,墨天轮将立刻删除相关内容。

评论