【问题标题】:Can't extend core Class无法扩展核心类
【发布时间】:2013-08-14 11:29:32
【问题描述】:

我正在尝试扩展核心类,但不知道为什么在通过 Rails 4 控制台调用时会失败:

# config/application.rb
config.autoload_paths += Dir["#{config.root}/lib/**/"]

# lib/core_ext/string.rb
class String
  def test
    self + " some test"
  end
end

# lib/core_ext/array.rb
class Array
  def mean
    sum / size if sum && size
  end
end

# lib/core_ext/test.rb
class Test
  def test
    "some test"
  end
end

Rails 控制台输出:

1] pry(main)> test = Test.new
#<Test:0x007ff63971b588>
[2] pry(main)> test.test
"some test"
[3] pry(main)> "string".test
NoMethodError: private method `test' called for "string":String
from (pry):3:in `__pry__'
[4] pry(main)> [1,2,3].mean
NoMethodError: undefined method `mean' for [1, 2, 3]:Array
from (pry):4:in `__pry__'

【问题讨论】:

标签: ruby-on-rails ruby


【解决方案1】:

您应该添加以下行以有效地将文件要求到您的项目中

Dir[File.join(Rails.root, "lib", "core_ext", "*.rb")].each {|l| require l }

取自In Ruby on Rails, to extend the String class, where should the code be put in?

【讨论】:

  • 这根本不适合我。我不知道为什么。这条线到底应该去哪里?我有完全相同的配置。
  • @Ariel 我没有亲自尝试过,但我猜想调用 Bundler#require 的 application.rb 周围(下)将是一个不错的区域。
【解决方案2】:

我会添加以下内容:

# In config/initializers/require.rb:
require "core_ext/string" 
require "core_ext/array" 
require "core_ext/test"

并且不要修改 config/application.rb 的 autoload_paths,它不会急切加载您的扩展。如果模块或类已经加载到其他地方,它不会扩展它。如需参考,请查看这些 SO question1question2

【讨论】:

    【解决方案3】:

    请注意,如果您对静态方法(例如 String.test)感兴趣,您可以将其声明为 def self.test

    【讨论】:

      猜你喜欢
      • 2023-03-12
      • 1970-01-01
      • 2015-12-03
      • 2012-09-26
      • 1970-01-01
      • 2013-07-01
      • 2015-07-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多