springBoot 整合ElasticSearch

本文介绍如何在Spring Boot项目中集成Elasticsearch,包括配置连接、创建和操作索引,以及通过实体类进行数据操作。同时,解决常见的中文查询问题,并提供详细的API使用示例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

依赖

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.3.3.RELEASE</version>
        <relativePath/> <!-- lookup parent from repository -->
    </parent>
    <groupId>com.hhy</groupId>
    <artifactId>elasticsearch</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <name>elasticsearch</name>
    <description>Demo project for Spring Boot</description>

    <properties>
        <java.version>1.8</java.version>
        <!--2.3.x默认elasticsearch的版本7.6.2,需要与我们自己的版本一致-->
        <elasticsearch.version>7.8.1</elasticsearch.version>
    </properties>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-configuration-processor</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
            <exclusions>
                <exclusion>
                    <groupId>org.junit.vintage</groupId>
                    <artifactId>junit-vintage-engine</artifactId>
                </exclusion>
            </exclusions>
        </dependency>
        <!-- https://mvnrepository.com/artifact/com.alibaba/fastjson -->
        <dependency>
            <groupId>com.alibaba</groupId>
            <artifactId>fastjson</artifactId>
            <version>1.2.73</version>
        </dependency>
    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

</project>

配置类

@Configuration
public class ElasticSearchConfig {

    @Bean
    public RestHighLevelClient restHighLevelClient() {
        return new RestHighLevelClient(
                RestClient.builder(
                        new HttpHost("127.0.0.1",9200,"http")));
    }
}

实体类

@Data
@NoArgsConstructor
@AllArgsConstructor
public class User {
    private String name;
    private Integer age;
    private LocalDate birthday;
    private String[] hobby;
}

测试链接

@SpringBootTest
class ElasticsearchApplicationTests {


    @Autowired
    private RestHighLevelClient restHighLevelClient;

    //索引的创建
    @Test
    public void createIndex(){
        try {
            //创建索引请求
            CreateIndexRequest request = new CreateIndexRequest("testIndex");
            //客户端执行请求
            CreateIndexResponse createIndexResponse = restHighLevelClient.indices().create(request, RequestOptions.DEFAULT);
            System.out.println(createIndexResponse);
        } catch (IOException e) {
            e.printStackTrace();
        }

    }
}

报错
[testIndex] ElasticsearchStatusException[Elasticsearch exception [type=invalid_index_name_exception, reason=Invalid index name [testIndex], must be lowercase]
]
解决
索引必须是小写

常用API使用

package com.hhy.elasticsearch;

import com.alibaba.fastjson.JSON;
import com.hhy.elasticsearch.entity.User;
import org.elasticsearch.action.admin.indices.delete.DeleteIndexRequest;
import org.elasticsearch.action.delete.DeleteRequest;
import org.elasticsearch.action.delete.DeleteResponse;
import org.elasticsearch.action.get.GetRequest;
import org.elasticsearch.action.get.GetResponse;
import org.elasticsearch.action.index.IndexRequest;
import org.elasticsearch.action.index.IndexResponse;
import org.elasticsearch.action.search.SearchRequest;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.action.support.master.AcknowledgedResponse;
import org.elasticsearch.action.update.UpdateRequest;
import org.elasticsearch.action.update.UpdateResponse;
import org.elasticsearch.client.RequestOptions;
import org.elasticsearch.client.RestHighLevelClient;
import org.elasticsearch.client.indices.CreateIndexRequest;
import org.elasticsearch.client.indices.CreateIndexResponse;
import org.elasticsearch.client.indices.GetIndexRequest;
import org.elasticsearch.common.xcontent.XContentType;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.index.query.TermQueryBuilder;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.fetch.subphase.FetchSourceContext;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import java.io.IOException;
import java.time.LocalDate;
import java.util.UUID;

@SpringBootTest
class ElasticsearchApplicationTests {


    @Autowired
    private RestHighLevelClient restHighLevelClient;

    //索引的创建
    @Test
    public void createIndex(){
        try {
            //创建索引请求
            CreateIndexRequest request = new CreateIndexRequest("test-index");
            //客户端执行请求
            CreateIndexResponse createIndexResponse = restHighLevelClient.indices().create(request, RequestOptions.DEFAULT);
            System.out.println(createIndexResponse);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //索引是否存在
    @Test
    public void exitIndex() {
        try {
            GetIndexRequest request = new GetIndexRequest("test-index");
            boolean exists = restHighLevelClient.indices().exists(request, RequestOptions.DEFAULT);
            System.out.println(exists);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //索引的删除
    @Test
    public void delIndex() {
        try {
            DeleteIndexRequest request = new DeleteIndexRequest("test-index");
            AcknowledgedResponse delete = restHighLevelClient.indices().delete(request, RequestOptions.DEFAULT);
            System.out.println(delete.isAcknowledged());
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //文档的创建
    @Test
    public void addDocument() {
        try {
            //创建对象
            User user = new User("wangwu", 20, LocalDate.parse("2000-01-01"), new String[]{"唱", "跳", "rap", "篮球"});
            //创建请求
            IndexRequest request = new IndexRequest("test-index");
            //规则 put /test-index/_doc/id
            request.id(UUID.randomUUID().toString());//我的结果UUID 095abde7-23e8-4939-9ee9-21140fa378c1
            //数据封入json
            IndexRequest source = request.source(JSON.toJSONString(user), XContentType.JSON);
            //客户端发送请求,获取响应结果
            IndexResponse response = restHighLevelClient.index(request, RequestOptions.DEFAULT);
            System.out.println(response.toString());
            //对应我们命令返回的状态
            System.out.println(response.status());
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //文档是否存在
    @Test
    public void exitDocument() {
        try {
            //获取文档,判断是否存在 get /index/_doc/id
            GetRequest getRequest = new GetRequest("test-index", "095abde7-23e8-4939-9ee9-21140fa378c1");//index,id
            //不返回_source的上下文
            getRequest.fetchSourceContext(new FetchSourceContext(false));
            boolean exists = restHighLevelClient.exists(getRequest, RequestOptions.DEFAULT);
            System.out.println(exists);
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    //获取文档内容
    @Test
    public void getDocument() {
        try {
            GetRequest getRequest = new GetRequest("test-index", "095abde7-23e8-4939-9ee9-21140fa378c1");//index,id
            GetResponse documentFields = restHighLevelClient.get(getRequest, RequestOptions.DEFAULT);
            System.out.println(documentFields.toString());
            //{"_index":"test-index","_type":"_doc","_id":"095abde7-23e8-4939-9ee9-21140fa378c1","_version":1,"_seq_no":0,"_primary_term":1,"found":true,"_source":{"age":20,"birthday":"2000-01-01","hobby":["唱","跳","rap","篮球"],"name":"张三"}}
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //修改文档内容
    @Test
    public void updDocument() {
        try {
            UpdateRequest updateRequest = new UpdateRequest("test-index", "095abde7-23e8-4939-9ee9-21140fa378c1");
            User user = new User();
            user.setName("李四~~~~~~~~~~");
            UpdateRequest doc = updateRequest.doc(JSON.toJSONString(user), XContentType.JSON);
            UpdateResponse update = restHighLevelClient.update(doc, RequestOptions.DEFAULT);
            System.out.println(update.status());//OK
            //查看结果
            getDocument();//{"_index":"test-index","_type":"_doc","_id":"095abde7-23e8-4939-9ee9-21140fa378c1","_version":2,"_seq_no":1,"_primary_term":2,"found":true,"_source":{"age":20,"birthday":"2000-01-01","hobby":["唱","跳","rap","篮球"],"name":"李四~~~~~~~~~~"}}
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //删除文档内容
    @Test
    public void delDocument() {
        try {
            DeleteRequest deleteRequest = new DeleteRequest("test-index", "095abde7-23e8-4939-9ee9-21140fa378c1");
            DeleteResponse deleteResponse = restHighLevelClient.delete(deleteRequest, RequestOptions.DEFAULT);
            System.out.println(deleteResponse.status());//OK
            //是否存在
            exitDocument();//false
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
    //查询
    @Test
    public void queryDocument(){
        try {
            SearchRequest searchRequest = new SearchRequest("test-index");
            //构造查询条件
            SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();
            //查询条件可以使用 QueryBuilders工具类创建
            //termQuery精确匹配
            TermQueryBuilder builder = QueryBuilders.termQuery("name", "张三");
            //matchAllQuery匹配所有QueryBuilders.matchAllQuery();
            searchSourceBuilder.query(builder);
            //分页  searchSourceBuilder.from();  searchSourceBuilder.size();
            //高亮 searchSourceBuilder.highlighter();
            //排序 searchSourceBuilder.sort()
            searchRequest.source(searchSourceBuilder);

            SearchResponse response = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);

            System.out.println(JSON.toJSONString(response.getHits()));
            

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

问题

queryDocument()里 的QueryBuilders.termQuery(“name”, “张三”); 查询结果为空,

elasticsearch查询时termQuery查询中文匹配失败

解决方法


TermQueryBuilder builder = QueryBuilders.termQuery(“name.keyword”, “张三”);

二 相当于模糊查询(想要精确匹配不要用)
MatchQueryBuilder builder = QueryBuilders.matchQuery(“name”, “张三”);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值