当我为实体编写accessor时,我通常会添加同一查询的同步和异步版本。例如:
@Accessor
public interface SourceDataAccessor {
@Query("select * from source_data where data_id = ?")
Result<SourceDataCass> get(UUID dataId);
@Query("select * from source_data where data_id = ?")
ListenableFuture<Result<SourceDataCass>> getAsync(UUID dataId);
}
但是当访问者被实例化时,警告会出现在日志中:
12:32:49,793 WARN com.datastax.driver.core.Cluster:2109 - Re-preparing already prepared query select * from source_data where data_id = ?. Please note that preparing the same query more than once is generally an anti-pattern and will likely affect performance. Consider preparing the statement only once.
可能有一种方法可以同时拥有相同查询的同步版本和异步版本,但是没有重新准备吗?
答案 0 :(得分:2)
这是一个有趣的用例。
目前我们不支持它,因此解决方法是仅使用异步方法编写访问者,然后使用getAsync().getUninterruptibly()
作为同步版本(&#39; s&#39&#39 ; s内部完成)。我同意它不是非常用户友好,您可以使用包装类来完成它,但这仍然是一个额外的步骤。
我们可以很容易地做的一件事是在处理方法时缓存预准备语句,因此至少在同一个接口中重复查询时不会准备两次。
如果您有兴趣在驱动程序中看到此信息,请打开JIRA ticket。如果你想自己修复它,你也可以创建一个拉取请求(从快速看,唯一的改变方法是AccessorMapper#prepare)。
答案 1 :(得分:0)
您可以更改访问者以返回Statement
。
@Accessor
public interface SourceDataAccessor {
@Query("select * from source_data where data_id = ?")
Statement get(UUID dataId);
}
然后使用
执行StatementResultSet rs = session.execute(statement);
或
ResultSetFuture rsf = session.executeAsync(statement);
为了将ResultSet映射到您的类,您可以使用Mapper
MappingManager mappingManager = new MappingManager(session);
Mapper mapper = mappingManager.mapper(SourceDataCass.class);
Result<SourceDataClass> sourceDataClass = mapper.map(rs);