如何在Rails中将参数传递给委托方法

Ada*_*NYC 13 model-view-controller ruby-on-rails presenter activemodel

我想有一个仪表板来显示多个模型的摘要,我使用Presenter实现它而没有自己的数据.我使用ActiveModel类(没有数据表):

class Dashboard
  attr_accessor :user_id
  def initialize(id)
    self.user_id = id
  end

  delegate :username, :password, :to => :user 
  delegate :address,  :to => :account
  delegate :friends,   :to => :friendship

end 
Run Code Online (Sandbox Code Playgroud)

通过代表,我希望能够打电话Dashboard.address回来Account.find_by_user_id(Dashboard.user_id).address.

如果Dashboard是一个ActiveRecord类,那么我可以声明Dashboard#belongs_to :account并且委托会自动工作(即,Account会知道它应该从Dashboard实例中的user_idequals 返回地址属性to user_id).

但Dashboard不是ActiveRecord类,所以我不能声明belongs_to.我需要另一种方法来告诉Account查找正确的记录.

有办法克服这个问题吗?(我知道我可以假装Dashboard有一个空表,或者我可以将User的实例方法重写为带参数的类方法.但这些解决方案都是黑客攻击).

谢谢.

Ben*_*ret 13

在编写时delegate :address, :to => :account,这会address在Dashboard上创建一个新方法,它基本上account在同一个对象上调用该方法,然后调用addressaccount方法的结果.这(非常粗略地)类似于写作:

class Dashboard
 ...
  def address
    self.account.address
  end
 ...
end
Run Code Online (Sandbox Code Playgroud)

使用当前的类,您所要做的就是创建一个account方法,该方法返回正确的帐户user_id:

class Dashboard
  attr_accessor :user_id
  def initialize(id)
    self.user_id = id
  end

  delegate :username, :password, :to => :user 
  delegate :address,  :to => :account
  delegate :friends,   :to => :friendship

  def account
    @account ||= Account.find_by_user_id(self.user_id)
  end
end
Run Code Online (Sandbox Code Playgroud)

这将允许您访问这样的地址:

dashboard = Dashboard.new(1)
# the following returns Account.find_by_user_id(1).address
address = dashboard.address
Run Code Online (Sandbox Code Playgroud)