我的模型及其关联是:
class Post < ActiveRecord::Base
has_many :comments
end
class Comment < ActiveRecord::Base
belongs_to :post
validates :commenter, :presence => true
end
案例1 :当我尝试下面的代码时,会调用自动保存方法。
@post = Post.find(3)
@comments = @post.comments
p @comments #=> []
p @comments.class #=> Array
if @comments.empty?
3.times do
@comments << @post.comments.build
end
end
p @comments.first.errors #=>{:commenter=>["can't be blank"]}
案例2:如果我手动将相同的空数组初始化为@comments,则自动保存不会调用。例如,
p @comments #=> []
p @comments.class #=> Array
if @comments.empty?
@comments = []
p @comments #=> []
3.times do
@comments << @post.comments.build
end
end
p @comments.first.errors #=>{}
什么是避免自动保存的最佳解决方案,请任何人解释为什么上述代码的行为不同?
答案 0 :(得分:1)
Rails广泛使用monkey-patching,因此rails Array与纯Ruby数组不同。 (比较irb > [].methods
和rails c > [].methods
根据<<
集合
has_many
方法
立即触发update sql而不等待保存或更新调用 在父对象上
因此,很可能Rails拥有集合事件的“观察者”,并在您尝试添加新对象时触发验证。
在第二个片段中,您使用纯数组(不是has_many
集合),因此不会触发更新操作。
为避免更新操作,您根本不需要<<
@post = Post.find(3)
@comments = @post.comments
if @comments.empty?
3.times do
@post.comments.build
end
end
p @comments.size
=> 3
答案 1 :(得分:0)
自动保存在Post模型中定义。阅读有关自动保存的here。如果我正确理解您的问题,那么定义:autosave => false
。