Rails - 范围和多对多关系
Rails - scopes and many-to-many relationships
我有一个包含电影和类型的 Rails 应用程序,其中电影 has_many 类型(喜剧、动作、戏剧等)和类型 has_many 电影。显然我有一个 join-table genres_movies,来跟踪多对多关系。
我正在使用示波器来轻松获取没有任何类型的电影 - 但我不确定相应的语法是什么。这样的东西不起作用:
scope :no_genres, -> { joins(:genres).where(genres: { id: nil}) }
(我发现关系数据库令人困惑 :)
如果您不熟悉关系数据库,那么我应该告诉您,当您进行连接时,它会选择有匹配数据的结果。因此,当您加入具有流派的电影时,结果由有电影的地方和有流派的地方组成,并且它们匹配。因此,如果一部电影没有流派,它就不会有匹配的流派,因此它不会出现在结果中。
所以你想要的是左侧 movies
和右侧 genres
的左外连接。左外部连接将确保即使是没有类型的电影也会出现在结果中。结果中 genres
table 的所有值都将使用 NULL。因此,如果您随后使用 id: nil
执行 where
,您将只获得那些没有类型的记录,因此所有没有类型的电影。
scope :no_genres, -> { left_joins(:genres).where(genres: { id: nil}) }
我有一个包含电影和类型的 Rails 应用程序,其中电影 has_many 类型(喜剧、动作、戏剧等)和类型 has_many 电影。显然我有一个 join-table genres_movies,来跟踪多对多关系。
我正在使用示波器来轻松获取没有任何类型的电影 - 但我不确定相应的语法是什么。这样的东西不起作用:
scope :no_genres, -> { joins(:genres).where(genres: { id: nil}) }
(我发现关系数据库令人困惑 :)
如果您不熟悉关系数据库,那么我应该告诉您,当您进行连接时,它会选择有匹配数据的结果。因此,当您加入具有流派的电影时,结果由有电影的地方和有流派的地方组成,并且它们匹配。因此,如果一部电影没有流派,它就不会有匹配的流派,因此它不会出现在结果中。
所以你想要的是左侧 movies
和右侧 genres
的左外连接。左外部连接将确保即使是没有类型的电影也会出现在结果中。结果中 genres
table 的所有值都将使用 NULL。因此,如果您随后使用 id: nil
执行 where
,您将只获得那些没有类型的记录,因此所有没有类型的电影。
scope :no_genres, -> { left_joins(:genres).where(genres: { id: nil}) }