我有以下模型:
class ActivityLog < ActiveRecord::Base
validates :user_id, :instance_id, :action, presence: true
validates :user_id, :instance_id, :action, numericality: true
def log
ActivityLog.create(
user_id: current_user ? current_user.id : -1,
instance_id: instance_id,
action: actions.index(action)
)
end
private
def actions
['start','stop','create','destroy']
end
end
当我从 Rails 控制台调用以下行时,出现错误:
ActivityLog.log(user_id: 1, instance_id:1, action: 'create')
# Error returned from console
NoMethodError: undefined method `log' for #<Class:0x007fb4755a26a8>
为什么我的方法调用不起作用?我在类里面定义了它,但它说它是未定义的。我错过了什么或误解了什么?谢谢。
最佳答案
创建方法log
假设您有一个类User
,并且在该类中,您定义了方法has_cell_phone
。 (该方法的内容无关紧要。)当您在类中将方法定义为 def has_cell_phone
时,可以在任何 User
对象上调用该方法。虽然 class User
本身是一个 class 对象,但您可以在直接类为 User
的对象上调用它。用正确的术语来说,您将为 User
类的实例编写一个实例方法。
您收到该错误是因为您定义的方法 log
仅适用于 ActivityLog
类的_instance。如果执行以下操作,则可以根据当前代码正确调用 log
:
activity_log = ActivityLog.create # with required params
activity_log.log
其次,您正在调用带有参数的log
,而您的方法定义不需要任何参数。 (这看起来像 def log(params)
。)
现在,您可以在此处修改现有代码。当您想调用整个 类(即类本身)的方法时,您可以在类方法定义前加上关键字self
。例如,对于 User
类,它将是 def self.create_user_with_cell_phone
。您还可以向该方法添加参数。您在“方法调用”行中提供的参数,我会将它们添加到您的类方法中,如下所示:
def self.log(instance_id, action)
# ...
end
ActivityLog.log(1, 'create')
您不需要包含 user_id
,因为根据您的逻辑,它会检查 current_user
对象是否为 true
,并且从那里开始。
创建类常量
再看你的问题,我发现你定义了一个方法actions
。还记得我说过的实例方法吗?由于 actions
似乎将始终保持不变,因此我建议您将其设为一个!为此,建议您在类中的任何方法定义之前放置以下行。
ACTIONS = ['start','stop','create','destroy']
然后,任何时候你想在 ActivityLog
类中调用 ACTIONS
时,你都可以执行以下操作:ACTIONS.index(action)
.如果您想在其类的外部 调用此常量,您可以这样做:ActivityLog::ACTION
。它与类方法调用的语法相似,而是使用::
将类与常量分开。重新检查您的代码,它现在应该如下所示:
class ActivityLog < ActiveRecord::Base
ACTIONS = ['start','stop','create','destroy']
validates :user_id, :instance_id, :action, presence: true
validates :user_id, :instance_id, :action, numericality: true
def self.log(instance_id, action)
ActivityLog.create(
user_id: (current_user ? current_user.id : -1),
instance_id: instance_id,
action: ACTIONS.index(action)
)
end
end
关于ruby-on-rails - 在 Rails 4 的模型/类中定义自定义方法,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31462005/