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

执行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的步骤完成。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值