在 rails 中加入没有关系的表
joins on tables without relation in rails
无法在没有关系的表上使用 joins
的解决方法是什么?
例如:
class Student
end
class Lesson
end
Student 和 Lesson 之间没有显式关联,但是,在 DB 中,我们有隐式关联:students.lesson_id 和 lessons.id。
使用纯 SQL 可以连接这两个表,但是,使用 rails 提供的 joins
像这样:
Student.joins(:lesson).where('student.lesson_id=lesson.id')
会抛出"Association named 'lesson' was not found on Student; perhaps you misspelled it?"
我正在寻找符合以下要求的解决方法:
- 为了提高效率,使用RDBMS查询会比较理想。 (Rails sort_by, find etc 都没有)
- 为了提高可读性,raw SQL并不理想。
有什么解决办法吗?谢谢!
活动记录方法 .joins
已经加入外键。无需在 where 语句中再次指定它。您可以使用 where
来过滤您收到的结果。
:lesson
in joins(:lesson)
必须是 Student
模型中定义的关系的名称:
class Student < ApplicationRecord
belongs_to :lesson
end
然后您可以将查询重写为:
Student.joins(:lesson).all
但这会导致 N+1 个查询,以防您需要访问 Lesson
:
students = Student.joins(:lesson).all
lesson_name = students.first.lesson.name
为避免这种情况,请改用 includes
:
Student.includes(:lesson).all
您可以(应该)将 counter-part 关系添加到 Lesson
:
class Lesson < ApplicationRecord
has_many :students
end
顺便说一句,您可以在连接中使用字符串:
Student.joins('join lessons on students.lesson_id = lessons.id')
无法在没有关系的表上使用 joins
的解决方法是什么?
例如:
class Student
end
class Lesson
end
Student 和 Lesson 之间没有显式关联,但是,在 DB 中,我们有隐式关联:students.lesson_id 和 lessons.id。
使用纯 SQL 可以连接这两个表,但是,使用 rails 提供的 joins
像这样:
Student.joins(:lesson).where('student.lesson_id=lesson.id')
会抛出"Association named 'lesson' was not found on Student; perhaps you misspelled it?"
我正在寻找符合以下要求的解决方法:
- 为了提高效率,使用RDBMS查询会比较理想。 (Rails sort_by, find etc 都没有)
- 为了提高可读性,raw SQL并不理想。
有什么解决办法吗?谢谢!
活动记录方法 .joins
已经加入外键。无需在 where 语句中再次指定它。您可以使用 where
来过滤您收到的结果。
:lesson
in joins(:lesson)
必须是 Student
模型中定义的关系的名称:
class Student < ApplicationRecord
belongs_to :lesson
end
然后您可以将查询重写为:
Student.joins(:lesson).all
但这会导致 N+1 个查询,以防您需要访问 Lesson
:
students = Student.joins(:lesson).all
lesson_name = students.first.lesson.name
为避免这种情况,请改用 includes
:
Student.includes(:lesson).all
您可以(应该)将 counter-part 关系添加到 Lesson
:
class Lesson < ApplicationRecord
has_many :students
end
顺便说一句,您可以在连接中使用字符串:
Student.joins('join lessons on students.lesson_id = lessons.id')