Spring Boot + Elasticsearch 实现索引的日常维护

全文检索的应用越来越广泛,几乎成了互联网应用的标配,商品搜索、日志分析、历史数据归档等等,各种场景都会涉及到大批量的数据,在全文检索方面,方案无外乎Lucene、Solr、Elasticsearch三种应用的较为广泛。es、solr的底层都依托于Lucene,但es比solr学习成本更低,由于其提供的RESTful API简单快捷,对互联网应用开发而言更是如虎添翼。

下面结合以实际案例,通过Java API的形式操作es数据集。

框架选型基础是Spring Boot + Spring-data-elasticsearch + elasticsearch。

使用ElasticsearchRepository的形式来连接、维护ES数据集,ElasticsearchRepository中提供了简单的操作索引数据的方法集合,继承自ElasticsearchCrudRepository,涵盖了CRUD、排序、分页等常见的基本操作功能。

 
  1. @NoRepositoryBean  

  2. public interface ElasticsearchRepository<T, ID extends Serializable> extends ElasticsearchCrudRepository<T, ID> {  

  3.    <S extends T> S index(S var1);  

  4.  

  5.    Iterable<T> search(QueryBuilder var1);  

  6.  

  7.    Page<T> search(QueryBuilder var1, Pageable var2);  

  8.  

  9.    Page<T> search(SearchQuery var1);  

  10.  

  11.    Page<T> searchSimilar(T var1, String[] var2, Pageable var3);  

  12.  

  13.    void refresh();  

  14.  

  15.    Class<T> getEntityClass();  

  16. }  

从基本的pom配置开始

 
  1. xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

  2.    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">

  3.    4.0.0

  4.    com.esp.index.data

  5.    esp-cube

  6.    0.0.1-SNAPSHOT

  7.  

  8.    

  9.        org.springframework.boot

  10.        spring-boot-starter-parent

  11.        1.5.2.RELEASE

  12.         />

  13.    

  14.  

  15.    

  16.        UTF-8

  17.        UTF-8

  18.        1.7

  19.    

  20.  

  21.    

  22.        

  23.            org.springframework.boot

  24.            spring-boot-starter-jdbc

  25.            

  26.                

  27.                    org.apache.tomcat

  28.                    tomcat-jdbc

  29.                

  30.            

  31.        

  32.        

  33.            org.springframework.boot

  34.            spring-boot-starter-data-elasticsearch

  35.        

  36.        

  37.            org.springframework.boot

  38.            spring-boot-starter-web

  39.            

  40.                

  41.                    log4j-over-slf4j

  42.                    org.slf4j

  43.                

  44.            

  45.        

  46.        

  47.            org.springframework.boot

  48.            spring-boot-starter

  49.            

  50.                

  51.                    org.springframework.boot

  52.                    spring-boot-starter-logging

  53.                

  54.            

  55.        

  56.        

  57.            org.springframework.boot

  58.            spring-boot-starter-test

  59.            test

  60.        

  61.        

  62.            org.springframework.boot

  63.            spring-boot-starter-log4j

  64.            1.3.1.RELEASE

  65.        

  66.    

  67.  

  68.    

  69.        esp-cube

  70.        

  71.            

  72.                org.springframework.boot

  73.                spring-boot-maven-plugin

  74.            

  75.        

  76.    

编写自己的Resository操作类

 
  1. public interface ArticleSearchRepository extends ElasticsearchRepository<Article, Long>{

  2.    List<Article> findByAbstractsAndContent(String abstracts, String content);

  3. }

其中Article为是与elasticsearch连接的实体类,类似于PO的概念,其中指定的索引名称、类型名称、及分片、副本数量等要素。

 
  1. @Data

  2. @Document(indexName = "article_index", type = "article", shards = 5, replicas = 1, indexStoreType = "fs", refreshInterval = "-1")

  3. public class Article implements Serializable {

  4.  

  5.    /**

  6.     * serialVersionUID:

  7.     *

  8.     * @since JDK 1.6

  9.     */

  10.    private static final long serialVersionUID = 1L;

  11.  

  12.    @Id

  13.    private Long id;

  14.    /** 标题 */

  15.    private String title;

  16.    /** 摘要 */

  17.    private String abstracts;

  18.    /** 内容 */

  19.    private String content;

  20.    /** 发表时间 */

  21.    @Field(format = DateFormat.date_time, index = FieldIndex.no, store = true, type = FieldType.Object)

  22.    private Date postTime;

  23.    /** 点击率 */

  24.    private Long clickCount;

  25. }

我们需要定义域的实体和一个Spring data的基本的CRUD支持库类。用id注释定义标识符字段,如果你没有指定ID字段,Elasticsearch不能索引你的文件。同时需要指定索引名称类型,@Document注解也有助于我们设置分片和副本数量。

接口类

 
  1. public interface ArticleService {

  2.  

  3.    /**

  4.     * saveArticle: 写入

  5.     *

  6.     * @author guooo Date:2017年9月27日下午3:20:06

  7.     * @param article

  8.     * @return

  9.     * @since JDK 1.6

  10.     */

  11.    long saveArticle(Article article);

  12.  

  13.    /**

  14.     * deleteArticle: 删除,并未真正删除,只是查询不到

  15.     *

  16.     * @author guooo Date:2017年9月27日下午3:20:08

  17.     * @param id

  18.     * @since JDK 1.6

  19.     */

  20.    void deleteArticle(long id);

  21.  

  22.    /**

  23.     * findArticle:

  24.     *

  25.     * @author guooo Date:2017年9月27日下午3:20:10

  26.     * @param id

  27.     * @return

  28.     * @since JDK 1.6

  29.     */

  30.    Article findArticle(long id);

  31.  

  32.    /**

  33.     * findArticlePageable:

  34.     *

  35.     * @author guooo Date:2017年9月27日下午3:20:13

  36.     * @return

  37.     * @since JDK 1.6

  38.     */

  39.    List<Article> findArticlePageable();

  40.  

  41.    /**

  42.     * findArticleAll:

  43.     *

  44.     * @author guooo Date:2017年9月27日下午3:20:15

  45.     * @return

  46.     * @since JDK 1.6

  47.     */

  48.    List<Article> findArticleAll();

  49.  

  50.    /**

  51.     * findArticleSort:

  52.     *

  53.     * @author guooo Date:2017年9月27日下午3:20:18

  54.     * @return

  55.     * @since JDK 1.6

  56.     */

  57.    List<Article> findArticleSort();

  58.  

  59.    /**

  60.     * search:

  61.     *

  62.     * @author guooo Date:2017年9月27日下午3:20:22

  63.     * @param content

  64.     * @return

  65.     * @since JDK 1.6

  66.     */

  67.    List<Article> search(String content);

  68.  

  69.    /**

  70.     * update: es没有修改操作,结合save操作完成

  71.     *

  72.     * @author guooo Date:2017年9月27日下午3:20:25

  73.     * @param id

  74.     * @return

  75.     * @since JDK 1.6

  76.     */

  77.    long update(long id);

  78. }

接口实现

 
  1. @Service

  2. public class ArticleServiceImpl implements ArticleService {

  3.  

  4.    final int page = 0;

  5.    final int size = 10;

  6.  

  7.    /* 搜索模式 */

  8.    String SCORE_MODE_SUM = "sum"; // 权重分求和模式

  9.    Float MIN_SCORE = 10.0F; // 由于无相关性的分值默认为 1 ,设置权重分最小值为 10

  10.  

  11.    Pageable pageable = new PageRequest(page, size);

  12.  

  13.    @Autowired

  14.    ArticleSearchRepository repository;

  15.  

  16.    @Override

  17.    public long saveArticle(Article article) {

  18.        Article result = repository.save(article);

  19.        return result.getId();

  20.    }

  21.  

  22.    @Override

  23.    public void deleteArticle(long id) {

  24.        repository.delete(id);

  25.    }

  26.  

  27.    @Override

  28.    public Article findArticle(long id) {

  29.        return repository.findOne(id);

  30.    }

  31.  

  32.    @Override

  33.    public List<Article> findArticlePageable() {

  34.  

  35.        return repository.findAll(pageable).getContent();

  36.    }

  37.  

  38.    @Override

  39.    public List<Article> findArticleAll() {

  40.        Iterable<Article> iterables = repository.findAll();

  41.        List<Article> articles = new ArrayList<>();

  42.        for (Article article : iterables) {

  43.            articles.add(article);

  44.        }

  45.        return articles;

  46.    }

  47.  

  48.    @Override

  49.    public List<Article> findArticleSort() {

  50.        List<Order> orders = new ArrayList<>();

  51.        Order order = new Order(Direction.ASC, "clickCount");

  52.        orders.add(order);

  53.        Sort sort = new Sort(orders);

  54.        Iterable<Article> iterables = repository.findAll(sort);

  55.        List<Article> articles = new ArrayList<>();

  56.        for (Article article : iterables) {

  57.            articles.add(article);

  58.        }

  59.        return articles;

  60.    }

  61.  

  62.    @Override

  63.    public List<Article> search(String content) {

  64.        return repository.findByAbstractsAndContent(content, content);

  65.    }

  66.  

  67.    @Override

  68.    public long update(long id) {

  69.        Article article = repository.findOne(id);

  70.        article.setTitle("test");

  71.        Article retun = repository.save(article);

  72.        System.out.println(retun.getId()+"更新的数据");

  73.        return retun.getId();

  74.    }

  75. }

是不是与JPA、hibernate操作数据集的手法很类似?

controller方法类:

 
  1. @RestController

  2. @RequestMapping(value = "/article")

  3. public class APIArticleController {

  4.  

  5.    @Autowired

  6.    ArticleService articleService;

  7.  

  8.  

  9.    @RequestMapping(value = "save", method = RequestMethod.POST)

  10.    public long save() {

  11.        for (int i = 10000; i < 12000; i++) {

  12.            Article article = new Article();

  13.            article.setClickCount(Long.valueOf(i + RandomUtils.nextInt(23, i)));

  14.            article.setAbstracts("我的一个测试" + i);

  15.            article.setContent(i + "这是第一个测试的内容@spring-data-elasticsearch");

  16.            article.setPostTime(new Date());

  17.            article.setId(Long.valueOf(RandomUtils.nextLong(i, i)));

  18.            long _id = articleService.saveArticle(article);

  19.            System.out.println(_id);

  20.        }

  21.        return 23;

  22.    }

  23.  

  24.    @RequestMapping(value = "delete", method = RequestMethod.POST)

  25.    public void deleteArticle(long id) {

  26.        articleService.deleteArticle(id);

  27.    }

  28.  

  29.    @RequestMapping(value = "findOne", method = RequestMethod.POST)

  30.    public Article findArticle(long id) {

  31.        return articleService.findArticle(id);

  32.    }

  33.  

  34.    @RequestMapping(value = "findArticlePageable", method = RequestMethod.POST)

  35.    public List<Article> findArticlePageable() {

  36.        return articleService.findArticlePageable();

  37.    }

  38.  

  39.    @RequestMapping(value = "findArticleAll", method = RequestMethod.POST)

  40.    public List<Article> findArticleAll() {

  41.        return articleService.findArticleAll();

  42.    }

  43.  

  44.    @RequestMapping(value = "findArticleSort", method = RequestMethod.POST)

  45.    public List<Article> findArticleSort() {

  46.        return articleService.findArticleSort();

  47.    }

  48.  

  49.    @RequestMapping(value = "search", method = RequestMethod.POST)

  50.    public List<Article> search(String content) {

  51.        return articleService.search(content);

  52.    }

  53.  

  54.    @RequestMapping(value = "update", method = RequestMethod.POST)

  55.    public long update(long id) {

  56.        return articleService.update(id);

  57.    }

  58. }

Spring Boot的启动类及配置项,这里略过,项目启动后,可能过controller暴露出来的方法进行Article数据索引的CRUD操作

 

  • 程序员,保护你的好奇心和求知欲

  • 程序员的2017年书单整理

  • 你是『眼高手低』的程序员吗

  • 怎么定位自己在团队里的角色

  • 软件生命周期与技术人的职业周期

欢迎加入我的星球

Spring Boot + Elasticsearch 实现索引的日常维护_第1张图片

 

 

你可能感兴趣的:(spring,boot,elasticsearch,elasticsearch)