SpringBoot+Lucene案例介绍
一、案例介绍
- 模拟一个商品的站内搜索系统(类似淘宝的站内搜索);
- 商品详情保存在mysql数据库的product表中,使用mybatis框架;
- 站内查询使用Lucene创建索引,进行全文检索;
- 增、删、改,商品需要对Lucene索引修改,搜索也要达到近实时的效果。
对于数据库的操作和配置就不在本文中体现,主要讲解与Lucene的整合。
一、引入lucene的依赖
向pom文件中引入依赖
1 | <!--核心包--> |
三、配置初始化Bean类
初始化bean类需要知道的几点:
1.实例化 IndexWriter,IndexSearcher 都需要去加载索引文件夹,实例化是是非常消耗资源的,所以我们希望只实例化一次交给spring管理。
2.IndexSearcher 我们一般通过SearcherManager管理,因为IndexSearcher 如果初始化的时候加载了索引文件夹,那么
后面添加、删除、修改的索引都不能通过IndexSearcher 查出来,因为它没有与索引库实时同步,只是第一次有加载。
3.ControlledRealTimeReopenThread创建一个守护线程,如果没有主线程这个也会消失,这个线程作用就是定期更新让SearchManager管理的search能获得最新的索引库,下面是每25S执行一次。
4.要注意引入的lucene版本,不同的版本用法也不同,许多api都有改变。
1 | @Configuration |
四、创建需要的Bean类
创建商品Bean
1 | /** |
创建一个带参数查询分页通用类PageQuery类
1 | /** |
五、创建索引库
1.项目启动后执行同步数据库方法
项目启动后,更新索引库中所有的索引。
1 | /** |
2.从数据库中查询出所有的商品
从数据库中查找出所有的商品
1 | @Override |
3.创建这些商品的索引
把List中的商品创建索引
我们知道,mysql对每个字段都定义了字段类型,然后根据类型保存相应的值。
那么lucene的存储对象是以document为存储单元,对象中相关的属性值则存放到Field(域)中;
Field类的常用类型
Field类 | 数据类型 | 是否分词 | index是否索引 | Stored是否存储 | 说明 |
---|---|---|---|---|---|
StringField | 字符串 | N | Y | Y/N | 构建一个字符串的Field,但不会进行分词,将整串字符串存入索引中,适合存储固定(id,身份证号,订单号等) |
FloatPoint LongPoint DoublePoint |
数值型 | Y | Y | N | 这个Field用来构建一个float数字型Field,进行分词和索引,比如(价格) |
StoredField | 重载方法,,支持多种类型 | N | N | Y | 这个Field用来构建不同类型Field,不分析,不索引,但要Field存储在文档中 |
TextField | 字符串或者流 | Y | Y | Y/N | 一般此对字段需要进行检索查询 |
上面是一些常用的数据类型, 6.0后的版本,数值型建立索引的字段都更改为Point结尾,FloatPoint,LongPoint,DoublePoint等,对于浮点型的docvalue是对应的DocValuesField,整型为NumericDocValuesField,FloatDocValuesField等都为NumericDocValuesField的实现类。
commit()的用法
commit()方法,indexWriter.addDocuments(docs);只是将文档放在内存中,并没有放入索引库,没有commit()的文档,我从索引库中是查询不出来的;
许多博客代码中,都没有进行commit(),但仍然能查出来,因为每次插入,他都把IndexWriter关闭.close(),Lucene关闭前,都会把在内存的文档,提交到索引库中,索引能查出来,在spring中IndexWriter是单例的,不关闭,所以每次对索引都更改时,都需要进行commit()操作;
这样设计的目的,和数据库的事务类似,可以进行回滚,调用rollback()方法进行回滚。
1 | @Autowired |
六、多条件查询
按条件查询,分页查询都在下面代码中体现出来了,有什么不明白的可以单独查询资料,下面的匹配查询已经比较复杂了.
searcherManager.maybeRefresh()方法,刷新searcherManager中的searcher,获取到最新的IndexSearcher。
1 | @Autowired |
七、删除更新索引
1 | @Override |
八、补全Spring中剩余代码
Controller层
1 | @RestController |
1 | public class ResultUtil<T> { |
1 | public class ResultBean<T> implements Serializable { |
1 | public enum ResultEnum { |