我正在尝试使用具有命名范围的类的继承:
Class A < ActiveRecord::Base
scope :useful_scope, lambda { |value1, value2|
where(:value1 => value1, :value2 => value2)
end
end
Class B < A
set_table_name "b"
end
我遇到的问题是sql查询中的表名仍然引用A类的表:
A.useful_scope("alpha", "beta").to_sql
=> "SELECT \"a\".* FROM \"a\" WHERE \"a\".\"value1\" = 'alpha' AND \"a\".\"value2\" = 'beta'"
B.useful_scope("alpha", "beta").to_sql
=> "SELECT \"b\".* FROM \"b\" WHERE \"a\".\"value1\" = 'alpha' AND \"a\".\"value2\" = 'beta'"
请注意,WHERE 语句中的表名称仍然引用 A。我正在修改现有的 gem,并且始终对 A 类范围具有各种依赖项,因此我需要维护它的当前语法。我想在 WHERE 子句 SQL 中维护表名说明符,以确保该范围在与其他命名范围定义嵌套时表现良好。
我尝试过以下方法:
- 使用 lambda 参数作为表名称。这破坏了对仅提供当前 2 个属性的范围的其他引用的语法。
- 使用抽象类来定义范围。发生了相同的表名称绑定(bind),但使用了抽象类的类名称。
- 使用模块中定义的范围并包含该模块。发生了相同的表名绑定(bind)。
有没有一种方法可以强制在每个继承的类上评估范围,以便它不会显式映射到父类表?
最佳答案
我最终使用匿名范围来解决此问题。代码如下所示:
def self.useful_scope(value1, value2)
scoped(:conditions => { :value1 => value1, :value2 => value2 })
end
现在,这可以在父类和继承类中正确评估,并保留作用域所需的行为。
关于sql - Rails 3 中继承的命名范围映射到错误的表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5452910/