Rails使用单例类语法在类方法中使用相同名称自动加载类

时间:2013-03-04 12:56:33

标签: ruby-on-rails ruby autoload

假设我在Rails应用程序中的不同模块(全局命名空间/无命名空间和“Foo”)中有两个具有相同名称的类(“Bar”)。 这两个类分别位于“app / models / bar.rb”或“app / models / foo / bar.rb”中,因此可以通过rails自动加载。

# "app/models/foo/bar.rb"
module Foo
  class Bar
    def self.some_method
    end
  end
end

# "app/models/bar.rb"
class Bar
end

我在Foo命名空间中有另一个类,它在类方法中使用Bar类。

module Foo
  class Qux
    class << self
      def something
        Bar.some_method # This raises a NoMethod error because
                        # it uses the Bar defined in the global namespace
                        # and not the one in Foo
      end
    end
  end
end

Rails自动加载尝试使用当前类name加载Bar,在单例类中为nil,默认为“Object”。

klass_name = name.presence || "Object"  # from active_support/dependencies.rb

这会导致Rails从“app / models / bar.rb”而不是“app / models / foo / bar.rb”加载Bar。 如果我使用Qux.something定义def self.something,则.name为“Foo :: Qux”而不是nil,并且自动加载功能正常。

我现在看到3个选项可以解决这个问题:

1)重命名Bar个班级之一 2)到处使用self.语法 3)命名空间BarFoo::Bar明确无处不在

我不喜欢这些选项,因为:

1)Bar只是最适合的名称 2)class << self本身完全没问题并被大多数红宝石开发者使用,所以下一个可怜的家伙很快再次遇到同样问题的机会很高 3)与2)相同,它并没有真正解决潜在的“问题”,并且有人将在未来浪费一些时间来弄清楚为什么他的代码不能按预期工作。

你能想到还有另一种更好的选择吗?

0 个答案:

没有答案