如何通过“has_many”关联获取数据?
Posted
技术标签:
【中文标题】如何通过“has_many”关联获取数据?【英文标题】:How to fetch data through "has_many" associations? 【发布时间】:2014-09-18 09:12:37 【问题描述】:我有以下模型结构:
class User < ActiveRecord::Base
has_many :favorites
end
class Favorite < ActiveRecord::Base
belongs_to :user
belongs_to :company
end
class Color < ActiveRecord::Base
belongs_to :company
end
class Company < ActiveRecord::Base
has_many :colors
has_many :favorities
end
这意味着一家公司有多种颜色。每个用户都可以收藏一家公司(然后我可以打印出相应公司提供的每种颜色)。
但我正在尝试显示我收藏的公司提供的所有颜色。
我试过这样:
favorited_colors = current_user.favorites.colors
undefined method `colors' for #<ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Favorite:0x007fe037da01f0>
和
favorited_colors = current_user.favorites.companies.colors
undefined method `companies' for #<ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Favorite:0x007fe038ce8db0>
除了通过 each 循环遍历所有收藏的公司并将所有颜色保存到数组中之外,还有其他方法可以从收藏的公司获取所有颜色的列表吗?
谢谢
【问题讨论】:
你没有用户和公司之间的联系,也没有用户和颜色之间的联系。因此,不,没有办法得到你正在尝试的东西 【参考方案1】:这应该可以从 rails 3.1 开始:
class User
has_many :favorites
has_many :companies, :through => :favorites
has_many :favorit_colors, :through => :companies
end
然后
favorited_colors = current_user.favorit_colors
不过,这未经测试。
【讨论】:
【参考方案2】:收藏
您遇到的问题是您在集合对象上调用 companies
方法
这里的问题是您只能在对象的单个实例上调用方法。您看到的错误很好地证明了这一点:
undefined method `companies' for #<ActiveRecord::Associations::CollectionProxy::ActiveRecord_Associations_CollectionProxy_Favorite:0x007fe038ce8db0>
您应该尝试使其工作的方式是调用以下内容:
current_user.favorites.each do |favourite|
= favourite.colors
end
我了解您想要实现的目标,所以让我给您一些想法:
关联扩展
Rails 有一个名为ActiveRecord Association Extensions 的功能,它可以让您提供所需的功能:
#app/models/user.rb
class User < ActiveRecord::Base
has_many :favorites do
def colors
# Business logic for colours here
end
end
end
现在这是完全未经测试的。但是,我对 Rails 的这一深层部分有经验,因此我知道您将使用以下数据集:
proxy_association.owner
返回关联所属的对象。proxy_association.reflection
返回描述关联的反射对象。proxy_association.target
返回 belongs_to 或 has_one 的关联对象,或关联对象的集合 has_many 或 has_and_belongs_to_many。
由此,您将能够根据您希望显示的colors
构造一个数组/对象:
has_many :favorites do
def colors #totally untested
colors =
favorites = proxy_association.target
favorites.each do |favorite|
favorite.company.colors.each do |color|
colors << color
end
end
return colors
end
end
【讨论】:
以上是关于如何通过“has_many”关联获取数据?的主要内容,如果未能解决你的问题,请参考以下文章
如何在has_many中获取模型的属性:通过Rails 5中的关联