有人知道为什么包含的方法在类方法中不起作用吗?
class MyClass
include ActionView::Helpers::NumberHelper
def test
puts "Uploading #{number_to_human_size 123}"
end
def self.test
puts "Uploading #{number_to_human_size 123}"
end
end
ree-1.8.7-2011.03 :004 > MyClass.new.test
Uploading 123 Bytes
=> nil
ree-1.8.7-2011.03 :005 > MyClass.test
NoMethodError: undefined method `number_to_human_size' for MyClass:Class
from /path/to/my/code.rb:9:in `test'
from (irb):5
ree-1.8.7-2011.03 :006 >
答案 0 :(得分:11)
对于想要在类级别lib或模型中使用某些自定义帮助程序的人来说,有时包含所有帮助程序是不值得的。相反,直接调用它:
class MyClass
def test
::ApplicationController.helpers.number_to_human_size(42)
end
end
(取自http://makandracards.com/makandra/1307-how-to-use-helper-methods-inside-a-model)
答案 1 :(得分:7)
我遇到了同样的问题。这就是我如何解决它,
helper = Object.new.extend(ActionView::Helpers::NumberHelper)
helper.number_to_human_size(1000000)
感谢RailsForum。
答案 2 :(得分:6)
在没有看到帮助程序代码的情况下很难判断,但是include
会将该模块中的所有方法插入到您包含的类的实例中。 extend
用于将方法带入类。因此,如果您只是在NumberHelper中定义了方法,那么这些方法将放在MyClass的所有实例上,而不是类。
许多Rails扩展的工作方式是使用已整合到ActiveSupport :: Concern中的技术。 Here是一个很好的概述。
基本上,在模块中扩展ActiveSupport :: Concern将允许您在名为ClassMethods和InstanceMethods的子模块中指定要将哪些函数添加到包含模块的类和实例中。例如:
module Foo
extend ActiveSupport::Concern
module ClassMethods
def bar
puts "I'm a Bar!"
end
end
module InstanceMethods
def baz
puts "I'm a Baz!"
end
end
end
class Quox
include Foo
end
Quox.bar
=> "I'm a Bar"
Quox.new.baz
=> "I'm a Baz"
我之前使用过这个来做类似定义ClassMethods中的bar函数,然后通过定义一个只调用this.class.bar的同名的bar方法使它可用于实例,使它可以从两个调用。 ActiveSupport :: Concern还有很多其他有用的东西,比如允许你定义在包含模块时回调的块。
现在,这发生在这里特别是因为你include
你的助手,这可能表明这个功能比助手更通用 - 助手只会自动包含在视图中,因为它们仅用于帮助查看。如果您想在视图中使用帮助器,可以使用类中的helper_method
宏来使该方法对您的视图可见,或者更好的是,如上所述制作模块,而不是将其视为帮助器,但是使用include将它混合到你想要使用它的类中。我想我会走那条路 - 没有什么说你不能在NumberHelper中创建一个HumanReadableNumber模块和include
来制作它它可以在您的视图中轻松使用。
答案 3 :(得分:0)
我面临着同样的问题。就我而言,将df1 = df.drop_duplicates(['nameid_index', 'projectid_index']).merge(df_copy)
替换为include
即可使其工作。
extend