Google File System总结

此文章完全基于作者本人对论文的理解,可能会哪里理解得不到位,仅供参考。

目的

GFS诞生是为了如何设计一个高效的顺序读写的分布式文件系统。

 

需要解决的问题

需要解决的问题都是分布式要解决的惯例了。性能,容错,复制和一致性。

 

性能

利用复数台机器的资源来完成工作,性能就可以有显著提高。所以自然就会想到把数据分片,分成复数片段后分布在不同的机子上,就可以做到同时从不同的机子上读取数据了。

容错

但是一旦你同时运行了成百上千台机器,那么就会将本来很小的错误给放大,本来概率很低的错误就可能会变成经常发生的错误,这时候就需要一个良好的容错系统。

复制

容错有个极其简单的处理思路是你拥有复数数据备份,一旦一个挂掉了你就切换另一个。

一致性

但是一旦你使用了复制,那么你的系统可能会导致数据不一致。为了解决一致性,你需要做更多的工作,那么这就会影响性能。

 

GFS采用的是弱一致性,他们在性能和一致性上取得了均衡点。下面再详细说说。

 

总体设计

1.一个master(有复数个副本)。master保存着文件名->位置的映射表。

2.n个trunk server (同样也是有副本的),trunk server存储了实际的文件数据。文件的分片单位为trunk。

3.master知道所有的文件,所有的trunk server,所有的trunk。

 

master保存的数据

1.filename->trunk id数组的映射。

2.trunk id->struct的映射。struct里包含了list(trunk server),每个trunk的version,哪个trunk server是primary server,least的值。

master的部分数据都会存到硬盘里以便恢复。用的方式是log+定时checkpoint。(为什么不用database, 因为log是顺序的速度比较快,但是如果log太长了也会导致性能下降,所以会在适当的时候加checkpoint减少下次重演的时间)。

 

least

primary server有一个least,这个least master和primary都知道,只有在least期间primary才能担任primary。

 

read操作

1.client发送filename和offset告诉master他想读这个地方的数据。

2.假设一个trunk大小为64MB(论文中用的这个大小),master对offset/trunk size得到数组index,然后通过映射表可以知道trunk id。再通过trunk id去拿到trunk server list。然后将trunk server list返回给client。

3.client会自己去寻找最近的server(论文中没详细介绍如何去找最近的server),然后把请求发给server读取数据,并且cache trunk server list的数据以便下次不用再问master。

4.trunk server通过filename找到对应的trunk的数据后返回给client。已知trunk id和offset,对应trunk的实际偏移量是可以算出来的。

5.如果读取超过一个trunk的大小,提供的底层接口里会把他分成多次请求发给master。

read操作实际上对不同的trunk server读取,读出来的副本可能是不一致的。

 

write操作

本文只提append操作。如果写入跨多个trunk那么客户端会分成多次操作执行下面的步骤

1.client会告诉master我想往filename里append数据。

2.master会告诉client这个文件的最后一个trunk在哪里。

        这里会有两种情况。如果不存在primary,master需要找到拥有最新副本的trunk server。通过和master知道的最新版本号对比可知道哪个副本是最新的。(不能单纯通过取最大来得到最新副本,因为最新的副本可能还没启动),然后选择其中一个拥有最新副本的当作primary。然后master版本号递增,通知primary和secondary他们的身份和当前版本号。

最后将trunk server list返回给client,并且附加primary和secondary的信息。

3.将data发给primary和secondary。primary和secondary收到后会告诉client。

4.当client确认到所有primary和secondary都收到了data后会告诉primary已经全部收到消息。

5.primary会以自己的某种方式按顺序写入数据,因为primary会收到复数的client的请求,所以需要用比如队列的机制去处理。

6.primary会查看末尾,确保trunk还有空间,然后将data写入到trunk末尾。并且告诉secondary以同样的offset写入data。

7.secondary可能会成功也可能会失败。如果全部成功,则会告诉客户端成功,如果有一个失败则返回失败。(注意这个地方,因为这个地方的原因所以你从不同的副本上读取数据是有可能不一样的)

 

若某台secondary挂了,重启定义一遍primary和secondary。

若primary挂了则等待least结束后重新定义一遍。

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值