您的位置:首页 > 移动开发 > Swift

Swift源码解析之添加设备到Ring

2018-03-30 18:43 453 查看
执行swift-ring-builder的add命令添加设备到Ring中,与create命令类似,add命令由swift.cli.ringbuilder.Commands类add()函数完成
# swift/cli/ringbuilder.py
def add():
#_parse_add_values()解析参数,并返回一个device的列表,然后检查新添加的device是否在devs列表中,
#如果没有,则通过RingBuild类的add_dev()函数将新的device添加到Ring中
if len(argv) < 5 or len(argv) % 2 != 1:
print Commands.add.__doc__.strip()
exit(EXIT_ERROR)
for new_dev in _parse_add_values(argv[3:]):
for dev in builder.devs:
if dev is None:
continue
if dev['ip'] == new_dev['ip'] and \
dev['port'] == new_dev['port'] and \
dev['device'] == new_dev['device']:
print 'Device %d already uses %s:%d/%s.' % \
(dev['id'], dev['ip'], dev['port'], dev['device'])
print "The on-disk ring builder is unchanged.\n"
exit(EXIT_ERROR)
dev_id = builder.add_dev(new_dev)
print('Device %s with %s weight got id %s' %
(format_device(new_dev), new_dev['weight'], dev_id))
builder.save(argv[1])
exit(EXIT_SUCCESS)
最终使用第一步中创建的swift.common.ring.builder.RingBuilder类实例的add_dev()函数完成设备的添加。
# swift/common/ring/builder.py
def add_dev(self, dev):
"""
将一个设备添加到ring里面去。这个设备的dict数据至少需要包含以下的键值(key)
====== ===============================================================
id 设备的唯一编号(类型为整数),如果"id" key在dict中没有指定,则默认该设备的id为系统中下一个可用的id号
weight 这个设备的权重。这个权重值用来暗示会有多少个partition分配到这个设备上来。
region 设备所在的region号(类型为整数)。
zone 设备所在的zone号(类型为整数)。一个partition会被尽可能地发配到分布在不同的(region,zone)的设备上去。
ip 设备的ip地址
port 该设备的tcp端口
device 该设备的名字(譬如,sdb1)
meta 元数据,用于存储用户自定义数据,譬如设备上线时间,硬件描述,等等
====== ===============================================================
注意::添加一个设备不会立即导致rebalance,因为用户可能想在添加多个设备之后统一做rebalance
"""
if 'id' not in dev:
dev['id'] = 0
if self.devs:
dev['id'] = max(d['id'] for d in self.devs if d) + 1
if dev['id'] < len(self.devs) and self.devs[dev['id']] is not None:
raise exceptions.DuplicateDeviceError(
'Duplicate device id: %d' % dev['id'])
# Add holes to self.devs to ensure self.devs[dev['id']] will be the dev
while dev['id'] >= len(self.devs):
self.devs.append(None)
dev['weight'] = float(dev['weight'])
dev['parts'] = 0
self.devs[dev['id']] = dev
#根据设备的weight计算应该接纳的parttion个数
self._set_parts_wanted()
self.devs_changed = True
self.version += 1
return dev['id']
这个函数先计算所要添加device的ID,ID值可以不是连续的,设备表中间允许空洞的存在。然后将设备加入到Ring的设备表中,最后设置相关flag,devs_changed表示设备表有变化,需要rebalance。这个函数返回后,swift.cli.ringbuilder.Commands类的add()函数会再次调用RingBuild类的save()函数,将更新过的Ring信息写到builder文件中去。到此添加设备到Ring的步骤完成。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  Swift