使用增量计数器在Couchbase群集中生成唯一密钥

Mik*_*ock 9 nosql couchbase

我听说Couchbase和其他NoSQL数据库最常见的问题是如何为记录生成唯一键 - 或者更具体地说 - 如何复制常见关系数据库的AUTO INCREMENT功能.

经常提到的Couchbase中的解决方案是增量函数,您可以在数字键上调用增量,它将按顺序生成一个新的唯一编号.

我的问题是,我无法理解我在复制方面遇到的大问题.

假设您有一个包含三个Couchbase节点的集群,并且您正在存储请求日志.您想要键入此日志,以便创建名为"requestlog_counter"的条目.

现在说我们有4个web节点,每个节点每秒接收20个请求,每个节点需要记录为"request :: {ID})".这是80秒的请求.

假设节点1和3具有一点点网络延迟,但两者都在同一时间接收这40个请求中的一个.您的脚本会递增请求计数器(假设此示例当前为1500)并获取ID.当然,BOTH Couchbase实例现在可以将1501返回到Web节点1和3,并且两个服务器现在都将尝试将它们正在处理的请求存储为"request:1501".

现在,复制将处理这一点,基本上最新的将赢得.但是你现在已经丢失了一个请求的记录.

那么现在是否意味着实际上你需要一种更好的方式来键入重要数据,并且在NoSQL集群环境中应该避免使用自动增量来获取绝对值和唯一密钥生成?

或者 - 作为密钥生成过程的一部分,您可以做些什么使100%可靠.

还请考虑使用跨数据中心复制的多集群环境.

谢谢.

麦克风

m03*_*eek 8

首先根据couchbase 文档功能,increment并且decremant在集群内是"原子的".因此,如果你使用它们来生成"自动增量",那么一切都应该正常工作.

但是如果你想保留在couchbase中保存新项目的同时你不会覆盖现有的(例如"BOTH Couchbase实例可以返回1501"的情况)你可以使用商店操作StoreMode.Add.因此,如果您同时打电话couchbase.store(StoreMode.Add, "request:1501",value),一个请求将成功完成,其他请求将失败并且您可以捕获此"失败"并尝试再次重复该存储操作(获取新密钥的新自动增量ID)

  • 正如我所说,增量在一个集群中是原子的.如果您打算使用XDCR,则需要在"自动增量"中添加类似集群ID的内容.即`请求:<cluster_id>:<autoincrement_id>`或`request:<autoincrement_id>:<cluster_id>`.在这种情况下,即使您获得两个相同的自动增量ID,您的密钥也将是唯一的,因为它将具有唯一的`cluster_id`.但是,对我来说,如果我需要XDCR,我将只使用GUID并添加类似时间戳的内容来排序值而不关心原子操作. (3认同)
  • 好的,请考虑跨数据中心复制示例.假设DC1和DC2之间的链路断开5秒,在此期间DC1和DC2每个接收并处理200个请求.我们的汽车公司现在发生的事情比自动增量都增加到1700并且两个DC都有使用这些ID存储的记录'那么会发生什么?在这种情况下,存储命令不会失败,因此,无论是否原子,操作都会导致数据一致性发生相当可怕的事情? (2认同)