openstack swift ring文件解析
一直以为对swift的ring文件充满好奇,这段时间重新研究swift,正好借此机会好好研究下。
ring文件时一个Gzip的压缩文件,可以通过相关python库直接读取这个文件,代码如下: gz_file =GzipFile('/etc/swift/object.ring.gz','rb')
这里的gz_file其实就是一个文件句柄,通过read我们可以读取数据进行分析。 1、 前4个字节 ‘RING‘ 2、 第5和6个字节版本信息 1 3、 接下来的四个字节是一个字典(设备信息、part-shift、replica_count)的长度信息 4、 接下来就该字典的内容,如下: {u'devs':[{u'replication_port': 6000,u'zone': 1,u'weight': 1.0,u'ip': u'192.168.246.6',u'region': 1,u'port':6000,u'replication_ip': u'192.168.246.6',u'meta': u'',u'device':u'vdb',u'id': 0},{u'replication_port': 6000,u'zone': 2,u'ip': u'192.168.246.7',u'port': 6000,u'replication_ip': u'192.168.246.7',u'device': u'vdb',u'id': 1},u'zone': 3,u'ip': u'192.168.246.8',u'replication_ip': u'192.168.246.8',u'id':2},u'ip':u'192.168.246.9',u'replication_ip':u'192.168.246.9',u'id': 3}], u'part_shift': 14, u'replica_count': 2} 其中: devs 指的是这个ring中包含哪些设备,就是通过swift-ring-builder add这个操作加进来的设备; part_shift: 32-partition_power; replica_count 指的是副本数; 5、 接下来是replica_count*(2*partition_count)个字节的信息,这部分内容不可直接打印,但load ring文件的时候这部分会转 换成array,作为ring_dict['replica2part2dev_id']的列表项(partition_count = 1 << (32 - ring_dict['part_shift'])),详细 说明如下:ring_dict['replica2part2dev_id']是一个列表,其项目的数目等于replica_count,每一项都是一个array,其形式为 array.array ('H',gz_file.read(2 * partition_count)),array可以打印出来,形式上就是一个数组,每个array包含了partition 个项,每一项的内容就是device的id。 6、至此ring文件就读完了
重点说下ring_dict['replica2part2dev_id']的value的含义。顾名思义,其实就是副本—partition—设备id的映射关系。顶层是 array,每个array对应一个副本;array的大小与partition数目一致;array中每一项对应一个partition;array[partition-num] 得到的就是这个partition的设备id。比如要查询partition=X的设备,方法如下:
Devid=[] For replica in ring_dict['replica2part2dev_id']: Devip.append(replica[X]) ring_dict['replica2part2dev_id']其实就是如下的一个二维数组:
在分析的过程中对swift的概念也有所理解: 创建ring时,通过指定的参数即可计算出partition的数据,partition相关的内容也是存放在ring文件中。在对运行中的程序,partition对应于array,array的数量就是备份的次数。我们可以认为每个partition在每个array中对应一个备份。我们可以查询给定partition的位置(备份几次,就会有几个位置)。
由account/container/object可以查询到对应的part,再由part可以查询到对应的node。 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |