前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【SpringBoot2.0系列11】SpringBoot之@Elasticsearch完成CURD

【SpringBoot2.0系列11】SpringBoot之@Elasticsearch完成CURD

作者头像
yukong
发布2018-10-09 16:02:30
2.2K0
发布2018-10-09 16:02:30
举报
文章被收录于专栏:yukong的小专栏

【SpringBoot系列01】初识SpringBoot

【SpringBoot系列02】SpringBoot之使用Thymeleaf视图模板

【SpringBoot系列03】SpringBoot之使用freemark视图模板

【SpringBoot系列04】SpringBoot之使用JPA完成简单的rest api

【SpringBoot系列05】SpringBoot之整合Mybatis

【SpringBoot2.0系列06】SpringBoot之多数据源动态切换数据源

【SpringBoot2.0系列07】SpringBoot之redis使用(Lettuce版本)

【SpringBoot2.0系列08】SpringBoot之redis数据缓存管理

【SpringBoot2.0系列09】SpringBoot之rabbitmq使用

【SpringBoot2.0系列10】SpringBoot之@Scheduled任务调度

【SpringBoot2.0系列11】SpringBoot之@Elasticsearch完成CURD

ElasticSearch是一个基于Lucene的搜索服务器。它提供了一个分布式多用户能力的全文搜索引擎,基于RESTful web接口。Elasticsearch是用Java开发的,并作为Apache许可条款下的开放源码发布,是当前流行的企业级搜索引擎。设计用于云计算中,能够达到实时搜索,稳定,可靠,快速,安装使用方便。

如果在springboot使用Easticsearch呢。在这里我们使用spring-boot-starter-data-elasticsearch。

它提供一系列简单的api给我们使用,让我们有种操作关系数据库的感觉。

好了话不多说,先说一下环境。

  • spring boot2.x
  • jdk8
  • elasticsearch5.x(6.x也可以)

依赖

引入依赖

代码语言:javascript
复制
  <dependencies>

        <!-- lombok -->
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <version>1.16.22</version>
        </dependency>
        <!-- elasticsearch -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-elasticsearch</artifactId>
        </dependency>

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

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

在这里我们分别引入elasticsearch跟lombok的依赖,关于lombok的介绍大家可以看看这篇文章 讲的很详细。我这简单的介绍一下在项目中使用Lombok可以减少很多重复代码的书写。比如说getter/setter/toString等方法的编写。

配置es地址

在下文中我将用es代替elasticsearch。我们打开application.yml文件 配置如下

代码语言:javascript
复制
  spring:
  data:
    elasticsearch:
      # 集群的名字
      cluster-name: wali
      # 节点的ip与端口 注意端口是9300不是9200
      cluster-nodes: 127.0.0.1:9300

构建文档对象

假设这是一个商品索引goods,他有一个类型是电脑computer。

分别有四个字段

  • id 唯一标识
  • name 商品名称
  • number 商品数量
  • desc 商品具体描述 我们根据上面的描述,编写出对应的实体类
代码语言:javascript
复制
@Data
@ToString
@Accessors(chain = true)
@Document(indexName = "goods", type = "computer")
public class Good {

    /**
     * 主键,注意这个搜索是id类型是string,与我们常用的不同
     * Id注解加上后,在Elasticsearch里相应于该列就是主键了,在查询时就可以直接用主键查询
     */
    @Id
    private String id;

    private String name;

    private String desc;

    private Integer number;

}

其中@Data @ToString @Accessors(chain = true) 是属于lombok注解。

  • @Data 会自动上传get/set方法
  • @ToString 会生成tostring方法
  • @Accessors(chain = true) 会让我们set方法可以链式调用 @Document注解

@Document注解里面的几个属性,类比mysql的话是这样:

indexName –> 索引库的名称,建议以项目的名称命名,就相当于数据库DB

type –> 类型,建议以实体的名称命名Table ,就相当于数据库中的表table

Document –> row 就相当于某一个具体对象

jpa构建文档库

接着,我们可以通过jpa构建文档库,来操作我们的goods对应的文档。

因为我们引入的是spring data的elasticsearch所以它遵循spring data的接口,也就是说操作elasticSearch与操作spring data jpa的方法是完全一样的,我们只将文档库继承ElasticsearchRepository即可。

代码语言:javascript
复制
public interface GoodRepository extends ElasticsearchRepository<Good, String> {

   /**
     * 根据商品名称查询 分页
     * @param name
     * @param pageable
     * @return
     */
    Page<Good> findByName(String name, Pageable pageable);

}

然后创建对应的测试类。前面说过快捷键ctrl+shift+t

并且编写测试方法,我们分别需要测试添加 删除 修改 查询 分页查询方法。

代码语言:javascript
复制
@Component
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
public class GoodRepositoryTest extends Chapter10ApplicationTests {

    @Autowired
    private GoodRepository goodRepository;
    
    @Test
    public void save(){}

    @Test
    public void update(){}

    @Test
    public void select(){}

    @Test
    public void delete(){}

    @Test
    public void findByName() {
       
    }
}

上面代码我们是通过基础主测试类然后使用@Component注解就可以,这样就不需要每个测试都要@SpringTest注解与@RunWith注解了

另外@FixMethodOrder(MethodSorters.NAME_ASCENDING)这个注解是表示按照方法名的顺序来排序,不然它不会按照我们方法书写的顺序执行,那么就有可能导致,还没save就select,这样就会失败了。

接下来继续编写方法体。goodRepository跟我们直接data-jparespository用法基本一致。都有继承save,delete,find方法的。

代码语言:javascript
复制
@Test
    public void save(){
        Good good = new Good();
        good.setId("100")
                .setName("联想e541")
                .setDesc("联想e系列")
                .setNumber(10);
        Good result = goodRepository.save(good);
        Assert.assertNotNull(result);
    }

    @Test
    public void select(){
        // 需要注意find方法返回的死Optional对象 需要调用get方法返回具体的实体类对象
        Good result = goodRepository.findById("100").get();
        Assert.assertNotNull(result);

    }

    @Test
    public void update(){
        Good result = goodRepository.findById("100").get();
        result.setNumber(300);
        // 更新也是调用save方法
        Good good = goodRepository.save(result);
        Assert.assertNotNull(good);

    }



    @Test
    public void delete(){
        goodRepository.deleteById("100");
    }

我们首先测试增删改查方法。并且通过Assert断言来判断。

image.png

测试通过,

接下来我测试一下分页查询方法,首页我们看一下es中、goods索引computer类别下有哪些文档。

代码语言:javascript
复制
curl -XGET  'http://127.0.0.1:9200/goods/computer/_search?pretty'

结果如下

代码语言:javascript
复制
{
  "took" : 21,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : 3,
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "goods",
        "_type" : "computer",
        "_id" : "_search",
        "_score" : 1.0,
        "_source" : {
          "id" : "_search",
          "name" : "macbook",
          "number" : 20,
          "desc" : "macbook air"
        }
      },
      {
        "_index" : "goods",
        "_type" : "computer",
        "_id" : "2",
        "_score" : 1.0,
        "_source" : {
          "id" : "2",
          "name" : "think pad",
          "number" : 20,
          "desc" : "联想旗下thinkpad系列"
        }
      },
      {
        "_index" : "goods",
        "_type" : "computer",
        "_id" : "1",
        "_score" : 1.0,
        "_source" : {
          "id" : "1",
          "name" : "macbook",
          "number" : 20,
          "desc" : "macbook pro"
        }
      }
    ]
  }
}

我看到在computer类别中存有三条文档,name分别是 macbook think pad macbook,所以我们查询一下name=macbook的文档,pageSize=1,pageNum=1.

代码语言:javascript
复制
@Test
    public void findByName() {
        String name = "macbook";
        Pageable pageable = new PageRequest(1,1);
        Page<Good> goods = goodRepository.findByName(name, pageable);
        System.out.println(goods.getContent());
        Assert.assertEquals(1, goods.getSize());

    }

我们查询name为macbook的数据,并且限制每页一条,所以我们查询的结果总数应该是一条。结果如下。

在这节,我们了解了springboot与es的curd操作,都是比较简单的,那么下节我们会详细了解springboot对es如何进行复杂查询,与聚合查询。

最后本节的配套代码地址为https://github.com/YuKongEr/SpringBoot-Study/tree/master/chapter10

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018.09.04 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 依赖
  • 配置es地址
  • 构建文档对象
  • jpa构建文档库
相关产品与服务
Elasticsearch Service
腾讯云 Elasticsearch Service(ES)是云端全托管海量数据检索分析服务,拥有高性能自研内核,集成X-Pack。ES 支持通过自治索引、存算分离、集群巡检等特性轻松管理集群,也支持免运维、自动弹性、按需使用的 Serverless 模式。使用 ES 您可以高效构建信息检索、日志分析、运维监控等服务,它独特的向量检索还可助您构建基于语义、图像的AI深度应用。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档