syy*_*yys 5 hbase duplicates primary-key-design
我需要存储由userId标识的用户生成的事件.每个用户都属于由companyId标识的公司.我在HBase中提出了一个表格设计如下:
rowkey:< companyId > < 用户id > < 时间戳 >
column-family:info(封装事件属性集,如下所示)
列:< attr1 >,< attr2 > .... < attrn >
我知道这个关键设计将有助于稍后使用部分密钥扫描在companyId和/或userId上查询数据.话虽如此,我有一些问题和疑虑,并希望得到一些想法.
1-如果我们有一个读用例,读取给定时间范围的所有数据,那么使用当前设计,我们将无法使用rowKey.相反,我们必须在时间戳字段上进行全扫描和过滤行(作为attr列之一单独维护)我是否完全偏离此处?
2-如何处理重复?我知道HBase会在这种情况下创建一个新版本的行,但它是否允许稍后根据1中提到的读取用例进行读取?我知道您可以在查询时控制版本,但它是一个好的设计还是错误地重载了本机功能?
3-这涉及区域服务器热点.我们没有单一的密钥,但是如果说,一个特定的公司或用户非常活跃,我们仍然会遇到这个问题.基于服务器数量的散列和分段在这种情况下不起作用?也许如果我们在timestamp字段上哈希并将其附加到rowKey而不是原始值?但问题是,扫描密钥的时间戳组件是不可能的.我们必须在列中有一个单独的列(attr)来捕获它.有什么建议?
非常感谢您提供的任何输入(评论,链接,书籍,想法).
1:阅读用例
这取决于您的用例:
如果您希望在给定时间范围内获取组织的每个用户数据,那么您所拥有的对我来说似乎是正确的,并且您必须对所有组织数据进行扫描。
如果您希望读取给定的所有数据,您当前的密钥设计似乎不错。尽管我会翻转组织和用户 ID 位置来生成新键(rowkey : userId-companyId-timestamp)。由于来自独立用户的数据是不相交的,因此现在不需要将它们耦合在一起。
如果将时间戳推到顶部(rowkey : timestamp-companyId-userId),您可以对以时间范围定义的位置结束的所有组织/所有用户信息运行扫描(跳过全表扫描)
2:重复
注意:Hbase 默认情况下最多记录一个单元格的 3 个版本(也不要将这些版本时间戳与 rowkey 上的时间戳混淆)。您可以增加此限制并从不同版本获取结果,但不建议此版本计数过高。
如果您要覆盖以前保存的值,我建议不要依赖于查找以前保存的版本(尽管有多种方法可以实现这一点)。如果您必须能够保存/获取所有以前记录的数据,您也可以使用新列来存储新值。
3:热点地区
如果一家公司非常活跃,您可以将 companyId-userId 的哈希值附加到您的 rowkey 中。这会将写入分发到任何组织。
如果用户非常活跃并且存在以最佳方式取回所有数据的用例,那么我不确定对密钥或时间戳进行散列是一个好的解决方案。您肯定希望将用户的数据保存在一起,但我不确定这里更好的解决方案是什么。
根据我对你的问题的理解,我可能会将ROWKEY设计为HASH(companyId-UserId)-companyId-UserId-Timestamp