😎 知识点概览
为了方便后续回顾该项目时能够清晰的知道本章节讲了哪些内容,并且能够从该章节的笔记中得到一些帮助,所以在完成本章节的学习后在此对本章节所涉及到的知识点进行总结概述。
本章节为【学成在线】项目的 day11
的内容
- 基于
Java
客户端实现 DSL 搜索 - 搭建
ElasticSearch
集群环境 - 使用
Logstash
自动创建ElasticSearch
的索引、数据文档 - 基于
ElasticSearch
开发搜索服务接口
目录
内容会比较多,小伙伴们可以根据目录进行按需查阅。
一、搜索管理
0x01 准备环境
1、创建映射
创建 xc_course
索引库,方式如下
post:http://localhost:9200/xc_course/doc/_mapping
{
"properties": {
"description": {
"type": "text",
"analyzer": "ik_max_word",
"search_analyzer": "ik_smart"
},
"name": {
"type": "text",
"analyzer": "ik_max_word",
"search_analyzer": "ik_smart"
},
"pic": {
"type": "text",
"index": false
},
"price": {
"type": "float"
},
"studymodel": {
"type": "keyword"
},
"timestamp": {
"type": "date",
"format": "yyyy-MM-dd HH:mm:ss||yyyy-MM-dd||epoch_millis"
}
}
}
2、插入原始数据
向 xc_course/doc
中插入以下三个文档数据:
PUT:http://localhost:9200/xc_course/doc/1
{
"name": "Bootstrap开发",
"description": "Bootstrap是由Twitter推出的一个前台页面开发框架,是一个非常流行的开发框架,此框架集成了多种页面效果。此开发框架包含了大量的CSS、JS程序代码,可以帮助开发者(尤其是不擅长页面开发的程序人员)轻松的实现一个不受浏览器限制的精美界面效果。",
"studymodel": "201002",
"price":38.6,
"timestamp":"2018-04-25 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}
PUT:http://localhost:9200/xc_course/doc/2
{
"name": "java编程基础",
"description": "java语言是世界第一编程语言,在软件开发领域使用人数最多。",
"studymodel": "201001",
"price":68.6,
"timestamp":"2018-03-25 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}
PUT:http://localhost:9200/xc_course/doc/3
{
"name": "spring开发基础",
"description": "spring 在java领域非常流行,java程序员都在用。",
"studymodel": "201001",
"price":88.6,
"timestamp":"2018-02-24 19:11:35",
"pic":"group1/M00/00/00/wKhlQFs6RCeAY0pHAAJx5ZjNDEM428.jpg"
}
3、简单的搜索一下
简单搜索就是通过 url
进行查询,以 get
方式请求 ES
。
格式:GET …/_search?q=…
q:搜索字符串。
例子:?q=name:spring
搜索name中包括spring的文档。
0x02 DSL 搜索
DSL(Domain Specific Language) 是 ES
提出的基于 json
的搜索方式,在搜索时传入特定的 json
格式的数据来完成不同的搜索需求。
DSL
比 URI
(在url传递搜索参数) 搜索方式功能强大,在项目中建议使用 DSL
方式来完成搜索。
1、查询所有文档
查询所有索引库的文档。
发送:post http://localhost:9200/_search
查询指定索引库 指定类型 下的文档。(通过使用此方法)
发送:post http://localhost:9200/xc_course/doc/_search
{
"query": {
"match_all": {
}
},
"_source" : ["name","studymodel"]
}
_source:
source
源过虑设置,指定结果中所包括的字段有哪些。
搜索结果:
{
"took": 9,
"timed_out": false,
"_shards": {
"total": 1,
"successful": 1,
"skipped": 0,
"failed": 0
},
"hits": {
"total": 3,
"max_score": 1.0,
"hits": [
{
"_index": "xc_course",
"_type": "doc",
"_id": "1",
"_score": 1.0,
"_source": {
"studymodel": "201002",
"name": "Bootstrap开发"
}
},
{
"_index": "xc_course",
"_type": "doc",
"_id": "2",
"_score": 1.0,
"_source": {
"studymodel": "201001",
"name": "java编程基础"
}
},
{
"_index": "xc_course",
"_type": "doc",
"_id": "3",
"_score": 1.0,
"_source": {
"studymodel": "201001",
"name": "spring开发基础"
}
}
]
}
}
结果说明:
字段名称 | 描述 |
---|---|
took | 本次操作花费的时间,单位为毫秒。 |
timed_out | 请求是否超时 |
_shards | 说明本次操作共搜索了哪些分片 |
hits | 搜索命中的记录 |
hits.total | 符合条件的文档总数 hits.hits :匹配度较高的前N个文档 |
hits.max_score | 文档匹配得分,这里为最高分 |
_score | 每个文档都有一个匹配度得分,按照降序排列。 |
_source | 显示了文档的原始内容。 |
使用JAVA 客户端实现:
-
创建搜索请求对象
-
指定类型(部分版本不需要指定类型,这里以
6.2.1
为例) -
构建搜索源对象
-
配置搜索方式,设置需要过滤字段
-
向搜索请求中设置搜索源
-
执行搜索,向ES发起
http
请求 -
搜索结果
asd as
-
匹配到的总记录数
-
得到匹配度高的文档
-
遍历结果,获取
SearchHit
对象中的属性,输出或者存档。
具体代码如下:
@SpringBootTest
@RunWith(SpringRunner.class)
public class TestSearch {
@Autowired
RestHighLevelClient client;
//搜索type下的全部记录
@Test
public void testSearchAll() throws IOException {
//获取搜索请求对象,并且设置类型
SearchRequest searchRequest = new SearchRequest("xc_course");
searchRequest.types("doc");
SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
//设置搜索方式
searchSourceBuilder.query(QueryBuilders.matchAllQuery());
//配置source源字段过虑,1显示的,2排除的
searchSourceBuilder.fetchSource(new String[]{
"name","studymodel"}, new String[]{
});
//将搜索源配置到搜索请求中,执行搜索,获取搜索响应结果
searchRequest.source(searchSourceBuilder);
SearchResponse searchResponse = client.search(searchRequest);
//获取所有搜索结果、总匹配数量
SearchHits hits = searchResponse.getHits();
long totalHits = hits.getTotalHits();
//筛选出匹配度高的文档记录
SearchHit[] searchHits = hits.getHits();
//遍历结果
for (SearchHit hit : searchHits) {
String index = hit.getIndex();
String type = hit.getType();
String id = hit.getId();
float score = hit.getScore();
String sourceAsString = hit.getSourceAsString();
Map<String, Object> sourceAsMap = hit.getSourceAsMap();
String name = (String) sourceAsMap.get("name");
String studymodel = (String) sourceAsMap.get("studymodel");
String description = (String) sourceAsMap.get("description");
System.out.println(name);
System.out.println(studymodel);
System.out.println(description);
}
}
}
2、分页查询
ES
支持分页查询,传入两个参数:from
和 size
。
-
form:表示起始文档的下标,从0开始。
-
size:查询的文档数量。
发送:post http://localhost:9200/xc_course/doc/_search
{
"from" : 0,
"size" : 1,
"query": {
"match_all": {
}
},
"_source" : ["name","studymodel"]
}
使用JAVA 客户端实现:
//分页查询
@Test
public void testSearchPage() throws IOException {
//获取搜索请求对象,并且设置类型
SearchRequest searchRequest = new SearchRequest("xc_course");
searchRequest.types("doc");
SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
//设置搜索方式
searchSourceBuilder.query(QueryBuilders.matchAllQuery());
//ES这里是按起始坐标来实现分页查询,所以我们要指定一个页码
int pageNum = 1;
int size = 2;
//通过页码和查询数量得出起始位置
int fromNum = (pageNum - 1) * size;
//分页查询,设置起始下标,从0开始
searchSourceBuilder.from(0);
//每页显示个数
searchSourceBuilder.size(size);
//配置source源字段过虑,1显示的,2排除的
searchSourceBuilder.fetchSource(new String[]{
"name","studymodel"}, new String[]{
});
//将搜索源配置到搜索请求中,执行搜索,获取搜索响应结果
searchRequest.source(searchSourceBuilder);
SearchResponse searchResponse = restHighLevelClient.search(searchRequest);
//获取所有搜索结果、总匹配数量
SearchHits hits = searchResponse.getHits();
long totalHits = hits.getTotalHits();
//筛选出匹配度高的文档记录
SearchHit[] searchHits = hits.getHits();
//遍历结果
for(SearchHit hit : searchHits){
System.out.println(hit.toString());
}
}
3、Term Query
Term Query
为精确查询,在搜索时会整体匹配关键字,不再将关键字分词。
发送:post http://localhost:9200/xc_course/doc/_search
{
"query": {
"term" : {
"name": "spring"
}
},
"_source" : ["name","studymodel"]
}
上边的搜索会查询 name
包括 spring
这个词的文档。
JAVA客户端实现:
/**
* Term Query 精确查询
*/
@Test
public void TestSearchTermQuery() throws IOException {
SearchRequest searchRequest = new SearchRequest("xc_course");
searchRequest.types("doc");
SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
//设置查询类型为termQuery,精确匹配name中包含spring的文档
searchSourceBuilder.query(QueryBuilders.termQuery("name","spring"));//source源字段过虑
//不指定过滤条件则默认显示查询到的文档的所有字段
searchSourceBuilder.fetchSource(new String[]{
}, new String[]{
});
//设置搜索源并获取搜索结果
searchRequest.source(searchSourceBuilder);
SearchResponse searchResponse = restHighLevelClient.search(searchRequest);
//获取搜索结果
// .getHits() 取本次所有匹配结果
// .getHits().getHits() 筛选出匹配度高的文档记录
SearchHits hits = searchResponse.getHits();
long tot