• ElasticsearchRestTemplate 和ElasticsearchRepository 的使用


    目录

    一、使用ElasticsearchRestTemplate类

     1.引用Maven类库

    2. 配置文件application.yml

    3.创建实体类(用于JSON文档对象的转换)

    二、使用ElasticsearchRepository 类

    1.引用Maven类库

    2. 配置文件application.yml

    3. ElasticsearchRepository接口的源码 

    4.CrudRepository  源码

    5. 查询查找策略

    5.1存储库方法可以定义为具有以下返回类型,用于返回多个元素:

    5.2 使用@Query注解

    6.开发实例:


    操作ElasticSearch的数据,有两种方式一种是 ElasticsearchRepository 接口,另一种是ElasticsearchTemplate接口。SpringData对ES的封装ElasticsearchRestTemplate类,可直接使用,此类在ElasticsearchRestTemplate基础上进行性一定程度的封装,使用起来更方便灵活,拓展性更强。ElasticsearchRepository可以被继承操作ES,是SpringBoot对ES的高度封装,操作最为方便,但牺牲了灵活性。

      Spring boot 和Elasticsearch版本关系:

    一、使用ElasticsearchRestTemplate类

        1.引用Maven类库

    1. <dependency>
    2. <groupId>org.springframework.boot</groupId>
    3. <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
    4. </dependency>

         2. 配置文件application.yml

    1. spring:
    2. elasticsearch:
    3. rest:
    4. uris: http://192.168.10.202:9200
    5. connection-timeout: 1s
    6. read-timeout: 1m
    7. username: elastic
    8. password: elastic

    注意,如果es资源没有开启x-pack安全插件的话,可以不加username和password(因为默认是没有的)。

    3.创建实体类(用于JSON文档对象的转换)

    1. import com.fasterxml.jackson.annotation.JsonFormat;
    2. import lombok.Data;
    3. import org.springframework.data.annotation.Id;
    4. import org.springframework.data.elasticsearch.annotations.DateFormat;
    5. import org.springframework.data.elasticsearch.annotations.Document;
    6. import org.springframework.data.elasticsearch.annotations.Field;
    7. import org.springframework.data.elasticsearch.annotations.FieldType;
    8. import java.time.LocalDate;
    9. import java.time.LocalDateTime;
    10. /**
    11. * @author Sinbad
    12. * @description: 测试ES对象
    13. * @date 2022/8/26 17:12
    14. */
    15. @Document(indexName = "mysql-test")
    16. @Data
    17. public class TestEsEntity {
    18. @Id
    19. Long id;
    20. @Field(type = FieldType.Text, name = "addr")
    21. String addr;
    22. @Field(type = FieldType.Text, name = "name")
    23. String name;
    24. @Field(type = FieldType.Date, name = "birthday", pattern = "yyyy-MM-dd")
    25. LocalDate birthday;
    26. @JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8",locale = "zh_CN")
    27. @Field(type = FieldType.Date, name = "create_time", pattern = "yyyy-MM-dd HH:mm:ss",format =DateFormat.custom )
    28. LocalDateTime createTime;
    29. }

     @Document注解:表示对应一个索引名相关的文档
    @Data注解:lombok的,为类提供读写属性, 此外还提供了 equals()、hashCode()、toString() 方法
    @Id 注解:表示文档的ID字段
    @Field注解:文档字段的注解,对于日期含时间的字段,要写patten和format,不然会无法更新文档对象
    @JsonFormat注解:将文档转换成JSON返回给前端时用到
    注意日期类型字段不要用java.util.Date类型,要用java.time.LocalDate或java.time.LocalDateTime类型。

     测试实例:

    1. import com.hkyctech.commons.base.entity.JsonResult;
    2. import com.hkyctech.tu.core.vo.TestEsEntity ;
    3. import lombok.extern.slf4j.Slf4j;
    4. import org.elasticsearch.index.query.BoolQueryBuilder;
    5. import org.elasticsearch.index.query.QueryBuilders;
    6. import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
    7. import org.springframework.data.domain.PageRequest;
    8. import org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate;
    9. import org.springframework.data.elasticsearch.core.query.NativeSearchQuery;
    10. import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
    11. import org.springframework.data.elasticsearch.core.query.Query;
    12. import org.springframework.stereotype.Service;
    13. import javax.annotation.Resource;
    14. @Slf4j
    15. @Service
    16. public class ElasticSearchServiceImpl {
    17. @Resource
    18. ElasticsearchRestTemplate elasticsearchTemplate; //直接注入就可以用了
    19. /***
    20. * @description 查询全部数据
    21. */
    22. public Object testSearchAll(){
    23. Query query=elasticsearchTemplate.matchAllQuery();
    24. return elasticsearchTemplate.search(query, TestEsEntity .class);
    25. }
    26. /***
    27. * @description 精确查询地址字段
    28. * @param keyword 搜索关键字
    29. */
    30. public Object testSearchAddr(String keyword) {
    31. NativeSearchQuery nativeSearchQuery = new NativeSearchQueryBuilder()
    32. //查询条件
    33. .withQuery(QueryBuilders.queryStringQuery(keyword).defaultField("addr"))
    34. //分页
    35. .withPageable(PageRequest.of(0, 10))
    36. //高亮字段显示
    37. .withHighlightFields(new HighlightBuilder.Field(keyword))
    38. .build();
    39. return elasticsearchTemplate.search(nativeSearchQuery, TestEsEntity .class);
    40. }
    41. /***
    42. * @description 组合查询,查询关键词不分词,关系and
    43. */
    44. public Object testComboSearchAnd(){
    45. BoolQueryBuilder esQuery=QueryBuilders.boolQuery()
    46. .must(QueryBuilders.termQuery("addr", "深圳"))
    47. .must(QueryBuilders.termQuery("addr", "广东"));
    48. NativeSearchQuery nativeSearchQuery = new NativeSearchQueryBuilder()
    49. //查询条件
    50. .withQuery(esQuery)
    51. //分页
    52. .withPageable(PageRequest.of(0, 10))
    53. .build();
    54. return elasticsearchTemplate.search(nativeSearchQuery, TestEsEntity .class);
    55. }
    56. /***
    57. * @description 组合查询,查询关键词不分词,关系or
    58. */
    59. public Object testComboSearchOr(){
    60. BoolQueryBuilder esQuery=QueryBuilders.boolQuery()
    61. .should(QueryBuilders.termQuery("addr", "深圳"))
    62. .should(QueryBuilders.termQuery("addr", "广东"));
    63. NativeSearchQuery nativeSearchQuery = new NativeSearchQueryBuilder()
    64. //查询条件
    65. .withQuery(esQuery)
    66. //分页
    67. .withPageable(PageRequest.of(0, 10))
    68. .build();
    69. return elasticsearchTemplate.search(nativeSearchQuery, TestEsEntity .class);
    70. }
    71. /***
    72. * @description 索引或更新文档
    73. * @param vo 文档对象
    74. */
    75. public JsonResult testPutDocument(TestEsEntity vo){
    76. try {
    77. Object data = elasticsearchTemplate.save(vo);
    78. return JsonResult.getSuccessResult(data,"更新成功");
    79. }catch (Exception e){
    80. // 看http请求响应日志其实操作成功了,但是会报解析出错,可能是spring的bug,这里拦截一下
    81. String message=e.getMessage();
    82. if(message.indexOf("response=HTTP/1.1 200 OK")>0 || message.indexOf("response=HTTP/1.1 201 Created")>0){
    83. return JsonResult.getSuccessResult("更新成功");
    84. }
    85. return JsonResult.getFailResult(e.getStackTrace(),e.getMessage());
    86. }
    87. }
    88. /***
    89. * @description 删除文档
    90. * @param id 文档ID
    91. */
    92. public JsonResult deleteDocument(String id){
    93. try {
    94. elasticsearchTemplate.delete(id, TestEsEntity .class);
    95. return JsonResult.getSuccessResult("删除成功");
    96. }catch (Exception e){
    97. String message=e.getMessage();
    98. // 看http请求响应日志其实操作成功了,但是会报解析出错,可能是spring的bug,这里拦截一下
    99. if(message.indexOf("response=HTTP/1.1 200 OK")>0 ){
    100. return JsonResult.getSuccessResult("删除成功");
    101. }
    102. return JsonResult.getFailResult(e.getStackTrace(),e.getMessage());
    103. }
    104. }
    105. }

    二、使用ElasticsearchRepository 类

      1.引用Maven类库

    1. <dependency>
    2. <groupId>org.springframework.boot</groupId>
    3. <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
    4. </dependency>

      2. 配置文件application.yml

    1. spring:
    2. elasticsearch:
    3. rest:
    4. uris: http://192.168.10.202:9200
    5. connection-timeout: 1s
    6. read-timeout: 1m
    7. username: elastic
    8. password: elastic

     3. ElasticsearchRepository接口的源码 

    1. package org.springframework.data.elasticsearch.repository;
    2. import java.io.Serializable;
    3. import org.elasticsearch.index.query.QueryBuilder;
    4. import org.springframework.data.domain.Page;
    5. import org.springframework.data.domain.Pageable;
    6. import org.springframework.data.elasticsearch.core.query.SearchQuery;
    7. import org.springframework.data.repository.NoRepositoryBean;
    8. @NoRepositoryBean
    9. public interface ElasticsearchRepository<T, ID extends Serializable> extends ElasticsearchCrudRepository<T, ID> {
    10. <S extends T> S index(S entity);
    11. Iterable<T> search(QueryBuilder query);
    12. Page<T> search(QueryBuilder query, Pageable pageable);
    13. Page<T> search(SearchQuery searchQuery);
    14. Page<T> searchSimilar(T entity, String[] fields, Pageable pageable);
    15. void refresh();
    16. Class<T> getEntityClass();
    17. }

     4.CrudRepository  源码

    1. package org.springframework.data.repository;
    2. import java.util.Optional;
    3. /**
    4. * Interface for generic CRUD operations on a repository for a specific type.
    5. *
    6. * @author Oliver Gierke
    7. * @author Eberhard Wolff
    8. */
    9. @NoRepositoryBean
    10. public interface CrudRepository<T, ID> extends Repository<T, ID> {
    11. /**
    12. * Saves a given entity. Use the returned instance for further operations as the save operation might have changed the
    13. * entity instance completely.
    14. *
    15. * @param entity must not be {@literal null}.
    16. * @return the saved entity will never be {@literal null}.
    17. */
    18. <S extends T> S save(S entity);
    19. /**
    20. * Saves all given entities.
    21. *
    22. * @param entities must not be {@literal null}.
    23. * @return the saved entities will never be {@literal null}.
    24. * @throws IllegalArgumentException in case the given entity is {@literal null}.
    25. */
    26. <S extends T> Iterable<S> saveAll(Iterable<S> entities);
    27. /**
    28. * Retrieves an entity by its id.
    29. *
    30. * @param id must not be {@literal null}.
    31. * @return the entity with the given id or {@literal Optional#empty()} if none found
    32. * @throws IllegalArgumentException if {@code id} is {@literal null}.
    33. */
    34. Optional<T> findById(ID id);
    35. /**
    36. * Returns whether an entity with the given id exists.
    37. *
    38. * @param id must not be {@literal null}.
    39. * @return {@literal true} if an entity with the given id exists, {@literal false} otherwise.
    40. * @throws IllegalArgumentException if {@code id} is {@literal null}.
    41. */
    42. boolean existsById(ID id);
    43. /**
    44. * Returns all instances of the type.
    45. *
    46. * @return all entities
    47. */
    48. Iterable<T> findAll();
    49. /**
    50. * Returns all instances of the type with the given IDs.
    51. *
    52. * @param ids
    53. * @return
    54. */
    55. Iterable<T> findAllById(Iterable<ID> ids);
    56. /**
    57. * Returns the number of entities available.
    58. *
    59. * @return the number of entities
    60. */
    61. long count();
    62. /**
    63. * Deletes the entity with the given id.
    64. *
    65. * @param id must not be {@literal null}.
    66. * @throws IllegalArgumentException in case the given {@code id} is {@literal null}
    67. */
    68. void deleteById(ID id);
    69. /**
    70. * Deletes a given entity.
    71. *
    72. * @param entity
    73. * @throws IllegalArgumentException in case the given entity is {@literal null}.
    74. */
    75. void delete(T entity);
    76. /**
    77. * Deletes the given entities.
    78. *
    79. * @param entities
    80. * @throws IllegalArgumentException in case the given {@link Iterable} is {@literal null}.
    81. */
    82. void deleteAll(Iterable<? extends T> entities);
    83. /**
    84. * Deletes all entities managed by the repository.
    85. */
    86. void deleteAll();
    87. }

    5. 查询查找策略

    5.1存储库方法可以定义为具有以下返回类型,用于返回多个元素:

    • List

    • Stream

    • SearchHits

    • List>

    • Stream>

    • SearchPage

    5.2 使用@Query注解

     使用@query注释对方法声明query。

    1. interface BookRepository extends ElasticsearchRepository<Book, String> {
    2. @Query("{\"match\": {\"name\": {\"query\": \"?0\"}}}")
    3. Page<Book> findByName(String name,Pageable pageable);
    4. }

    设置为注释参数的字符串必须是有效的 Elasticsearch JSON 查询。 它将作为查询元素的值发送到Easticsearch;例如,如果使用参数 John 调用函数,它将生成以下查询正文:

    1. {
    2. "query": {
    3. "match": {
    4. "name": {
    5. "query": "John"
    6. }
    7. }
    8. }
    9. }

    @Query采用集合参数的方法进行注释

    1. @Query("{\"ids\": {\"values\": ?0 }}")
    2. List<SampleEntity> getByIds(Collection<String> ids);

    将进行ID查询以返回所有匹配的文档。因此,调用List为[“id1”、“id2”、“id3”]的方法将生成查询主体

    1. {
    2. "query": {
    3. "ids": {
    4. "values": ["id1", "id2", "id3"]
    5. }
    6. }
    7. }

    6.开发实例:

    1. public interface LogRepository extends ElasticsearchRepository<Log, String> {
    2. /**
    3. * 定义一个方法查询:根据title查询es
    4. *
    5. * 原因: ElasticsearchRepository会分析方法名,参数对应es中的field(这就是灵活之处)
    6. * @param title
    7. */
    8. List<Log> findBySummary(String summary);
    9. List<Log> findByTitle(String title);
    10. /**
    11. * 定义一个方法查询: 根据title,content查询es
    12. */
    13. List<Log> findByTitleAndContent(String title, String content);
    14. }
    1. @PostMapping("save")
    2. public void save(@Validated @RequestBody Log req){
    3. Log dto = new Log();
    4. dto.setTitle(req.getTitle());
    5. dto.setSummary(req.getSummary());
    6. dto.setContent(req.getContent());
    7. dto.setCreateTime(new Date());
    8. dto.setId(req.getId());
    9. LogRepository.save(dto);
    10. return ;
    11. }
    12. @PostMapping("testTitle")
    13. public void testSearchTitle(@Validated @RequestBody Log req){
    14. List<Log> searchResult = logRepository.findByTitle(req.getMobileType());
    15. Iterator<Log> iterator = searchResult.iterator();
    16. while(iterator.hasNext()){
    17. System.out.println(iterator.next());
    18. }
    19. System.out.println("sa");
    20. return;
    21. }

    官网:Spring Data Elasticsearch - Reference Documentation

  • 相关阅读:
    【七:docken+jenkens部署】
    qt输出自定义的pdf文件源码详解
    Android 开发学习(二)
    【软考学习3】数据表示——浮点数计算 + 单精度浮点数IEEE754计算
    Spark(林子雨慕课课程)
    二、python+前端 实现MinIO分片上传
    PHP8的数据封装(数据隐藏)-PHP8知识详解
    HTTP+ 加密 + 认证 + 完整性保护 =HTTPS(HTTPS 安全通信机制)
    关于游戏公司组织架构的小讨论
    redis初级介绍
  • 原文地址:https://blog.csdn.net/leesinbad/article/details/128278548