0

我有cassandra如下模型。

from uuid import uuid4
from uuid import uuid1

from cassandra.cqlengine import columns, connection
from cassandra.cqlengine.models import Model
from cassandra.cqlengine.management import sync_table


class BaseModel(Model):
    __abstract__ = True

    id = columns.UUID(primary_key=True, default=uuid4)
    created_timestamp = columns.TimeUUID(primary_key=True,
                                         clustering_order='DESC',
                                         default=uuid1)
    deleted = columns.Boolean(required=True, default=False)

class OtherModel(BaseModel):
    __table_name__ = 'other_table'
    name = columns.Text(required=True, default='')



if __name__ == '__main__':
    connection.setup(hosts=['localhost'],
                     default_keyspace='test')
    sync_table(OtherModel)

    OtherModel.create(id='d43ca2c3-b670-4efc-afd7-b46ada88c3fc', name='test')

当我创建记录时,它会设置created_timestamp我的系统或我执行此代码的位置。

我的系统和cassandra服务器有不同的时间戳。

如果我在系统时间所在的位置执行此操作,2017-01-13 10:20:30那么它将时间戳设置为相同。如果我再次从另一个系统执行相同的timestamp操作2017-01-13 10:20:20,那么它设置相同。

当我运行查询时

select * from test.other_table where id=d43ca2c3-b670-4efc-afd7-b46ada88c3fc limit 1;

它应该返回latest最后插入的(最后一个)记录,但由于系统时间戳与我插入记录的位置不同,它会给出最先插入的第一条记录。

4

1 回答 1

1

从上面的 python 代码创建的架构是:

CREATE TABLE test.other_table (
    id uuid,
    created_timestamp timeuuid,
    deleted boolean,
    name text,
    PRIMARY KEY (id, created_timestamp)
) WITH CLUSTERING ORDER BY (created_timestamp DESC)

鉴于您的示例, created_timestamp 是主键的组成部分,因此表中将有两个不同的行 10:20:30 和 10:20:20。将 order 设置为 DESC,您的读取查询将按排序顺序返回值,最大的在前或 2017-01-13 10:20:30。插入行的顺序无关紧要,因为 created_timestamp 是一个聚类列。

如果 created_timestamp 不是主键的一部分,那么 Cassandra 将只返回最新值。Cassandra 有一个由协调器生成的内部单元格时间戳,它确定何时插入或更新单元格。Cassandra 的合并过程在读取请求期间使用它来确定最后插入的值。您不能从客户端代码中设置它,但您可以使用 CQL writetime()函数查看 upsert 时间。

例如,

select id, dateOf(created_timestamp), writetime(name) from other_table;

将返回:

 id                                   | system.dateof(created_timestamp) | writetime(name)
--------------------------------------+----------------------------------+------------------
 d43ca2c3-b670-4efc-afd7-b46ada88c3fc |         2017-01-14 23:09:08+0000 | 1484435348108365
 d43ca2c3-b670-4efc-afd7-b46ada88c3fc |         2017-01-14 23:07:30+0000 | 1484435250481046

如果您希望使用协调器的时间戳,则必须使用 CQL 语句而不是对象映射器:

import uuid
from cassandra.cluster import Cluster

cluster = Cluster()
session = cluster.connect("test")

stmt = session.prepare(
"""
    INSERT INTO test.other_table (id,created_timestamp) VALUES (?,now());
"""
)
session.execute(stmt,[uuid.uuid4()])
于 2017-01-14T18:06:49.517 回答