elasticsearch(ES)在SpringBoot中的基本使用

一、引言

 ES是一个基于Lucene的搜索服务器。它提供了一个分布式多用户能力的全文搜索引擎,基于Restful web接口。它是一种企业级别的搜索引擎,本身使用Java开发的,类似的搜索引擎还有Apache Solr 也是基于Lucene.

基本概念

ES 是面向文档类型的数据库,一条数据在这里就是一条文档(documnet),用JSON作为文档序列化得格式,为便于理解,我们可将ES的一些基本概念和典型的关系型数据库MySQL作对比

ES的概念和MySQL作对比
ES概念MySQL概念
index(索引)database(数据库)
type(类型)table(表)
document(一条文档)row(一行数据)
field(字段)col(列,字段)

ES最核心的功能是提供强大的搜索功能,后面会继续深入探讨,本文首先作为入门,介绍如何在我们的springboot项目中引入ES搜索引擎,并做简单的使用。

二、ES在SpringBoot中的应用

  1)首先在pom文件中引入spring data ES的依赖包

<!--引用elasticsearch(ES)jar包-->
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
		</dependency>

2)然后我们新建一个book类

@Data
@Document(indexName = "es_book_index",type = "es_book_type")
public class Book {
    @Id
    @Field(type = FieldType.Keyword)
    private String id;
    @Field(type = FieldType.Keyword)
    private String name;
    @Field(type = FieldType.Integer)
    private Integer pageNum;
    @Field(type = FieldType.Double)
    private Double price;
    @Field(type = FieldType.Text)
    private String introduction;
    @Field(type = FieldType.Date)
    private Date date;
    
}

这个类上的注解见名知意,@Document 表征以这个实体类建立一个ES索引,名字为es_book_index, 类型为es_book_type,字段上的注解@ID,分别表征该字段为document的ID,然后@Field指定说明该字段的特定类型

3)然后我们新建EsBookRepository 接口继承 elasticsearchRepository,就可以集成我们日常开发的常用的增删改查的功能,其次,在该repository中,我们还可以按照JPA的命名约定写出一系列的方法而不需要操作语句,非常方便。

@Repository
public interface EsBookRepository extends ElasticsearchRepository<Book,String> {
// 根据书名字查询
    List<Book> queryByName(String name);
//    根据相应价格统计书本的数量
    long countBooksByPrice(Integer price);
//    根据名字删除
    void deleteByName(String name);

}

4)另外我们也可以使用search()方法,然后构建查询方法具体示例为:

@Service
public class BookService {

    @Autowired
    private EsBookRepository bookRepository;
//  完全匹配项查询
    public List<Book> findBookByTermQuery(Integer pageNum){
        TermQueryBuilder termQuery = QueryBuilders.termQuery("pageNum",pageNum);
        Iterable<Book> bookIterable = bookRepository.search(termQuery);
        Iterator<Book> iterator = bookIterable.iterator();
//      遍历该迭代器,取出相应结果
        List<Book> books = new ArrayList<>();
        while(iterator.hasNext()){
            books.add(iterator.next());
        }
        return books;
    }

//    模糊匹配查询
    public List<Book> findBooksLikeByMatchQuery(String word){
        MatchQueryBuilder matchQueryBuilder = QueryBuilders.matchQuery("introduction", word);
        Iterable<Book> bookIterable = bookRepository.search(matchQueryBuilder);
        Iterator<Book> iterator = bookIterable.iterator();
//      遍历该迭代器,取出相应结果
        List<Book> books = new ArrayList<>();
        while(iterator.hasNext()){
            books.add(iterator.next());
        }
        return books;
    }
//    范围查询
public List<Book> findBooksLikeByRangeQuery(Integer minPageNum,Integer maxPageNum){
    RangeQueryBuilder rangeQueryBuilder = QueryBuilders.rangeQuery("pageNum").gte(minPageNum).lte(maxPageNum);
    Iterable<Book> bookIterable = bookRepository.search(rangeQueryBuilder);
    Iterator<Book> iterator = bookIterable.iterator();
//      遍历该迭代器,取出相应结果
    List<Book> books = new ArrayList<>();
    while(iterator.hasNext()){
        books.add(iterator.next());
    }
    return books;
}

5)最后我们建立controller层,模拟向该es_book_index中插入一些数据,然后使用之前构建的查询方法都能得到相应的结果

@RestController
@RequestMapping(value = "/testBookEs")
@Api(description = "ES book实体类测试")
public class TestBookEsController {
    @Autowired
    private EsBookRepository bookRepository;
    @Autowired
    private BookService bookService;
    @ApiOperation(value = "批量保存book数据")
    @RequestMapping(value = "/batchSave", method = RequestMethod.PUT)
    public String testSaveBook(@RequestParam Integer n) {
        Random random = new Random();
        String[] names = {"三国志", "三国演义", "三国", "红楼梦","红楼","西游记","三国演义"};
        Integer[] pageNums = {100,200,300,400,500};
        String[] introductions = {"这是一本很好的故事","这里面有非常动人的故事","孙悟空三大白骨精"};
        Double[] prices = {38.6,35.8,50.9,40.7};
        Date date = new Date();
        Date[] dates = {date, DateUtil.getOneDayOnset(-2,date), DateUtil.getOneDayOnset(1,date),DateUtil.getOneDayOnset(2,date)};
        for (int i = 0; i < n; i++) {
            Book b = new Book();
            String id = UUID.randomUUID().toString().replace("_","").substring(0,10);
            b.setId(id);
            b.setName(names[random.nextInt(names.length)]);
            b.setPageNum(pageNums[random.nextInt(pageNums.length)]);
            b.setPrice(prices[random.nextInt(prices.length)]);
            b.setIntroduction(introductions[random.nextInt(introductions.length)]);
            b.setCreateTime(dates[random.nextInt(dates.length)]);
            bookRepository.save(b);
        }
        return "ok";
    }
    @ApiOperation(value = "单项查询")
    @RequestMapping(value = "/findBookByTermQuery", method = RequestMethod.GET)
    public  List<Book> findBookByTermQuery(@RequestParam Integer pageNum){
        List<Book> bookByTermQuery = bookService.findBookByTermQuery(pageNum);
        return bookByTermQuery;
    }
    @ApiOperation(value = "模糊查询")
    @RequestMapping(value = "/findBooksLikeByMatchQuery", method = RequestMethod.GET)
    public  List<Book> findBooksLikeByMatchQuery(@RequestParam String word){
        List<Book> books = bookService.findBooksLikeByMatchQuery(word);
        return books;
    }
    @ApiOperation(value = "范围查询")
    @RequestMapping(value = "/findBooksLikeByRangeQuery", method = RequestMethod.GET)
    public  List<Book> findBooksLikeByRangeQuery(@RequestParam Integer min, @RequestParam Integer max){
        List<Book> books = bookService.findBooksLikeByRangeQuery(min,max);
        return books;
    }
    @ApiOperation(value = "JPA-method-根据价格查询")
    @RequestMapping(value = "/countBooksByPrice", method = RequestMethod.GET)
    public long countBooksByPrice(@RequestParam Double price){
        long count = bookRepository.countBooksByPrice(price);
        return count;
    }
    @ApiOperation(value = "JPA-method-根据名字查询")
    @RequestMapping(value = "/queryByName", method = RequestMethod.GET)
    public  List<Book> queryByName(@RequestParam String name){
        List<Book> books = bookRepository.queryByName(name);
        return books;
    }
    @ApiOperation(value = "JPA-method-根据名字删除")
    @RequestMapping(value = "/deleteByName", method = RequestMethod.DELETE)
    public void deleteByName(@RequestParam String name){
        bookRepository.deleteByName(name);
    }
}

三、小结

本篇主要简单介绍了如何在springboot项目中使用ES这款强大的搜索引擎,并做了增删改查的示例,对一些常用简单的方法统计等有涉及到。ES的深入分析后续将会进一步介绍,包括ES提供的强大搜索统计聚合等功能后续将进一步探讨。

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值