在 Rails 加入 3 个表
Join 3 tables on Rails
我有 3 张桌子:
- 播放列表 has_many:曲目
- 曲目 belongs_to:播放列表,has_many:答案
- 答案 belongs_to:跟踪
一个播放列表有一个主题(不是唯一的,几个播放列表可能有相同的主题)
答案 的状态:真或假
我想查询给定主题的真实答案。
理论上,这应该有效:
Track.joins(:answers).where(answers:{status:true}).joins(:playlist).where(playlists:{theme: myGivenTheme})
实际上,它包括 .joins(:playlist),但每当我添加 where(playlists:...) 条件时都会失败。
我已经尝试 Track.includes(:playlist),试图适应 belongs_to,但也失败了,出现以下错误消息:
Track.joins(:answers).where(answers:{status:true}).joins(:playlist).where(playlist:{name:'French'}).count
(2.1ms) SELECT COUNT(*) FROM "tracks" INNER JOIN "answers" ON "answers"."track_id" = "tracks"."id" INNER JOIN "playlists" ON "playlists"."id" = "tracks"."playlist_id" WHERE "answers"."status" = AND "playlist"."name" = [["status", true], ["name", "French"]]
ActiveRecord::StatementInvalid: PG::UndefinedTable: ERROR: missing FROM-clause entry for table "playlist"
LINE 1: ..."."playlist_id" WHERE "answers"."status" = AND "playlist"...
^
from /Users/pierre/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activerecord-6.0.2.1/lib/active_record/connection_adapters/postgresql_adapter.rb:672:in `exec_params'
Caused by PG::UndefinedTable: ERROR: missing FROM-clause entry for table "playlist"
LINE 1: ..."."playlist_id" WHERE "answers"."status" = AND "playlist"...
^
from /Users/pierre/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activerecord-6.0.2.1/lib/active_record/connection_adapters/postgresql_adapter.rb:672:in `exec_params'
我会推荐你生的sql
Track.find_by_sql('SELECT * FROM tracks t
JOIN answers a ON a.id = t.answer_id
JOIN playlist p ON p.id = t.playlist_id
WHERE status = true
AND theme = ?', myGivenTheme);
假设您使用列的约定
您可以select特定的列,轨道模型上不存在的列将作为其中的一部分添加
您也可以一次加入两个表
Tracks.joins(:answers, :playlists)
我注意到您在 where
中使用单数加入 :playlist 和复数 :playlists
我终于解决了我的问题,希望这可能对我有所帮助,因为我没有找到很多关于这个特定语法主题的文档。正确的查询,找到整个用户的正确答案 (answer.status = true),对于给定的播放列表主题,名为 myGivenTheme 和给定的用户是:
Playlist.where(theme: myGivenTheme).joins(tracks: :answers).where(answers:{status: true, user_id: self.id})
我有 3 张桌子:
- 播放列表 has_many:曲目
- 曲目 belongs_to:播放列表,has_many:答案
- 答案 belongs_to:跟踪
一个播放列表有一个主题(不是唯一的,几个播放列表可能有相同的主题) 答案 的状态:真或假
我想查询给定主题的真实答案。
理论上,这应该有效:
Track.joins(:answers).where(answers:{status:true}).joins(:playlist).where(playlists:{theme: myGivenTheme})
实际上,它包括 .joins(:playlist),但每当我添加 where(playlists:...) 条件时都会失败。 我已经尝试 Track.includes(:playlist),试图适应 belongs_to,但也失败了,出现以下错误消息:
Track.joins(:answers).where(answers:{status:true}).joins(:playlist).where(playlist:{name:'French'}).count
(2.1ms) SELECT COUNT(*) FROM "tracks" INNER JOIN "answers" ON "answers"."track_id" = "tracks"."id" INNER JOIN "playlists" ON "playlists"."id" = "tracks"."playlist_id" WHERE "answers"."status" = AND "playlist"."name" = [["status", true], ["name", "French"]]
ActiveRecord::StatementInvalid: PG::UndefinedTable: ERROR: missing FROM-clause entry for table "playlist"
LINE 1: ..."."playlist_id" WHERE "answers"."status" = AND "playlist"...
^
from /Users/pierre/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activerecord-6.0.2.1/lib/active_record/connection_adapters/postgresql_adapter.rb:672:in `exec_params'
Caused by PG::UndefinedTable: ERROR: missing FROM-clause entry for table "playlist"
LINE 1: ..."."playlist_id" WHERE "answers"."status" = AND "playlist"...
^
from /Users/pierre/.rbenv/versions/2.6.5/lib/ruby/gems/2.6.0/gems/activerecord-6.0.2.1/lib/active_record/connection_adapters/postgresql_adapter.rb:672:in `exec_params'
我会推荐你生的sql
Track.find_by_sql('SELECT * FROM tracks t
JOIN answers a ON a.id = t.answer_id
JOIN playlist p ON p.id = t.playlist_id
WHERE status = true
AND theme = ?', myGivenTheme);
假设您使用列的约定
您可以select特定的列,轨道模型上不存在的列将作为其中的一部分添加
您也可以一次加入两个表
Tracks.joins(:answers, :playlists)
我注意到您在 where
中使用单数加入 :playlist 和复数 :playlists我终于解决了我的问题,希望这可能对我有所帮助,因为我没有找到很多关于这个特定语法主题的文档。正确的查询,找到整个用户的正确答案 (answer.status = true),对于给定的播放列表主题,名为 myGivenTheme 和给定的用户是:
Playlist.where(theme: myGivenTheme).joins(tracks: :answers).where(answers:{status: true, user_id: self.id})