知识卡片

Rowkey加随机前缀(salting)消除写热点,代价是一次scan要拆成多路并发

普通读书笔记卡

内容

HBase的Rowkey设计天然面临一个矛盾:如果Rowkey本身是有序递增的(比如按时间戳),写入操作会持续集中打到某几个特定的Region上,形成明显的写热点,无法充分利用集群里其他Region所在节点的写入能力;但如果为了消除热点而让数据随机分布,又会失去Rowkey有序带来的”范围scan”能力(按顺序区间高效扫描一批数据)。给出的解法是加随机前缀(salting):写入时给Rowkey人为加上一个随机选取的前缀(比如从001到100这个范围里随机取一个),这样原本会集中写入同一批Region的连续Rowkey,会因为这个随机前缀被分散打到不同的Region上,从而消除写热点、让集群里所有Region都能分担写入压力。但这个解法不是没有代价的:一旦Rowkey本身带上了随机前缀,原本一次简单的顺序scan操作就不能再直接进行了——因为真正想要的一批数据现在散落在带有001到100这100种不同前缀的各个Region里,要拿到完整的结果,必须对这100个前缀分别发起scan(也就是把原本一次scan拆解成100个并发的scan,再把结果合并起来)。这个案例给出了一条数据分布设计里典型的取舍模式:为了解决写入热点(一种性能问题)而主动引入随机性,几乎必然会以损失某种基于顺序性的查询能力(另一种性能特征)为代价——两者往往不可兼得,因为”写入均匀分布”这个诉求本质上要求数据在物理上被打散,而”范围查询高效”这个诉求本质上要求数据在物理上保持连续有序,这两个诉求在物理布局这个层面是天然矛盾的。这提示了一条评估类似取舍时的判断标准:要不要引入随机前缀,取决于自己真实的负载模式里,写热点带来的伤害和scan性能的损失,哪一个是更迫切需要优先解决的问题——如果写入压力集中是当前系统的主要瓶颈,用scan复杂度的适度提升去换取写入的均匀分布通常是值得的。

参考来源

- 位置:《高可用架构(第1卷)》第6章《大数据与数据库》"6.4 Hadoop、HBase年度回顾"节,"6.4.3 疑问与解惑"(源文件:_epub-src/OEBPS/Text/Chapter6_4_4.xhtml) - 结论依据:原文说明"可以考虑salt的方式,在写入的时候为Rowkey加随机前缀,比如前缀范围001~100,那么我可以随机为Rowkey加上这些前缀来消除热点,在scan的时候需要加上所有的前缀(001~100)来scan,不过这样一个scan就要转化为并发的100个scan",直接支撑本卡片结论。 - 原始内容:可以考虑salt的方式,在写入的时候为Rowkey加随机前缀,比如前缀范围001~100,那么我可以随机为Rowkey加上这些前缀来消除热点,在scan的时候需要加上所有的前缀(001~100)来scan,不过这样一个scan就要转化为并发的100个scan。