领先一步
VMware 提供培训和认证,以加速您的进步。
了解更多这是来自Couchbase的Simon BASLÉ的交叉发布博客。您可以在Twitter上找到他(
@simonbasle
)或github。在开发者门户上了解有关Couchbase和Couchbase Java SDK的更多信息。再次感谢Simon,并祝你和你的团队工作顺利!-Josh
Spring Data Couchbase 2.0是对原始Spring Data Couchbase 1.4.x连接器的重写。它基于Couchbase Java 2.2 SDK,并大量使用新的查询语言N1QL(在Couchbase Server 4.0中引入)为Spring Data用户提供更多功能。
第一个里程碑于去年8月发布,然后是候选版本,从那时起,实现了其他功能(和错误修复),现在可以向公众发布GA版本。
让我们快速浏览一下发生了哪些变化(使用⭐到⭐⭐⭐的符号表示我们认为每个功能有多棒和重要?)。
Spring Data Couchbase的1.x版本和2.x版本之间的主要区别在于
CouchbaseTemplate
!)当然,您仍然可以通过使用CouchbaseTemplate
而不是CouchbaseRepository
接口来访问更低级别的API,并且您甚至可以从SDK访问底层的Bucket
。
⭐⭐⭐
Couchbase 4.0中的主要新功能是N1QL,这是一种适用于JSON文档的SQL扩展(因此它向SQL添加了JSON相关的特性)。
这对Repository
模式和Spring Data中的查询推导尤其有用,因为绝大多数查询推导关键字都可以轻松转换为N1QL。
N1QL现在是存储库方法的默认支持Couchbase功能。如果要明确执行的查询,也可以选择使用@Query接口。
public interface UserRepository extends Repository<User, String> {
User findByUsernameEquals(String username);
List<User> findByUsernameContains(String contains);
@Query //optional for N1QL query derivation but more explicit
List<User> findByAgeBetween(int minAge, int maxAge);
}
⭐⭐
此版本中的一项重大更改是,现在,基于视图的存储库查询(即自定义存储库方法)更符合Spring Data的理念。它们还必须使用@View(viewName="something")
显式注释。
这意味着没有Couchbase特定的内容应该泄漏到您的存储库接口中。相反,您可以做的是对大多数查询使用查询推导机制。
查询推导在一定程度上也是可能的,在视图支持的方法中接受了一些关键字。
public interface UserRepository extends Repository<User, String> {
@Override
@View(designDocument = "user", viewName = "customFindAllView")
Iterable<User> findAll();
@View(viewName = "customFindByNameView")
User findByUsernameIs(String lowKey);
@View(viewName = "customFindByNameView")
List<User> findByUsernameBetween(String lowKey, String highKey);
}
⭐
另一项以前不支持的新功能是,如果您有一个reduce函数,则执行该函数。现在,为了执行它,您只需在@View
注释中将reduce
标志设置为true。
如果对您有意义(即您实际上使用了“count”reduce函数),您也可以在方法名前缀“count”而不是“find”。
请注意,Couchbase中的reduce函数可以是除预先存在的_count之外的其他内容,甚至可以返回除long之外的其他内容,例如JsonObject
,例如内置的_stats
。
类似地,在方法名称中添加变体“topX”或“firstX”将导致在请求上设置附加限制(例如,findFirst5ByLastName
将列表限制为5个结果)。
⭐⭐⭐
在使用异步填充的辅助索引(如视图和GSI(支持N1QL的新辅助索引引擎))时,经常会出现需要立即读取先前写入操作的修改。
这意味着只要数据仍在索引过程中,视图/N1QL就不应该给出答案,因此这牺牲了一些性能以换取一致性。
相反(并且是Spring Data Couchbase的当前默认设置)是通过接受返回陈旧数据来优先考虑性能。
我们添加了用于配置框架通过查询推导构建的所有查询(基于视图或基于N1QL)的全局语义,方法是在一致性概念周围提供一个小的抽象。
这是通过覆盖AbstractCouchbaseConfiguration
的getDefaultConsistency()
方法来完成的。Consistency
是一个枚举,允许您在READ_YOUR_OWN_WRITES
、STRONGLY_CONSISTENT
、UPDATE_AFTER
和EVENTUALLY_CONSISTENT
之间进行选择。请参阅官方文档,以获取有关它们的工作原理以及它们在查询时产生的影响的更多信息。
您也可以在XML中通过在<couchbase:template>
标签上使用一致性属性来实现。
自GA以来,存储库中的CRUD方法现在也考虑了默认配置的一致性。
⭐
一些用户报告了Spring Data和Couchbase Mobile方面的问题,Sync Gateway拒绝包含以下划线为前缀的字段的文档。
这对Spring Data来说是个问题,因为它默认情况下将类型信息存储在_class
字段中:()
解决方案是允许通过配置修改该类型信息字段的名称。您可以通过覆盖AbstractCouchbaseConfiguration
中的typeKey()
方法来做到这一点。例如,您可以使用常量MappingCouchbaseConverter.TYPEKEY_SYNCGATEWAY_COMPATIBLE
(即“javaClass
”)。
此字段是生成的N1QL查询用于过滤仅与存储库实体对应的文档的字段。
Pageable
/PageRequest
⭐⭐
使用 N1QL,对于通过查询派生生成的查询,现在支持Pageable
和Sort
参数。
PagingAndSortingRepository
支持。findAll
方法。使用默认配置的一致性。⭐⭐⭐
使用坐标查询 Couchbase!如果您的实体具有Point
(或x
和y
)位置,则可以使用以下方式查找它:
findByLocationWithin(Box area)
findByLocationWithin(Circle area)
,findByLocationWithin(Point center, Distance radius)
。findByLocationWithin(Polygon area)
,findByLocationWithin(Point[] polygon)
。findByLocationNear(Point near, Distance maxDistance)
。圆形和多边形类查询在服务器上以边界框近似值的形式快速执行,然后框架在呈现结果之前消除误报。
您可以利用 Couchbase 空间视图的多维特性,为您的查询添加额外的维度(例如,在城市范围内深夜营业的商店……)。
public interface DimensionalPartyRepository extends CrudRepository<Party, String> {
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocation")
List<Party> findByLocationNear(Point p, Distance d);
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocation")
List<Party> findByLocationWithin(Box boundingBox);
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocation")
List<Party> findByLocationWithin(Polygon zone);
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocationAndAttendees", dimensions = 3)
List<Party> findByLocationWithinAndAttendeesGreaterThan(Polygon zone, double minAttendees);
}
注意:如果您想重用注解,也可以这样做(对@View
和@Query
也适用)
public interface DimensionalPartyRepository extends CrudRepository<Party, String> {
//define your own meta-annotation
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocation", dimensions = 2)
@Retention(RetentionPolicy.RUNTIME)
@interface IndexedByLocation { }
//use it :)
@IndexedByLocation
List<Party> findByLocationNear(Point p, Distance d);
@IndexedByLocation
List<Party> findByLocationWithin(Box boundingBox);
@IndexedByLocation
List<Party> findByLocationWithin(Polygon zone);
//here we use a variation with 3 dimensions, so we need to revert to @Dimensional
@Dimensional(designDocument = "partyGeo", spatialViewName = "byLocationAndAttendees", dimensions = 3)
List<Party> findByLocationWithinAndAttendeesGreaterThan(Polygon zone, double minAttendees);
}
N1QL
@Query
现在支持 SpEL⭐⭐⭐
内联查询可以使用 SpEL 表示法来
#{#n1ql.selectEntity}
生成SELECT ... FROM ...
子句,并在WHERE
子句中使用#{#n1ql.filter}
将查询限制到正确的实体。⭐⭐
⚠️ 重要:这被认为是开发/测试期间的辅助手段,不建议在生产环境中使用
为了确保给定存储库中实体的 N1QL 索引在开发或预生产环境中被激活,可以使用@N1qlPrimaryIndexed
(启用桶范围的自由格式查询)和@N1qlSecondaryIndexed
(仅索引与实体类型对应的文档,类似于 SpEL #{#n1ql.filter}
生成的 WHERE 子句)对其进行注解。
此外,CRUD 操作的备份视图可以通过使用@ViewIndexed
注解存储库来自动创建(您需要提供设计文档名称,该名称应对应于实体的简单类名,首字母小写)。
此功能还必须通过在AbstractCouchbaseConfiguration
中重新定义indexManager
bean 来选择加入。
String
)⭐⭐
这尤其针对具有聚合函数(如COUNT(*)
、AVG(field)
等)的内联 N1QL 查询。查询必须返回具有单个投影的单行。
⭐⭐
使用命名参数或位置参数,但不能同时使用两者。命名参数的语法为$paramName
,要求每个方法参数都使用@Param("paramName")
进行注解。
⭐
其他功能包括
couchbase
”为前缀,以避免与其他存储发生冲突。CouchbaseTemplate
中的查找方法会消除已删除的文档。@Document
上设置过期时间,作为long
+ timeUnit
。还实现了一些错误修复和相较于 RC1 的改进。
⭐⭐⭐
文档 也得到了改进,增加了面向 Couchbase 的示例,说明如何向存储库添加自定义方法的实现、如何更改所有存储库的基类、如何在内联查询中处理 SpEL 等。
Spring Cache 支持已从 Spring Data 存储库中移除。它仍然存在,我们计划对其进行改进。目前,您可以在 GitHub 上的 Couchbase 存储库 中找到它,但它很快就会重新集成到 Spring 项目的官方系列中。
您可以将以下内容添加到项目的pom.xml
中以获取此 GA 版本(在dependencies
部分)
<!--<dependencies>-->
<dependency>
<groupId>org.springframework.data</groupId>
<artifactId>spring-data-couchbase</artifactId>
<version>2.0.0.RELEASE</version>
</dependency>
<!--</dependencies>-->
我们希望您喜欢此版本及其带来的所有新功能。下一步将是重新连接到Hopper
发布列车,预计在夏季之前发布版本2.1
。