博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Swift build(.build)和ring(.gz)的数据结构和文件的持久化机制
阅读量:4089 次
发布时间:2019-05-25

本文共 2592 字,大约阅读时间需要 8 分钟。

Ring的数据结构

  • 设备表(devs):将所有Device编号,设备表中的每一项对应一个Device,其中记录了Device的具体位置信息,包括Device Name, Device ID, IP, Port, Weight, Region和Zone等信息
  • 移位值(part_shift):表示Hash之后得出的Key进行移位的位数

    e.g. 假设有65536个node(2^16),有128(2^7)倍的partition数(2^23)。由于MD5是32位,使用part_shift(= 32 - partition_power)将Key映射到partition的2^23的一致性Hash环中

  • 设备查询表(replica2part2dev_id):存储Partition的各个副本与具体的Device ID的映射信息。replica2part2dev_id的每一列对应一个Partition,每一行对应Partition的一个副本

Ring具体映射过程

  • 使用对象的层次结构account/container/object计算出的Key作移位运算后得出Partition的编号,然后在replica2part2dev_id表中查得对应的三备份的Device ID,最后到devs中查得对应Device ID的IP及端口号

构建Ring

    Swift使用swift-ring-builder工具构建一个Ring,可分为三个步骤:

  • 创建Ring文件
       swift-ring-builder <build_file> create <part_power> <replicas> <min_part_hours>
       build_file是build的文件名,2^part_power是Partition的个数,replicas是副本的个数,min_part_hours单位为小时,一般设置24小时,表示某个Partition在移动后必须等待指定的时间才能再次移动
  • 添加设备到Ring中
      swift-ring-builder <build_file> add [r<region>] z<zone>-<ip>:<port>/<device_name>_<meta> <weight>
      region和zone表示Region和Zone的编号,ip:port表示设备所在节点的IP地址及端口号,device_name是该设备在该节点的名次(如sdb1),meta是该设备的元数据,weight是该设备的权重
  • 分配Partition
      swift-ring-builder <build_file> rebalance
      rebalance操作会根据builder file的定义将Partition分配到不同的设备。在rebalance之后需要将生成的Ring文件复制到所有运行相应服务(Account, Container或Object)的节点上,然后用该Ring文件作为参数启动相应的服务

    源码调用过程:

        swift-ring-builder工具的源码入口是bin/swift-ring-builder,这个脚本仅仅是对swift.cli.ringbuilder模块的封装,直接调用了swift.cli.ringbuilder的main函数
  • 首先调用swift.cli.ringbuilder.Commands类的create()函数完成builder文件的构建
  • 其次调用swift.cli.ringbuilder.Commands类的add()函数完成设备的添加并保存到builder文件中
  • 最后调用swift.cli.ringbuilder.Commands类的rebalance()函数实现balance并最终生成ring(.gz)文件

builder的数据结构:

    ring(.gz)文件的数据结构上述已分析,builder的数据结构与ring的数据结构稍有差异,包括: 

{'part_power': self.part_power,
 
'replicas': self.replicas,
 
'min_part_hours': self.min_part_hours,
 
'parts': self.parts,
 
'devs': self.devs,
 
'devs_changed': self.devs_changed,
 
'version': self.version,
 
'overload': self.overload,
 
'_replica2part2dev': self._replica2part2dev,
 
'_last_part_moves_epoch': self._last_part_moves_epoch,
 
'_last_part_moves': self._last_part_moves,
 
'_last_part_gather_start': self._last_part_gather_start,
 
'_dispersion_graph': self._dispersion_graph,
 
'dispersion': self.dispersion,
 
'_remove_devs': self._remove_devs}

builder(.builder)文件和ring(.gz)文件的持久化方式

    builder(.builder)文件的持久化方式

  • 在调用swift.cli.ringbuilder.Commands类的create()函数内部,通过调用的是save()函数将Ring的初始化信息保存到builder(.builder)文件中去
  • save()函数内部首先将Ring的初始化信息转化成builder数据结构构成的dict对象,然后采用pickle序列化的方式将dict对象持久化到builder(.builder)文件中,采用的是更高效的新的二进制协议

    ring(.gz)文件的持久化方式

  • 调用swift.common.ring.Ring类的save()函数实现ring(.gz)文件的持久化
  • save()函数内部首先将ring的数据结构转化成得对应的dict对象,再将其转化成JSON形式,然后将这些数据封装成字符串后写入到Gzip压缩文件中,最后flash

转载地址:http://tmbii.baihongyu.com/

你可能感兴趣的文章
5.WMTS 调用
查看>>
6.3dtiles 调用
查看>>
组件化:局部批量引入示例组件
查看>>
使用 Vuepress 创建自己的技术文档站
查看>>
工具:Nginx
查看>>
7.WMS 调用
查看>>
8.Terrain 调用
查看>>
组件:组件、方法和指令导出
查看>>
window.onresize 与 window.addEventListener(‘resize‘,...) 区别
查看>>
Vue 中添加拖动指令
查看>>
Vuepress CSS 样式覆盖:修改内容宽度
查看>>
《Leaflet 基础知识点》- 鼠标点击事件获取坐标点
查看>>
《Leaflet 基础知识点》- 地图定位、跳转和缩放
查看>>
《Leaflet 基础知识点》- 计算两点距离
查看>>
《Leaflet 基础知识点》- 设置图层透明度
查看>>
《Leaflet 基础知识点》- 添加图形标注
查看>>
Vue 中的图片加载(采坑)
查看>>
《Leaflet 基础知识点》- 在 Vue 中如何使用
查看>>
《Leaflet 基础知识点》- Map 交互事件详细说明
查看>>
《Leaflet 基础知识点》- 鼠标移动事件显示实时坐标
查看>>