Rails 4.1.16
Ruby 2.2.7
我有这个ActiveRecord模型:
class Something::Type < ActiveRecord::Base
参考这样的模型时:
Something::Type.find_by_whatever("test")
我收到以下错误:
NoMethodError: undefined method `find_by_whatever' for ActiveRecord::AttributeMethods::Serialization::Type:Class
[我了解Ruby常量已分解,因此Type
作为其自己的常量存在,并且自动加载器首先找到ActiveRecord::AttributeMethods::Serialization::Type
。
但是,以“绝对”方式引用名称空间(以冒号作为前缀)应该可以解决此问题,但是结果是相同的。有什么想法吗?
::Something::Type.find_by_whatever("test")
NoMethodError: undefined method `find_by_whatever' for ActiveRecord::AttributeMethods::Serialization::Type:Class
使用范围结果运算符定义类时的问题是,模块嵌套已解析到定义点(使用module关键字的点)。如果您查看模块嵌套:
class Something::Type < ActiveRecord::Base
puts Module.nesting.inpsect # [Something::Type]
end
该类甚至没有真正嵌套在Something模块中。这将给您一个非常令人惊讶的不断查找:
module Something
FOO = "test"
end
class Something::Type
puts Foo # gives a uninitialized constant error since its not looking in the Something module
end
相反,您应该始终使用显式嵌套声明命名空间的类:
module Something
class Type
puts Module.nesting.inspect # [Something::Type, Something]
puts Foo # test
end
end
这将为模块嵌套[Something::Type, Something]
,这意味着它将在相同的Something命名空间中正确查找常量。
[这是旧的经典自动装带器依赖于monkeypatching Module#const_missing
趋向于掩盖的东西。 Zeitwork并没有做到这一点。