我有Transactions
表,这是Users
和Products
之间的M:M表
class Transaction
belongs_to :user
belongs_to :product, counter_cache: :transactions_count
end
在事务表中,我有quantity
列。
在Products中,我有transactions_count
,它存储了该产品的购买次数。
但是计数器缓存只计算的行数。是否有办法计算数量的总和?
我知道我可以使用after_save :update_count
之类的东西,但是是否有Rails约定,当遵循将自动执行此任务时?
谢谢
我个人发现counter_cache
非常不可靠(给出负值等),并且倾向于回避,直到它得到改进
你可能感兴趣的东西:
<
别名列/strong>
我们想做类似的事情(从连接模型中提取),并发现一个可靠的方法是使用SQL别名列:
#app/models/user.rb
has_many :transactions
has_many :products, -> { select("#{User.table_name}.*, SUM(#{Transaction.table_name}.quantity) AS total") }, through: :transactions, dependent: :destroy
这可能需要一些工作,但会有所帮助#
ActiveRecord关联扩展
在发现.delegate
方法之后,我想看看我们是否可以为连接模型实现类似的东西。两周后,我们让它工作了:
#app/models/message.rb
Class Message < ActiveRecord::Base
has_many :image_messages
has_many :images, through: :image_messages, extend: ImageCaption
end
#app/models/concerns/image_caption.rb
module ImageCaption
#Load
def load
captions.each do |caption|
proxy_association.target << caption
end
end
#Private
private
#Captions
def captions
return_array = []
through_collection.each_with_index do |through,i|
associate = through.send(reflection_name)
associate.assign_attributes({caption: items[i]}) if items[i].present?
return_array.concat Array.new(1).fill( associate )
end
return_array
end
#######################
# Variables #
#######################
#Association
def reflection_name
proxy_association.source_reflection.name
end
#Foreign Key
def through_source_key
proxy_association.reflection.source_reflection.foreign_key
end
#Primary Key
def through_primary_key
proxy_association.reflection.through_reflection.active_record_primary_key
end
#Through Name
def through_name
proxy_association.reflection.through_reflection.name
end
#Through
def through_collection
proxy_association.owner.send through_name
end
#Captions
def items
through_collection.map(&:caption)
end
#Target
def target_collection
#load_target
proxy_association.target
end
end
这基本上是将连接模型(image_messages
)的属性连接到父对象(image
)。您可以使用它来总结proxy_association
通过集合中的quantity
,将用户拥有的每个product
附加到