Rails嵌套属性:至少需要两条记录
如何才能使提交产品至少需要两个选项记录?
class Product :destroy accepts_nested_attributes_for :options, :allow_destroy => :true, :reject_if => proc { |attrs| attrs.all? { |k, v| v.blank? } } validates_presence_of :user_id, :created_at validates :description, :presence => true, :length => {:minimum => 0, :maximum => 500} end class Option {:minimum => 0, :maximum => 60} end
class Product < ActiveRecord::Base #... all your other stuff validate :require_two_options private def require_two_options errors.add(:base, "You must provide at least two options") if options.size < 2 end end
只考虑一下karmajunkie回答:我会使用size
而不是count
因为如果某些构建(而不是保存)的嵌套对象有错误,则不会考虑它(它不在数据库上)。
class Product < ActiveRecord::Base #... all your other stuff validate :require_two_options private def require_two_options errors.add(:base, "You must provide at least two options") if options.size < 2 end end
如果您的表单允许删除记录,则.size
将不起作用,因为它包含标记为销毁的记录。
我的解决方案是:
validate :require_two_options private def require_two_options i = 0 product_options.each do |option| i += 1 unless option.marked_for_destruction? end errors.add(:base, "You must provide at least two option") if i < 2 end
使用Rails 5测试的更整洁的代码:
class Product < ActiveRecord::Base OPTIONS_SIZE_MIN = 2 validate :require_two_options private def options_count_valid? options.reject(&:marked_for_destruction?).size >= OPTIONS_SIZE_MIN end def require_two_options errors.add(:base, 'You must provide at least two options') unless options_count_valid? end end