创建数量列表后,应使用与列表关联的所有total_calories
的总和更新列表属性calories
。列表和食物相关联has_many :through
数量,每种食物都有calories
属性。
当我在c9.io托管的rails开发用户界面中创建List时,它的行为与预期一致。当我在控制台中创建一个List时,它没有; total_calories
未获得更新。怎么会这样?
我很感激有关调查内容的任何提示,因为我从未在控制台和开发用户界面之间遇到过这种不一致的问题。
服务对象count_calories.rb
:
class CountCalories
def initialize(list)
@list=list
end
def count
@calories = 0
@list.quantities.each do |q|
@calories += Food.find(q.food_id).calories
end
@list.update!(total_calories: @calories)
@list.save!
end
end
List控制器中的create方法:
def create
@list = WriteList.new(list_params).write
if @list.save
flash[:success] = "A list has been created!"
CountCalories.new(@list).count
redirect_to @list
else
render 'new'
end
end
服务对象write_list.rb
,以防有用:
class WriteList
def initialize(params)
@params=params
end
def write
ActiveRecord::Base.transaction do
list = List.new(days: @params[:days], name: @params[:name])
list.save!
3.times do
food1 = Food.all.sample.id
Quantity.create!(food_id: food1, list_id: list[:id], amount: 1+rand(6))
end
list.save!
return list
end
rescue
return List.new(days: @params[:days], name: @params[:name])
end
end
我唯一能想到的是,它可能与迁移创建total_calories有关:
class AddTotalCaloriesToLists < ActiveRecord::Migration
def change
add_column :lists, :total_calories, :integer, :default => 0
end
end
但大多数情况下,我感到困惑,并会感激任何提示。
答案 0 :(得分:0)
我相信你已经过度设计了你的问题。看起来你是来自Java Web堆栈,并且它以rails方式完成了不同的工作。如果您不需要服务对象,请避免使用它们。
class Food < ActiveRecord::Base
validates_presence_of :calories
has_many :lists, through: :food_lists, :dependent: :destroy
end
class FoodList < ActiveRecord::Base
belongs_to :food
belongs_to :list
validates_presence_of: :amount, :food, :list
end
class List < ActiveRecord::Base
has_many :food_lists
has_many :foods, through: :food_lists, dependent: :destroy
def total_calories
self.food_lists.map{|fl| fl.amount * fl.food.calories}.sum
end
end
应该计算可以动态计算的东西,只有在真正需要时才将它们存储为优化形式。它使您的业务领域更容易调试和支持。维持国家是最后的手段!