在rails中,我如何委托给一个类方法

时间:2013-01-28 17:59:36

标签: ruby-on-rails ruby-on-rails-3

class Task < ActiveRecord::Base
  attr_accessible :due_date, :text

  def self.this_week
    where(:due_date => Date.today.beginning_of_week..Date.today.end_of_week)
  end
end

class Important < ActiveRecord::Base
  attr_accessible :email

  has_one :task, :as => :taskable, :dependent => :destroy

  delegate this_week, :to => :task
end

到目前为止,当我尝试Important.this_week时,这个代表没有按预期工作。我收到一条错误消息,说明没有为类定义this_week方法...

有什么想法吗?我甚至可以委托给像这样的类方法吗?我可能会以这种方式扩展另一个或两个类Task,所以我很好奇这是如何以不会将一堆代码复制到每个实现类的方式工作的。

3 个答案:

答案 0 :(得分:29)

你正在接受ActiveSupport delegation core extensiondelegate帮助器为当前类定义实例方法,以便它的实例将调用委托给该实例上的某个变量。

如果你想在课堂级别委派,你需要打开单身人士课程并在那里设置代表团:

class Important < ActiveRecord::Base
  attr_accessible :email

  has_one :task, :as => :taskable, :dependent => :destroy

  class << self
    delegate :this_week, :to => :task
  end
end

但是这假设Important.task是对Task类的引用(它不是)

我建议明确代理,而不是依赖代表助手,这会让你的生活变得困难:

class Important < ActiveRecord::Base
  attr_accessible :email

  has_one :task, :as => :taskable, :dependent => :destroy

  class << self
    def this_week(*args, &block)
      Task.this_week(*args, &block)
    end
  end
end

答案 1 :(得分:15)

考虑继承,将方法委托给类方法:

delegate :this_week, :to => :class

你可以委托给一个特定的类(参见Isaac Betesh的答案):

delegate :this_week, :to => :Task

文档可在此处获取: http://api.rubyonrails.org/classes/Module.html#method-i-delegate

答案 2 :(得分:9)

您可以将方法委托给常量 - 它只是区分大小写。此外,方法的名称必须作为符号传递给delegate

class Important < ActiveRecord::Base
  delegate :this_week, :to => :Task
  # Note ':this_week' instead of 'this_week'
  # Note 'Task' instead of 'task'
end