首页 > 其他分享 >spring boot 集成 Elasticsearch

spring boot 集成 Elasticsearch

时间:2023-08-17 16:46:29浏览次数:40  
标签:String spring boot springframework data elasticsearch import org Elasticsearch

一、背景

  最近在做录制回放平台, 因为需要把部分数据存储到ES,因此特地实践和调研了一把,把相关材料记录一下;

  elastcishearch 版本:7.14.2

      spring boot版本:2.6.13

     spring-boot-starter-data-elasticsearch: 2.6.13

    版本参考文档 https://docs.spring.io/spring-data/elasticsearch/docs/5.2.0-M1/reference/html/#elasticsearch.clients

 

二、参考文档

https://learnku.com/docs/elasticsearch73/7.3

https://docs.kilvn.com/elasticsearch/docs/6.html

https://spring.io/projects/spring-data-elasticsearch/

三、接入步骤

 3.1 maven配置

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.4.0</version>
    <relativePath/>
</parent>

<dependencies>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
    </dependency>
    <dependency>
        <groupId>org.projectlombok</groupId>
        <artifactId>lombok</artifactId>
        <version>1.18.12</version>
        <scope>compile</scope>
    </dependency>
</dependencies>

 3.2 启动配置

 因为考虑可能要支持多数据源,所以我没有考虑在配置中使用 spring.data.elasticsearch.repositories.enabled=true 的方式,而是自定义了启动配置类,代码如下

 

 1 import org.elasticsearch.client.RestHighLevelClient;
 2 import org.springframework.beans.factory.annotation.Qualifier;
 3 import org.springframework.beans.factory.annotation.Value;
 4 import org.springframework.context.annotation.Bean;
 5 import org.springframework.context.annotation.Configuration;
 6 import org.springframework.data.elasticsearch.client.ClientConfiguration;
 7 import org.springframework.data.elasticsearch.client.RestClients;
 8 import org.springframework.data.elasticsearch.config.AbstractElasticsearchConfiguration;
 9 import org.springframework.data.elasticsearch.core.ElasticsearchOperations;
10 import org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate;
11 import org.springframework.data.elasticsearch.core.convert.ElasticsearchConverter;
12 
13 
14 @Configuration
15 public class RestClientConfig extends AbstractElasticsearchConfiguration {
16 
17  
18     @Value("${elasticsearch.url}")
19     private String elasticsearchUrl;
20 
21     @Value("${elasticsearch.username}")
22     private String username;
23 
24     @Value("${elasticsearch.password}")
25     private String password;
26 
27     
28     @Bean("esClient")
29     @Override
30     public RestHighLevelClient elasticsearchClient() {
31         final ClientConfiguration clientConfiguration = ClientConfiguration.builder()
32                 .connectedTo(elasticsearchUrl)
33                 .withBasicAuth(username, password)
34                 .build();
35         return RestClients.create(clientConfiguration).rest();
36     }
37 
38     @Override
39     @Bean(name = {"elasticSearchRestTemplate" })
40     public ElasticsearchRestTemplate elasticsearchOperations(ElasticsearchConverter elasticsearchConverter,
41                                                            @Qualifier("esClient") RestHighLevelClient elasticsearchClient) {
42         return new ElasticsearchRestTemplate(elasticsearchClient, elasticsearchConverter);
43     }
44 
45 }

以下配置可以放入到application.properties里面即可

elasticsearch.url=xxxx
elasticsearch.username=xxxx
elasticsearch.password=xxx

3.3 创建索引&定义实体对象

elasticsearch索引的创建,可以手动创建,也可以自动创建;我们可以利用spring-data-elasticsearch的自动创建的能力来构建索引

package com.example.es.entity;

import lombok.Data;
import org.springframework.data.annotation.Id;
import org.springframework.data.elasticsearch.annotations.Document;
import org.springframework.data.elasticsearch.annotations.Field;
import org.springframework.data.elasticsearch.annotations.FieldType;
import org.springframework.data.elasticsearch.annotations.Setting;

import java.util.Date;

/**
 * @author peng.hu1
 * @Date 2023/7/13 15:06
 */
@Data
@Setting(shards = 3)
@Document(indexName = "record", createIndex = true)
public class RecordEntity {

    /**
     * 主键
     */
    @Id
    private String id;


    @Field(name = "api", type = FieldType.Keyword)
    private String api;


    /**
     * 创建时间
     */
    @Field(value = "create_time")
    private Date createTime;


    /**
     * 应用名
     */
    @Field(value = "app_name", type = FieldType.Keyword)
    private String appName;


    /**
     * 环境信息
     */
    @Field(value = "env", type = FieldType.Keyword)
    private String env;

    /**
     * 机器IP
     */
    @Field(value = "host", type = FieldType.Keyword)
    private String host;

    /**
     * 链路追踪ID
     */
    @Field(value = "trace_id", type = FieldType.Keyword)
    private String traceId;

    /**
     * 主调用
     */
    @Field(value = "entrance_desc", type = FieldType.Keyword)
    private String entranceDesc;

    /**
     * 记录序列化信息
     */
    @Field(value = "wrapper_record", type = FieldType.Keyword, index = false)
    private String wrapperRecord;

    /**
     * 请求参数JSON
     */
    @Field(type = FieldType.Text, index=false)
    private String request;

    /**
     * 返回值JSON
     */
    @Field(type = FieldType.Text, index=false)
    private String response;
}

定义实体的时候,有几个关键注解需要说明一下,
@Document(indexName = "record", createIndex = true) 其中indexName为索引名,createIndex=true表示默认在插入的时候,会创建索引;索引是包含mapping 和 setting 的,mapping的配置是从@Field注解生成的; @Setting注解用于设置分片相关物理属性;

public @interface Field {
  FieldType type() default FieldType.Auto; //自动检测属性的类型,可以根据实际情况自己设置
  FieldIndex index() default FieldIndex.analyzed; //默认情况下分词,一般默认分词就好,除非这个字段你确定查询时不会用到
  DateFormat format() default DateFormat.none; //时间类型的格式化
  String pattern() default ""; 
  boolean store() default false; //默认情况下不存储原文
  String searchAnalyzer() default ""; //指定字段搜索时使用的分词器
  String indexAnalyzer() default ""; //指定字段建立索引时指定的分词器
  String[] ignoreFields() default {}; //如果某个字段需要被忽略
  boolean includeInParent() default false;
}

FieldType.Keyword 跟 FieldType.Text 都可以运用到字符串,最大的区别在于Text是会分词建立倒排索引的,这个按需选择类型就好;如果只是当做db来用,默认强制设置成keyWord类型更合适;

3.4 对索引对象的增删改查

定义接口

package com.example.es.service;

import com.example.es.entity.RecordEntity;
import com.example.es.model.Page;
import com.example.es.model.Search;

import java.util.List;

/**
 * @author peng.hu1
 * @Date 2023/8/17 16:22
 */
public interface RecordEntityService {

    public void save(RecordEntity entity);

    public void batchSave(List<RecordEntity> entityList);

    public Page<RecordEntity> search(Search search);

    public void remove(RecordEntity entity);
}

接口实现

package com.example.es.impl;

import com.example.es.entity.RecordEntity;
import com.example.es.model.Page;
import com.example.es.model.Search;
import com.example.es.service.RecordEntityService;
import org.elasticsearch.index.query.BoolQueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.sort.SortBuilders;
import org.elasticsearch.search.sort.SortOrder;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate;
import org.springframework.data.elasticsearch.core.SearchHit;
import org.springframework.data.elasticsearch.core.SearchHits;
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
import org.springframework.stereotype.Component;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.List;
import java.util.stream.Collectors;

/**
 * @author peng.hu1
 * @Date 2023/8/17 16:25
 */
@Component
public class RecordEntityServiceImpl implements RecordEntityService {

    @Resource(name = "elasticSearchRestTemplate")
    ElasticsearchRestTemplate elasticsearchRestTemplate;

    @Override
    public void save(RecordEntity entity) {
        elasticsearchRestTemplate.save(entity);
    }

    @Override
    public void batchSave(List<RecordEntity> entityList) {
        elasticsearchRestTemplate.save(entityList);
    }

    @Override
    public Page<RecordEntity> search(Search r) {
        NativeSearchQueryBuilder query = new NativeSearchQueryBuilder();
        BoolQueryBuilder queryBuilder = QueryBuilders.boolQuery();

        query.withQuery(queryBuilder);

        if(StringUtils.hasLength(r.getAppName())) {
            queryBuilder.filter(QueryBuilders.matchPhraseQuery("app_name", r.getAppName()));
        }

        if(StringUtils.hasLength(r.getEnv())) {
            queryBuilder.filter(QueryBuilders.matchPhraseQuery("env", r.getEnv()));
        }

        //分页 & 排序
        PageRequest pageRequest = PageRequest.of(r.getPage()-1, r.getPageSize());
        query.withQuery(queryBuilder);
        query.withPageable(pageRequest);
        query.withSorts(SortBuilders.fieldSort("create_time").order(SortOrder.DESC));

        SearchHits<RecordEntity> searchHits = elasticsearchRestTemplate.search(query.build(), RecordEntity.class);


        Page<RecordEntity> res = new Page<>();
        res.setPage(r.getPage());
        res.setPageSize(r.getPageSize());
        res.setTotal(searchHits.getTotalHits());
        res.setData(searchHits.stream().map(SearchHit::getContent).collect(Collectors.toList()));

        return res;
    }

    @Override
    public void remove(RecordEntity entity) {
        elasticsearchRestTemplate.delete(entity);
    }
}

至此接入流程就全部结束了



 

标签:String,spring,boot,springframework,data,elasticsearch,import,org,Elasticsearch
From: https://www.cnblogs.com/viogs/p/17637422.html

相关文章

  • springboot集成cas
    CAS介绍CAS是CentralAuthenticationService的缩写,中央认证服务,一种独立开放指令协议。CAS是耶鲁大学(YaleUniversity)发起的一个开源项目,旨在为Web应用系统提供一种可靠的单点登录方法,CAS在2004年12月正式成为JA-SIG的一个项目。特点:开源的企业级单点登录解决方案......
  • spring之RestTemplate使用
    1、带有头部信息的get请求//api访问链接Stringhost=aliWuliuConfig.getHost();//API访问后缀Stringpath=aliWuliuConfig.getPath()+"?type={type}&no={no}";Stringurl=host+path;//替换成自己的阿里云appcodeStringappcode=aliWuliuConfig.getAppcode();//......
  • spring缓存使用
    参考文献https://www.cnblogs.com/fashflying/p/6908028.html如有侵权,请联系删除 一、配置:1.依赖<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-cache</artifactId></dependency>2.bean注入......
  • IDEA社区版+SpringBoot+MyBatisPLus+MySQL实现数据库的保存、查询、修改操作
    一、概述使用IDEA社区+SpringBoot+MyBatisPlus+MySQL实现数据的保存修改与查询。主要记录一下踩坑过程。注意事项:1.社区版IDEA并不能直接创建SpringBoot工程,所以我采用的方式是在Spring官网上,让其帮助我创建一个,创建好后,直接下载。//参考案例https://blog.csd......
  • 【13章】SpringBoot打造企业级一体化SaaS系统
    课程下载——【13章】SpringBoot打造企业级一体化SaaS系统提取码:y8v1 分享课程——【13章】SpringBoot打造企业级一体化SaaS系统,附源码。课程中整合后端主流技术(SpringBoot、物理数据库隔离、加载动态权限、多方式权限控制)、前端必会框架(vue3),完整落地ERP+CRM一体化SaaS系统,带......
  • Spring Boot集成Sharding JDBC分库分表
    背景近期公司购物车项目需要使用ShardingJDBC分表,特记录下。ps:未分库依赖引入<!--sharding-sphereVersion:4.1.1--><dependency><groupId>org.apache.shardingsphere</groupId><artifactId>sharding-jdbc-spring-boot-starter</artifactId><ver......
  • Spring事务与锁的一些事
    1.Spring事务与synchronized顺序问题结论:保证释放锁在事务提交之后当一个方法加上事务后,在执行前要先开启事务,然后再执行目标方法,当目标方法执行完后提交事务。自然获取锁是在开启事务后才执行的操作,一个线程获取到锁,到执行完业务再到释放锁后,此时事务还未提交,此时另外一个......
  • Spring实现幂等性的方法
    在开发Web应用程序时,确保接口的幂等性是一项重要任务。幂等性是指对同一个请求的多次执行应该产生相同的结果,而不会引起不正确的操作或数据损坏。在Spring框架中,我们可以利用一些功能和工具来实现幂等性。本文将介绍一种基本的方法来在Spring中实现幂等性。1.幂等性的概念和原则在......
  • Springboot 转化器
    Springboot提供了很多转化器:其中有ApplicationConversionService:extendsFormattingConversionService。 publicstaticvoidaddApplicationConverters(ConverterRegistryregistry){ addDelimitedStringConverters(registry); registry.addConverter(newStringToDurationC......
  • 社区版idea 开发springmvc踩坑指南
    说明:社区版的idea不支持spring和web,所以在开发时跟旗舰版有些许不同,不同于旗舰版在加载spring,web子模块时社区版需要手动加载tomcat下的所有lib项目以及pro下加载的所有的依赖项lib到libraries中。此外社区版idea在springmvc开发时由于不直接支持web项目所以需要在pro项目的src目录......