持续创作,加速成长!这是我参与「掘金日新计划 · 6 月更文挑战」的第19天,点击查看活动详情
前言
上一章讲解了Spring Boot集成Elasticsearch的EsProductRepository实现查询,官方建议使RestHighLevelClient实现相关查询,本文将讲解Spring Boot 采用RestHighLevelClient实现查询
前期准备
Spring Boot集成Elasticsearch经常会遇到版本问题,下面我列举下Spring Boot与ES对应的版本列表,这样大家在也不会担心版本问题了。
通过这个图我们可以得知,Spring Boot2.3+版本以后,会自动引用elasticsearch-rest-high-level-client7.0+以上的的版本,所以ES客户端也需要安装7.0+以上的版本。
pom.xml引入相关jar包
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.3.3.RELEASE</version>
</parent>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
</dependency>
说明:网上很多人还都在使用的是elasticsearch-rest-high-level-client6.0+的版本,而引入Spring2.3.3版本会自动引入elasticsearch-rest-high-level-client7.0+的版本,其依赖关系如下:
基本使用
创建索引
请求示例
http://localhost:9090/hight/addProduct
{
"id":"9",
"skuNo":"sku0009",
"title":"小桥流水人家",
"price":"10.00",
"createDate":"1655132070891"
}
Controller实现如下
@Autowired
private RestHighLevelClient client;
@PostMapping("/addProduct")
public Result addProduct(@RequestBody Product product) throws IOException
{
IndexRequest indexRequest =new IndexRequest("product");
indexRequest.id(product.getId());
String jsonString=JSON.toJSONString(product);
indexRequest.source(jsonString,XContentType.JSON);
IndexResponse response = client.index(indexRequest,RequestOptions.DEFAULT);
return Result.success(response);
}
说明:XContentType可以支持多种数据格式,
- JSON:JSON数据格式
- Simple:简单对象
- YAML: YAML数据格式
- CBOR:简明二进制对象展现
词条匹配
请求示例
http://localhost:9090/hight/search?indexName=product&key=title&value=水
Conroller实现
@GetMapping("/search")
public Result search(String indexName,String key,String value) throws IOException
{
//设置多个文档
SearchRequest request =new SearchRequest(indexName);
SearchSourceBuilder sourceBuilder =new SearchSourceBuilder();
sourceBuilder.query(QueryBuilders.termQuery(key,value));
request.source(sourceBuilder);
SearchResponse response =client.search(request, RequestOptions.DEFAULT);
return Result.success(response);
}
查询结果
{
"data": [
{
"score": 1.4831866,
"id": "8",
"type": "_doc",
"nestedIdentity": null,
"version": -1,
"seqNo": -2,
"primaryTerm": 0,
"fields": {},
"highlightFields": {},
"sortValues": [],
"matchedQueries": [],
"explanation": null,
"shard": null,
"index": "product",
"clusterAlias": null,
"sourceAsMap": {
"price": 109.0,
"skuNo": "sku0008",
"id": "8",
"title": "水浒传",
"createDate": 1655132070891
},
"innerHits": null,
"rawSortValues": [],
"sourceRef": {
"fragment": true
},
"sourceAsString": "{\"createDate\":1655132070891,\"id\":\"8\",\"price\":109.0,\"skuNo\":\"sku0008\",\"title\":\"水浒传\"}",
"fragment": false
},
{
"score": 1.1272218,
"id": "9",
"type": "_doc",
"nestedIdentity": null,
"version": -1,
"seqNo": -2,
"primaryTerm": 0,
"fields": {},
"highlightFields": {},
"sortValues": [],
"matchedQueries": [],
"explanation": null,
"shard": null,
"index": "product",
"clusterAlias": null,
"sourceAsMap": {
"price": 10.0,
"skuNo": "sku0009",
"id": "9",
"title": "小桥流水人家",
"createDate": 1655132070891
},
"innerHits": null,
"rawSortValues": [],
"sourceRef": {
"fragment": true
},
"sourceAsString": "{\"createDate\":1655132070891,\"id\":\"9\",\"price\":10.0,\"skuNo\":\"sku0009\",\"title\":\"小桥流水人家\"}",
"fragment": false
}
],
"code": 200,
"msg": "操作成功"
}
说明:查询包含水字的词条的所有数据。
模糊查询
http://localhost:9090/hight/wildSearch?indexName=product&key=title&value=水
Conroller实现
@GetMapping("/wildSearch")
public Result wildSearch(String indexName,String key,String value) throws IOException
{
//设置多个文档
SearchRequest request =new SearchRequest(indexName);
SearchSourceBuilder sourceBuilder =new SearchSourceBuilder();
//设置模糊查询的条件
WildcardQueryBuilder matchQueryBuilder =new WildcardQueryBuilder(key,"*"+value+"*");
sourceBuilder.query(matchQueryBuilder);
request.source(sourceBuilder);
SearchResponse response =client.search(request, RequestOptions.DEFAULT);
return Result.success(response);
}
查询结果
{
"data": [
{
"score": 1.0,
"id": "2",
"type": "_doc",
"nestedIdentity": null,
"version": -1,
"seqNo": -2,
"primaryTerm": 0,
"fields": {},
"highlightFields": {},
"sortValues": [],
"matchedQueries": [],
"explanation": null,
"shard": null,
"index": "product",
"clusterAlias": null,
"sourceAsMap": {
"price": 99.0,
"skuNo": "sku0002",
"id": "2",
"title": "java从入门到精通",
"createDate": 1655132070891
},
"innerHits": null,
"rawSortValues": [],
"sourceRef": {
"fragment": true
},
"sourceAsString": "{\"createDate\":1655132070891,\"id\":\"2\",\"price\":99.0,\"skuNo\":\"sku0002\",\"title\":\"java从入门到精通\"}",
"fragment": false
},
{
"score": 1.0,
"id": "3",
"type": "_doc",
"nestedIdentity": null,
"version": -1,
"seqNo": -2,
"primaryTerm": 0,
"fields": {},
"highlightFields": {},
"sortValues": [],
"matchedQueries": [],
"explanation": null,
"shard": null,
"index": "product",
"clusterAlias": null,
"sourceAsMap": {
"price": 89.0,
"skuNo": "sku0003",
"id": "3",
"title": "java编程思想",
"createDate": 1655132070891
},
"innerHits": null,
"rawSortValues": [],
"sourceRef": {
"fragment": true
},
"sourceAsString": "{\"createDate\":1655132070891,\"id\":\"3\",\"price\":89.0,\"skuNo\":\"sku0003\",\"title\":\"java编程思想\"}",
"fragment": false
},
{
"score": 1.0,
"id": "4",
"type": "_doc",
"nestedIdentity": null,
"version": -1,
"seqNo": -2,
"primaryTerm": 0,
"fields": {},
"highlightFields": {},
"sortValues": [],
"matchedQueries": [],
"explanation": null,
"shard": null,
"index": "product",
"clusterAlias": null,
"sourceAsMap": {
"price": 89.0,
"skuNo": "sku0004",
"id": "4",
"title": "java设计模式",
"createDate": 1655132070891
},
"innerHits": null,
"rawSortValues": [],
"sourceRef": {
"fragment": true
},
"sourceAsString": "{\"createDate\":1655132070891,\"id\":\"4\",\"price\":89.0,\"skuNo\":\"sku0004\",\"title\":\"java设计模式\"}",
"fragment": false
}
],
"code": 200,
"msg": "操作成功"
}
从查询的结果来看,包含java分词的都模糊查询出来了。
范围查询
http://localhost:9090/hight/rangeSearch?indexName=product&beginTime=2022-06-01&endTime=2022-06-30
Conroller实现
@GetMapping("/rangeSearch")
public Result rangeSearch(String indexName,String beginTime,String endTime) throws IOException
{
//设置多个文档
SearchRequest request =new SearchRequest(indexName);
SearchSourceBuilder sourceBuilder =new SearchSourceBuilder();
//设置多个文档类型
BoolQueryBuilder boolQueryBuilder = QueryBuilders.boolQuery();
boolQueryBuilder.must(QueryBuilders.rangeQuery("createDate")
.gte(beginTime)
.lte(endTime)
.format("yyyy-MM-dd")
.timeZone("+08:00"));
sourceBuilder.query(boolQueryBuilder);
request.source(sourceBuilder);
SearchResponse response =client.search(request, RequestOptions.DEFAULT);
SearchHits hits = response.getHits();
SearchHit[] searchHits = hits.getHits();
return Result.success(searchHits);
}
查询结果
{
"data": {
"content": [
{
"id": "2",
"skuNo": "sku0002",
"title": "java从入门到精通",
"price": 99.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "3",
"skuNo": "sku0003",
"title": "java编程思想",
"price": 89.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "4",
"skuNo": "sku0004",
"title": "java设计模式",
"price": 89.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "5",
"skuNo": "sku0005",
"title": "Spring编程",
"price": 89.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "6",
"skuNo": "sku0006",
"title": "Spring Boot编程",
"price": 89.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "8",
"skuNo": "sku0008",
"title": "水浒传",
"price": 109.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
},
{
"id": "9",
"skuNo": "sku0009",
"title": "小桥流水人家",
"price": 10.0,
"createDate": "2022-06-13T14:54:30.891+00:00"
}
],
"pageable": {
"sort": {
"sorted": false,
"unsorted": true,
"empty": true
},
"offset": 0,
"pageNumber": 0,
"pageSize": 7,
"paged": true,
"unpaged": false
},
"aggregations": null,
"scrollId": null,
"maxScore": 1.0,
"totalElements": 7,
"totalPages": 1,
"number": 0,
"size": 7,
"sort": {
"sorted": false,
"unsorted": true,
"empty": true
},
"numberOfElements": 7,
"first": true,
"last": true,
"empty": false
},
"code": 200,
"msg": "操作成功"
}
总结
本文讲解了Spring Boot集成RestHighLevelClient实现基础查询,如有疑问请随时提问。