我正在为一个项目使用 spring-data-elasticsearch 来为其提供全文搜索功能。我们将真实数据保存在关系数据库中,并将相关元数据与相应的 id 一起保存在 elasticsearch 中。因此对于搜索结果,只有 id 字段是必需的,因为实际数据将从关系数据库中检索。
我正在根据搜索条件构建搜索查询,然后执行 queryForIds():
SearchQuery searchQuery = new NativeSearchQueryBuilder()
.withIndices(indexName)
.withTypes(typeName)
.withQuery(getQueryBuilder(searchParams))
.withPageable(pageable)
.build();
return elasticsearchTemplate.queryForIds(searchQuery);
如果我还需要那个特定搜索查询的总数,我可以再做一个 elasticsearchTemplate.count(searchQuery)
打电话,但据我所知,这将是多余的。我认为有一种方法可以通过使用 elasticsearchTemplate.queryForPage()
之类的东西来获取 id 列表和总计数。在一次通话中。
此外,我可以在 queryForPage(SearchQuery query, Class<T> clazz, SearchResultMapper mapper)
中使用自定义类吗?没有用 @Document
注释?实际的文档类真的很大,如果我不确定传递大类是否会给引擎带来任何额外负载,因为有超过 100 个字段需要 json 映射,但我只需要 id 字段。我会有一个.withFields("id")
无论如何在查询构建器中。
最佳答案
如果你想阻止对 elasticsearch 的两次调用,我建议编写一个自定义的 ResultsExtractor:
SearchQuery searchQuery = new NativeSearchQueryBuilder().withIndices(indexName)
.withTypes(typeName)
.withQuery(queryBuilder)
.withPageable(pageable)
.build();
SearchResult result = template.query(searchQuery, new ResultsExtractor<SearchResult>() {
@Override
public SearchResult extract(SearchResponse response) {
long totalHits = response.getHits()
.totalHits();
List<String> ids = new ArrayList<String>();
for (SearchHit hit : response.getHits()) {
if (hit != null) {
ids.add(hit.getId());
}
}
return new SearchResult(ids, totalHits);
}
});
System.out.println(result.getIds());
System.out.println(result.getCount());
其中 SearchResult 是自定义类:
public class SearchResult {
List<String> ids;
long count;
//getter and setter
}
这样就可以从elasticsearch中得到你需要的信息了SearchResponse
.
关于您的第二个问题:据我所知,在调用 queryForPage(SearchQuery query, Class<T> clazz, SearchResultMapper mapper)
时
未针对 @Document
检查通过的类注解。试试吧!
关于java - 在 spring-data-elasticsearch 中使用 ElasticsearchTemplate 获取 id 的计数和列表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35252156/