我们刚刚发布了Hibernate Search 6.1.0.Final!
Hibernate Search 6.1.0.Final最重要的更改是支持通过outbox-polling
协调策略进行异步、分布式自动索引。
但这并不止于此,还引入了Elasticsearch 7.16兼容性、OpenSearch 1.0/1.2兼容性、搜索DSL改进、条件批量索引等更多功能!
与Hibernate Search 6.0相比的新功能
异步、分布式自动索引
虽然在技术上可以在分布式应用程序中使用Hibernate Search 6.0和Elasticsearch,但它存在一些局限性。
Hibernate Search 6.1的主要目标是通过在应用程序节点之间引入协调来实现异步、分布式自动索引,以消除这些局限性。
Hibernate Search 6.1引入了第一个协调策略:outbox-polling
。此策略在数据库中创建一个出站表,将实体变更事件推送到该表,并依赖于后台处理器来消费这些事件并执行自动索引。
除了消除上述限制之外,这种策略的另一个优点是Hibernate Search将不再在应用线程中触发懒加载或构建文档,这可以提高应用程序的响应速度(提交时要做的工作更少)。
要立即尝试这种策略,只需设置以下属性(您还需要将表添加到数据库模式中)
hibernate.search.coordination.strategy = outbox-polling
有关如何配置协调的更多信息,请参阅文档中的这一部分:这里。
尽管您仍限于单个应用节点,但您将受益于所有其他优点(数据安全、提高应用程序响应速度等)。 |
OpenSearch兼容性
从版本6.1开始,Hibernate Search也兼容OpenSearch,这是Elasticsearch的Apache 2.0许可证分支,并且定期针对1.0和1.2版本进行测试。
要使用Hibernate Search与OpenSearch一起使用,请使用与Elasticsearch相同的Maven工件、配置和API。
使用Elasticsearch和OpenSearch之间的唯一(次要)区别在于是否显式配置Elasticsearch版本:对于OpenSearch,您需要将版本前缀为opensearch:
,例如opensearch:1.0
。
Search DSL改进
- 新的
terms
谓词 -
匹配包含某些术语的文档,可以是任意或全部术语。
特别适用于枚举类型字段。
List<Book> hits = searchSession.search( Book.class ) .where( f -> f.terms().field( "genre" ) .matchingAny( Genre.CRIME_FICTION, Genre.SCIENCE_FICTION ) ) .fetchHits( 20 );
- 新的
regexp
谓词 -
匹配包含与给定正则表达式匹配的单词的文档。
List<Book> hits = searchSession.search( Book.class ) .where( f -> f.regexp().field( "description" ) .matching( "r.*t" ) ) .fetchHits( 20 );
- 新的
id
投影 -
返回匹配实体的标识符。
List<Integer> hits = searchSession.search( Book.class ) .select( f -> f.id( Integer.class ) ) .where( f -> f.matchAll() ) .fetchHits( 20 );
distance
排序的.missing()
行为可配置-
距离排序现在允许指定遇到缺少值的文档时的行为(尽管只有Elasticsearch支持
.missing().first()
/.missing().last()
)。GeoPoint center = GeoPoint.of( 47.506060, 2.473916 ); List<Author> hits = searchSession.search( Author.class ) .where( f -> f.matchAll() ) .sort( f -> f.distance( "placeOfBirth", center ) .missing().first() ) .fetchHits( 20 );
- 相对字段路径
-
Search DSL现在允许创建接受相对字段路径的工厂(
SearchPredicateFactory
等)。如果您将工厂传递给可重用方法,这非常有用。
List<Book> hits = searchSession.search( Book.class ) .where( f -> f.bool() .should( f.nested().objectField( "writers" ) .nest( matchFirstAndLastName( f.withRoot( "writers" ), "bob", "kane" ) ) ) .should( f.nested().objectField( "artists" ) .nest( matchFirstAndLastName( f.withRoot( "artists" ), "bill", "finger" ) ) ) ) .fetchHits( 20 ); private SearchPredicate matchFirstAndLastName(SearchPredicateFactory f, String firstName, String lastName) { return f.bool() .must( f.match().field( "firstName" ) .matching( firstName ) ) .must( f.match().field( "lastName" ) .matching( lastName ) ) .toPredicate(); }
条件性批量索引
Hibernate Search 6.1引入了将批量索引应用于实体子集的能力,基于HQL/JPQL的“where”子句。
SearchSession searchSession = Search.session( entityManager );
MassIndexer massIndexer = searchSession.massIndexer();
massIndexer.type( Book.class ).reindexOnly( "e.publicationYear <= 2100" );
massIndexer.type( Author.class ).reindexOnly( "e.birthDate < :birthDate" )
.param( "birthDate", LocalDate.ofYearDay( 2100, 77 ) );
massIndexer.startAndWait();
命名谓词
Hibernate Search 6.1添加了命名谓词,这是一种将搜索逻辑作为自定义绑定器/桥接器的一部分进行定义的方法。
这在某种程度上是Hibernate Search 5中“全文过滤器”的回归。
自定义ES索引设置
从Hibernate Search 6.1版本开始,您可以提供包含您索引所需设置的JSON文件给Hibernate Search,并且当Hibernate Search创建/更新索引时会自动推送这些设置。
自定义ES索引映射
从Hibernate Search 6.1版本开始,您可以提供包含您索引部分映射需求的JSON文件给Hibernate Search,Hibernate Search会自动将其与生成的映射合并,以便在创建/更新索引时推送至Elasticsearch。
这在设置顶级映射属性时特别有用,例如禁用_source
字段。
访问Lucene的IndexReader
从Hibernate Search 6.1版本开始,当使用Lucene后端时,您可以现在检索一个IndexReader
。
SearchMapping mapping = Search.mapping( entityManagerFactory );
LuceneIndexScope indexScope = mapping
.scope( Book.class ).extension( LuceneExtension.get() );
try ( IndexReader indexReader = indexScope.openIndexReader() ) {
// work with the low-level index reader:
numDocs = indexReader.numDocs();
}
尽管通常不是必需的,但这对于高级的低级别操作可能很有用。
Lucene低级别命中缓存
从版本6.1开始,Hibernate Search允许在Lucene后端配置QueryCache
和QueryCachingPolicy
,为高级Lucene用户提供更多性能优化。
使用分词器/过滤器名称定义Lucene分析器
从Hibernate Search 6.1版本开始,无需引用Lucene类,可以实现一个LuceneAnalysisConfigurer
,通过名称引用分词器和过滤器。
这对于一些模块化环境很有用,在这些环境中,应用程序可能可以访问Hibernate Search类,但不能访问Lucene类。
Jakarta EE
从Hibernate Search 6.1版本开始,除了针对Java EE(JPA、CDI等)的传统工件之外,Hibernate Search现在还提供针对Jakarta EE 9.1(Jakarta Persistence 3、Jakarta CDI 3)的替代、实验性工件。
这些工件具有其artifact ID后缀为"-jakarta",类似于Hibernate ORM的等效工件(您应该一起使用)。
主要工件(例如 |
Hibernate ORM 6
从Hibernate Search 6.1版本开始,除了针对Hibernate ORM 5.x的传统工件之外,Hibernate Search现在还提供针对Hibernate ORM 6和Jakarta EE 9.1(Jakarta Persistence 3、Jakarta CDI 3)的替代、实验性工件。
这些工件具有其artifact ID后缀为"-orm6"。
主要工件(例如 |
Java模块
从版本6.1开始,尽可能的情况下,Hibernate Search现在提供具有完整Java模块定义的多发布JAR文件,该定义包括所有依赖项。
这排除了Lucene后端,因为Lucene 8已拆分包。
其他改进和错误修复
-
HSEARCH-4425:在OutboxPollingOutboxEventAdditionalJaxbMappingProducer中将非空属性标记为非空
-
HSEARCH-4443:出盒轮询实体(代理、出盒事件)中的枚举属性在数据库中有奇怪的类型
-
HSEARCH-4438:为自定义映射/设置文件中的语法错误提供更详细的错误信息
还有更多。要查看自上次发布以来的全部变更列表,请参阅发布说明。
如何获取此版本
所有详细信息都可在hibernate.org的专用页面上找到,并保持最新。