鉴于TimeUUID在CQL中允许您方便地使用now()
,您是否有任何理由不直接始终使用TimeUUID而不是普通的UUID?
UUID
和TIMEUUID
在Cassandra中以相同的方式存储,它们实际上只代表两种不同的排序实现。
TIMEUUID
列首先按其时间组件进行排序,然后再按其原始字节进行排序,而UUID
列首先按其版本进行排序,如果两者都是版本1,则按其时间组件进行排序,最后按其原始字节进行排序。有趣的是,UUIDType
和TimeUUIDType
之间的时间组件排序实现在Cassandra代码中是重复的,除了格式不同。
我认为UUID
与TIMEUUID
的问题主要是文档:如果您选择TIMEUUID
,则表示您正在按照时间顺序存储内容,并且这些内容可以同时发生,因此简单的时间戳不足够。使用UUID
表示您不关心顺序(即使在实践中,如果将版本1的UUID放入其中,列也会按时间排序),只是想确保事物具有唯一的ID。
即使使用NOW()
生成UUID
值很方便,但对于其他人阅读您的代码来说也非常令人惊讶。
总体来说,即使在大局上没有太大关系,但是对非1版本的UUID进行排序会比版本1稍快一些,因此如果您有一个UUID
列并自己生成UUID,则可以选择其他版本。
根据文档,TimeUUID
其实就是一个普通的UUID
。
UUID实际上是一个128位的值。想象一下这是一个非常大的数字。
特定的位可以通过多种方法确定。最原始的方法是将计算机网络硬件的MAC地址、当前日期和时间、加上一个任意数和一个随机数相结合。将所有这些内容压缩在一起,得到一个几乎是唯一的数字。
后来,由于各种原因(安全、隐私),在生成UUID值时发明了其他方法来组装位。这些其他方法省略了日期时间和/或MAC地址作为配料。重点是:并非所有UUID值都具有嵌入的日期时间值。一些建议
Cassandra似乎用这个特定版本的UUID来提取128位中的日期和时间部分。从UUID中提取日期时间是一个不好的想法。
首先,UUID从未旨在用于此类历史跟踪。事实上,UUID的规范明确承认(a)计算机时钟可能被重置,因此(b)后生成的UUID可能比以前的UUID记录了更早的日期时间。不从UUID中提取日期时间的另一个原因是,您可能会拥有并非通过时间方法生成的UUID,因此您将基于实际上并不代表创建日期时间的位构建数据时间值。第三个原因是,当编程代码以后进行重构时,UUID可能会在不同的时间生成,而数据库记录则不同,因此使用UUID的日期时间会引导错误。
如果您需要跟踪日期时间历史,请显式地进行跟踪。在您的数据中创建日期时间字段。顺便一提,要在UTC中跟踪该日期时间,但这是另一个话题。
insert into test_tuuid(1, now())
insert into test_tuuid(1, now())
insert into test_tuuid(1, now())
insert into test_tuuid(1, now())
49cbda60-961b-11e8-9854-134d5b3f9cf8
49d1a6c1-961b-11e8-9854-134d5b3f9cf8
49d59e61-961b-11e8-9854-134d5b3f9cf8
49d8d2b1-961b-11e8-9854-134d5b3f9cf8