如何将三表Inner Join SQL查询转换为Solr嵌套连接(Nested Join)查询?
前置索引Schema准备
Solr嵌套连接能力依赖层级化的嵌套文档结构,不能直接对三个独立存储的Solr核心做关联查询,需要先完成和原三表关系对齐的索引设计:
- 开启Solr嵌套文档支持,确保系统自动为所有嵌套节点生成
_root_、_nest_path_关联字段,用于层级关系识别 - 文档层级对齐原表关联逻辑:
- 顶层文档存储people表全量字段,通过
doc_type:people做类型标识,主键对应原表的people.id - 一级嵌套子文档挂载在people节点下,存储submissions表全量字段,通过
doc_type:submission做类型标识,内置person_id字段关联所属people的ID,主键对应原表的submissions.id - 二级嵌套子文档挂载在submission节点下,存储stage_transitions表全量字段,通过
doc_type:stage_transition做类型标识,主键和所属submission的ID值匹配,对应原表中submissions.id = stage_transitions.id的关联规则
- 顶层文档存储people表全量字段,通过
等价查询语法
可直接复用的Solr查询参数,和原SQL语义完全对齐:
# 核心检索条件 q={!parent which='doc_type:people'} {!parent which='doc_type:submission'} stage:lead # 返回字段配置,对应原SQL的select *全字段返回 fl=*,[child parentFilter='doc_type:people' childFilter='doc_type:submission' fl=*,[child parentFilter='doc_type:submission' childFilter='doc_type:stage_transition' fl=*]]
语义对齐校验
- 筛选条件对齐:最底层的
stage:lead检索条件,完全等价于原SQL中stage_transitions.stage = 'lead'的过滤规则,仅保留满足该条件的stage_transition节点 - 第一层关联对齐:通过内层
{!parent which='doc_type:submission'}回溯,找到所有满足筛选条件的stage_transition节点对应的直接父submission节点,等价于原SQL中submissions.id = stage_transitions.id的Inner Join关联,无有效stage_transition匹配的submission节点不会进入结果集 - 第二层关联对齐:通过外层
{!parent which='doc_type:people'}回溯,找到所有匹配到的submission节点对应的直接父people节点,等价于原SQL中people.id = submissions.person_id的Inner Join关联,无有效submission匹配的people节点不会进入结果集 - 结果范围对齐:配置的嵌套字段取回逻辑,会将people节点、其下关联的匹配submission节点、对应submission下的匹配stage_transition节点的全量字段返回,和原SQL三表Inner Join后的全字段查询结果范围完全一致
特别注意:整个查询从最内层的筛选节点向上回溯,不存在空匹配的父节点返回,完全等价于Inner Join的语义,不会出现Left Join场景下无关联子节点的父文档被返回的情况。
内容的提问来源于stack exchange,提问作者solrman
相关产品推荐
相关产品推荐

