自动负载均衡(Load balance)

背景

tablet是tera中管理数据的基本单位,所有的数据存取访问会落在tablet之上,通过预分表、split、merge等操作可以调整tablet所覆盖的数据范围,这样表格的逻辑结构得以确定。

当一个表格被分割为若干tablet之后,每个tablet中包含的数据量不同、承载的数据读写压力也不同。如何将这些tablet合理的分配到tabletnode之上,并且在系统运行过程中动态调整,保证上层服务稳定运行便是“自动负载均衡”需要解决的问题。

负载类型及特点

  1. 数据量

    • 关键资源:缓存容量(SSD、内存等)
    • 数据量均衡后可以最大化利用缓存磁盘或内存,使系统服务尽可能多的数据。
    • 经验表明,其它几种负载通常与数据量有很强联系,因此在系统运行中,保持各tabletnode之间数据量均衡是首要目标。
    • 对时间不敏感,数据量的变化通常较慢,而存储通常有较大buffer,因此只要在一个较长的间内保持均衡即可。
  2. 随机读

    • 关键资源:CPU
    • 当读压力大时,CPU会成为系统首先被用完的资源。最大化利用CPU,使系统提供尽可能高的读吞吐。
    • 一旦CPU被耗完,系统响应任何请求都会受到较大影响,因此读负载的均衡也非常重要。
    • 时效性要求高,读负载变化很快,容易形成热点,如果不能在较短时间内将热点的单机负载降低,CPU长时间用尽对系统危害很大。
  3. 顺序扫描

    • 关键资源:CPU、线程池
    • 通常扫描需要返回的数据量更多,单个任务的执行时间较长。当请求很多时,CPU和线程池的负载会显著增长。
    • 关键资源:IO(网络、磁盘)
    • 写会产生后台的compact操作(写放大),使系统的IO消耗较高。但在万M网卡及DFS环境下,磁盘和网络IO通常不是瓶颈。

实现

几种负载中数据量和读对系统的服务能力有较大影响,tera当前在这两种维度下实现自动负载均衡。

tera负载均衡由master完成,依赖tablet move操作,即从一个tabletnode上将其unload,再从另外一个tabletnode上load。

负载均衡在query tabletnode完成一轮后启动,保证用最新的tabletnode负载信息进行操作。

目标:从当前tabletnode->tablet的映射集合中通过策略选出部分需要移动的tablet,将其从原tabletnode中unload,并在负载较轻的tabletnode上load起来。

每次负载均衡会有一个待迁移tablet总量控制,保证每次并不会迁移过多tablet,可以保证任一时刻tablet的可用比例,以及cache失效比例。

过程分为两阶段:

  • 第一阶段优先进行读负载均衡,将读热点打散。
  • 第二阶段进行数据量均衡,视负载不均的情况可能执行N轮。

读负载均衡

  • 判定出现读热点:此tabletnode上发生读请求pending数目超过某阈值。
  • 并不期待将所有tabletnode的读请求完全平均,只将读热点打散至可服务状态即可。
  • 区分cache失效导致pending和cpu不足导致的pending,只对后者进行迁移
  • 迁移时每次选qps第二高的tablet,保证最忙tablet优先得到服务
  • 优先触发,剩余迁移quota用于size均衡
  • 将历史负载值加权加和至最新值中,平滑负载抖动

数据量负载均衡

  • 判定需要迁移:最大与最小数据量tabletnode比值超过某阈值。
  • 迁移前校验迁移结果,防止出现数据量反转,形成迁移的死循环。
  • 迁移时选择最有可能将数据量均衡的tablet进行迁移,防止迁移过多小tablet。
  • 在允许范围内可一次执行多轮,提高均衡较果。