Ruby on Rails关联同名属性表的查询实现及报错解决
问题解决:关联表的条件匹配查询实现
数据表结构
- type表:
id, name - section表(
type_id为关联type表id的外键):id, type_id, name, color
查询需求
传入参数@name时:
- 若
@name匹配section表的name字段,返回对应的section记录 - 若
@name匹配type表的name字段,返回该type下的所有section记录
示例数据
type表数据
id= 1, name: oneType id= 2, name: twoType id= 3, name: threeType
section表数据
id=1, type_id:1, name: section1 id=2, type_id:2, name: section2 id=3, type_id:2, name: section3
预期结果
- 当查询值为
'two'时,返回:id=2, type_id:2, name: section2 id=3, type_id:2, name: section3 - 当查询值为
'sect'时,返回所有section记录:id=1, type_id:1, name: section1 id=2, type_id:2, name: section2 id=3, type_id:2, name: section3 - 当查询值为
'section2'时,返回:id=2, type_id:2, name: section2
尝试代码及报错
尝试代码:
Section.joins(:type).where("name = ?", @name).select("id, name")
报错信息:
TypeError: can't quote Array
解决方案
报错原因
SQL条件中的name字段存在歧义——type和section表都有name字段,ActiveRecord无法确定引用哪个表的字段,导致解析失败;同时代码逻辑未覆盖需求中的两种匹配场景。
正确实现代码
模糊匹配版本(对应示例中'two'、'sect'的场景)
Section.joins(:type) .where("sections.name LIKE ? OR types.name LIKE ?", "%#{@name}%", "%#{@name}%") .select("sections.id, sections.type_id, sections.name, sections.color")
精确匹配版本(对应示例中'section2'的场景)
Section.joins(:type) .where("sections.name = ? OR types.name = ?", @name, @name) .select("sections.id, sections.type_id, sections.name, sections.color")
代码说明
- 明确指定
sections.name和types.name,消除字段歧义,解决报错问题 - 通过
OR逻辑同时覆盖两种匹配场景:section自身名称匹配、所属type的名称匹配 select语句明确指定返回section表的字段,避免因关联表存在同名字段导致的结果混乱
内容的提问来源于stack exchange,提问作者tunosi st
相关产品推荐
相关产品推荐

