Astyanax通过其AnnotatedCompositeSerializer
支持Cassandra中的复合列。我有一个具有3字段复合列名称的列族,类似于此示例,改编自Astyanax's documentation(列实际上不是sessionId
和token
,假装它们是出于参数的缘故):
// Annotated composite class
public class SessionEvent {
@Component(ordinal=0) UUID sessionId;
@Component(ordinal=1) UUID token;
@Component(ordinal=2) UUID timestamp;
public SessionEvent() { }
}
static AnnotatedCompositeSerializer<SessionEvent> eventSerializer
= new AnnotatedCompositeSerializer<>(SessionEvent.class);
static ColumnFamily<String, SessionEvent> CF_SESSION_EVENTS
= new ColumnFamily<>("SessionEvents",
StringSerializer.get(), eventSerializer);
// Querying cassandra for a column slice on one prefix, but we want two!
OperationResult<ColumnList<SessionEvent>> result = keyspace.prepareQuery(CF_SESSION_EVENTS)
.getKey("UserId1")
.withColumnRange(eventSerializer.buildRange()
.withPrefix("SessionId1")
.build())
.execute();
问题是:我想在前缀中查询包含两个复合列(在本例中为sessionId
和token
)的所有列,而不仅仅是一个,并且对于所有时间戳,不是只是在一个范围内。使用CQL3显然可以轻松实现这一点,但是我坚持使用Cassandra 1.0.x并且无法找到Astyanax接受的方式(通过调用withPrefix(UUID)
两次或传递复合数据结构)
Astyanax有没有办法做到这一点?我可以以某种方式使用基本RangeBuilder
并手动序列化开始和结束吗?
答案 0 :(得分:1)
Cassandra中的列按顺序存储。在您的示例中,sessionId是最重要的,后跟令牌,timestamp是最不重要的。换句话说,列按sessionId排序,然后是令牌,然后是时间戳。
如果我理解正确,您正在尝试使用指定的sessionId以及令牌和任何时间查询列。由于上述原因,具有匹配的sessionId和令牌的列将连续存储。您可以通过以下方式使用最小/最大日期来查询任何日期:
startTime = new Date(0);
endTime = new Date(Long.MAX_VALUE);
SessionEvent from = new SessionEvent(sessionId, token, startTime);
SessionEvent to = new SessionEvent(sessionId, token, endTime);
RangeBuilder rb = new RangeBuilder().setStart(from).setEnd(to);
OperationResult<ColumnList<SessionEvent>> result = keyspace
.prepareQuery(CF_SESSION_EVENTS)
.getKey("UserId1")
.withColumnRange(rb.build())
.execute();