搜索功能-实现思路
四种搜索词
搜索热词
热词是一种由运维提前维护好的搜索词,会展示在搜索界面的搜索框下,用户可以点击直接搜索该热词的相关结果。
运维维护好后,会双写到DB
和Redis
。接口查询时,会保存到本地缓存,有效期5分钟,所以维护了一个热词,需要五分钟后才能看到。
热词会被视为keyword
。
联想词
联想词是一种由运维维护的,用以提供用户搜索引导的搜索词。在用户输入部分内容后,会展示包含输入内容的联想词。
运维维护好后,会双写到DB
和ES
。由于ES
本身有一秒钟的写入缓存,故维护好后需要一秒钟后才能使用。
联想词会被视为keyword
。
特定词
特定词是运维维护的一种特殊的搜索词。当用户进行搜素操作时,会在查询商品前,优先查询特定词,特定次会返回一个超链接。前段会自动跳转到该超链接。
联想词会被视为keyword
。
同义词
同义词是运维维护的一种用来扩展搜索的搜索词。当用户在搜索框输入的搜索词(主词),能够关联查询到维护的同义词(子词)时,那么此时查询的keyword
就变成了主词+子词。
ES 使用
索引
对于需要查询多个字段的模糊查询,可以将多个字段融合成一个查询大字段keyword
,匹配该字段。
ElasticSearch
索引的删除,会同时删除索引下的文档数据。如确认有必要删除更改已有索引,需配合ElasticSearch
的reindex
操作,进行数据备份。
对于映射的定义,是一个文档及其包含的字段如何存储和索引的过程。ElasticSearch
中有三种映射模式。
模式 | 是否需要提前定义Mapping | 新加未定义字段对Mapping的影响 | 数据写入与搜索情况 |
---|---|---|---|
动态模式 | 否 | Mappping动态调整 | 可写,可搜 |
静态模式 | 是 | 不会有变化 | 可写,未定义字段不可搜 |
严格模式 | 是 | 插入未定义字段报错 | 同上 |
推荐采用静态模式。
- 从维护角度看,我们希望保持“先定义,再操作”的数据库操作习惯。
- 只需要考虑将搜索与聚合的字段添加到mapping中,后续只是用来展示的字段不会改变索引的结构,性能比动态模式更好。
- 即使添加了未定义字段的数据,也不会报错,仅作展示用,兼容性和健壮性和比严格模式好。
搜索实现
搜索功能主要由两部分组成:搜索,筛选。
搜索功能提供对搜索词的结果查询。接口返回结果是商品列表。
筛选功能提供对搜索词的搜索结果的聚合操作,提取筛选值关键字,以供用户分类筛选查看查询结果。接口返回数据是商品列表聚合出来的筛选条件。
从业务需求来看,搜索和筛选对于同一次搜索流程来说,在查询条件上是保持统一的。即接口查询入参相同。这样才能得到相同的es
搜索结果
搜索
搜索流程
设计模式
状态模式、责任链模式、策略模式
-
状态模式:控制流程
-
责任链模式:构建
DSL
-
策略模式:选择性构建
DSL
流程
- 搜索词
keyword
搜索Keyword
逻辑deeplink
特定词搜索- 存在则返回
- 作为类别名称查询关联类别
- 不存在:设置状态为关键字搜索
- 存在:设置状态为商品编码搜索
- 填充同义词、黑名单等前置条件
- 构建公共基础排序
- 策略构建排序
- 执行搜索
- 存在:
- 筛选操作:
- 执行聚合结果解析
- 自然排序
- 根据配置的筛选值顺序排序
- 执行聚合结果解析
- 搜索操作:
- 组装搜索结果,返回
- 筛选操作:
- 不存在:
- 如果状态为关键字搜索,修改状态为商品编码搜索
- 如果状态为商品编码搜索,修改状态为关键字搜索
- 清空搜索语句,重新组装,查询结果
- 存在:
- 商品分类
categoryCode
搜索- 构建状态为关键字类别搜索
- 类别信息查询
- 黑名单标记
- 构建指定类别为入参
- 公共排序
- 策略构建排序
- 执行搜索
- 同2.5
- 营销搜索
筛选
整体逻辑与商品相同,不同的是在流程中会添加商品的聚合语句,在结果解析中会加工聚合结果,处理成前段可展示的筛选条件。
在用户点击筛选条件时,筛选条件会转化为搜索关键字。