SpringBoot 中已经 通过 spring-boot-starter-data-elasticsearch 集成 ES 相关依赖,只需要通过 API 进行调用即可

1、基础环境

1.1、Maven

pom.xml

  1. <!-- springboot 版本说明 -->
  2. <parent>
  3. <groupId>org.springframework.boot</groupId>
  4. <artifactId>spring-boot-starter-parent</artifactId>
  5. <version>2.6.3</version>
  6. <relativePath/>
  7. </parent>
  8. <!-- 依赖版本说明-->
  9. <properties>
  10. <java.version>1.8</java.version>
  11. <fastJson.version>1.2.79</fastJson.version>
  12. </properties>
  13. <!-- 相关依赖 -->
  14. <dependencies>
  15. <!-- es 相关依赖-->
  16. <dependency>
  17. <groupId>org.springframework.boot</groupId>
  18. <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
  19. </dependency>
  20. <!-- json -->
  21. <dependency>
  22. <groupId>com.alibaba</groupId>
  23. <artifactId>fastjson</artifactId>
  24. <version>${fastJson.version}</version>
  25. </dependency>
  26. <!-- lombok-->
  27. <dependency>
  28. <groupId>org.projectlombok</groupId>
  29. <artifactId>lombok</artifactId>
  30. <optional>true</optional>
  31. </dependency>
  32. <!-- 常规基础依赖-->
  33. <dependency>
  34. <groupId>org.springframework.boot</groupId>
  35. <artifactId>spring-boot-devtools</artifactId>
  36. <optional>true</optional>
  37. </dependency>
  38. <dependency>
  39. <groupId>org.springframework.boot</groupId>
  40. <artifactId>spring-boot-starter-test</artifactId>
  41. </dependency>
  42. </dependencies>

1.2、 config类

需要声明绑定的 es 服务端信息,也可以通过 application.yaml 配置,推荐是试用配配置类的方式,也是官方推荐的方式。
方法一:编写配置类
后续对于 ES 操作的客户端主要用的就是这个配置类声明的 RestHighLevelClient

  1. @Configuration
  2. public class ElasticSearchClientConfig {
  3. /**
  4. * 服务端 ip 端口绑定
  5. *
  6. * @return
  7. */
  8. @Bean
  9. public RestHighLevelClient restHighLevelClient() {
  10. RestHighLevelClient client = new RestHighLevelClient(
  11. RestClient.builder(
  12. // 可以绑定多个地址,多个端口
  13. // new HttpHost("localhost", 9201, "http"),
  14. new HttpHost("localhost", 9200, "http"))
  15. );
  16. return client;
  17. }
  18. }

方法二:编写配置文件

  1. spring:
  2. elasticsearch:
  3. uris:
  4. - 127.0.0.1:9200

2、索引操作

编写测试类 IndicesTest 用于测试索引的基本操作

  1. @SpringBootTest
  2. public class IndicesTest {
  3. @Autowired
  4. private RestHighLevelClient restHighLevelClient;
  5. //索引名
  6. public static String INDICES_01 = "test";
  7. }

2.1、增加 - CreateIndexRequest

  1. @Test
  2. public void createIndices() throws IOException {
  3. //1.声明索引 INDICES_01 即为索引名称
  4. CreateIndexRequest indexRequest = new CreateIndexRequest(INDICES_01);
  5. //2.执行,并获得响应
  6. CreateIndexResponse createIndexResponse = restHighLevelClient.indices().create(indexRequest, RequestOptions.DEFAULT);
  7. System.out.println(createIndexResponse);
  8. }

2.2、删除 - DeleteIndexRequest

  1. //删除
  2. @Test
  3. public void delIndices() throws IOException {
  4. //1.声明索引
  5. DeleteIndexRequest indexRequest = new DeleteIndexRequest(INDICES_01);
  6. //2.执行,并返回响应
  7. AcknowledgedResponse response = restHighLevelClient.indices().delete(indexRequest, RequestOptions.DEFAULT);
  8. //3.打印响应
  9. System.out.println(response);
  10. }

2.3、查询 - GetIndexRequest

  1. //查询
  2. @Test
  3. public void getIndices() throws IOException {
  4. //声明
  5. GetIndexRequest indexRequest = new GetIndexRequest(INDICES_01);
  6. //执行
  7. GetIndexResponse getIndexResponse = restHighLevelClient.indices().get(indexRequest, RequestOptions.DEFAULT);
  8. //打印 test
  9. Arrays.stream(getIndexResponse.getIndices()).forEach(System.out::println);
  10. }

3、文档(数据)操作

此处的文档操作其实和 MySQL 中 对于数据的操作类型,在 Java 中最大的差异就是可以面向对象进行操作。
创建自定义测试实体类 User,后续文档操作其实就是对于 User 对象的操作

  1. @Data
  2. @NoArgsConstructor
  3. @AllArgsConstructor
  4. public class User {
  5. private Long id;
  6. private String name;
  7. private Integer age;
  8. }

3.1、增加 - IndexRequest

  1. @Test
  2. public void addData() throws IOException {
  3. //对象声明,
  4. User user = new User(4l, "zhangsan2", 15);
  5. //数据连接
  6. IndexRequest indexRequest = new IndexRequest(IndicesTest.INDICES_01);
  7. //也可以设置超时时长
  8. //indexRequest.timeout("10s");
  9. indexRequest.id(user.getId().toString());
  10. //设置文档Id ,如果不设置,会随机生成
  11. indexRequest.source(JSON.toJSONString(user), XContentType.JSON);
  12. //执行
  13. IndexResponse response = restHighLevelClient.index(indexRequest, RequestOptions.DEFAULT);
  14. //打印执行状态
  15. System.out.println(response.status());
  16. }

3.2、简单查询 - SearchRequest

此处示例只是简单的 match 查询,具体各种filter,term 等查询可根据上一章调用的 API 进行适当修改即可

  1. @Test
  2. public void searchData() throws IOException {
  3. SearchRequest searchRequest = new SearchRequest(IndicesTest.INDICES_01);
  4. //
  5. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  6. //设置查询条件
  7. // searchSourceBuilder.query(QueryBuilders.matchAllQuery());//不使用字段查询,查询全部
  8. // searchSourceBuilder.query(QueryBuilders.termQuery("name","zhangsan"));//不使用分词器,精确匹配
  9. // searchSourceBuilder.query(QueryBuilders.termQuery("name","张三"));//中文需要额外设置,不然匹配不上
  10. searchSourceBuilder.query(QueryBuilders.matchQuery ("name","name"));//
  11. searchRequest.source(searchSourceBuilder);
  12. //执行
  13. SearchResponse searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
  14. SearchHits hits = searchResponse.getHits();
  15. System.out.println("hits:"+hits.getTotalHits().toString());//hits:4 hits
  16. System.out.println("============================");
  17. Iterator<SearchHit> iterator = hits.iterator();
  18. while (iterator.hasNext()){
  19. SearchHit searchHit = iterator.next();
  20. System.out.println(searchHit.getSourceAsString());
  21. }
  22. }
  23. >>>>
  24. hits:1 hits
  25. ============================
  26. {"name":"This is name","age":30,"desc":"This is desc"}
  27. 1 hits

4、搜索操作 - SearchSourceBuilder

通过 MatchPhraseQueryBuilder 或者 _TermQueryBuilder_ 等查询器Builder 组装要查询的信息

  1. @Test
  2. public void search() throws IOException {
  3. SearchRequest searchRequest = new SearchRequest(IndicesTest.INDICES_01);
  4. SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
  5. // TermQueryBuilder termQueryBuilder = QueryBuilders.termQuery("name", "name");
  6. // searchSourceBuilder.query(termQueryBuilder);
  7. MatchPhraseQueryBuilder matchPhraseQueryBuilder = QueryBuilders.matchPhraseQuery("name", "name");
  8. searchSourceBuilder.query(matchPhraseQueryBuilder);
  9. searchSourceBuilder.timeout(new TimeValue(60, TimeUnit.SECONDS));
  10. searchRequest.source(searchSourceBuilder);
  11. SearchResponse search = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
  12. System.out.println("搜索结果:" + JSON.toJSONString(search.getHits()));
  13. //打印命中文档数据
  14. SearchHits hits = search.getHits();
  15. Arrays.stream(hits.getHits()).forEach(e -> {
  16. System.out.println(e.getSourceAsString());
  17. });
  18. }

执行结果

搜索结果:{“fragment”:true,”hits”:[{“documentFields”:{},”fields”:{},”fragment”:false,”highlightFields”:{},”id”:”zTX6k34BO8Pm06bHMWPC”,”matchedQueries”:[],”metadataFields”:{},”primaryTerm”:0,”rawSortValues”:[],”score”:1.1129161,”seqNo”:-2,”sortValues”:[],”sourceAsMap”:{“name”:”This is name”,”age”:30,”desc”:”This is desc”},”sourceAsString”:”{\”name\”:\”This is name\”,\”age\”:30,\”desc\”:\”This is desc\”}”,”sourceRef”:{“fragment”:true},”type”:”_doc”,”version”:-1}],”maxScore”:1.1129161,”totalHits”:{“relation”:”EQUAL_TO”,”value”:1}} {“name”:”This is name”,”age”:30,”desc”:”This is desc”}