以通函 dependent: :destroy
为例问题:
class User < ActiveRecord::Base
has_one: :staff, dependent: :destroy
end
class Staff < ActiveRecord::Base
belongs_to :user, dependent: :destroy
end
如果我调用
user.destroy
, 关联的 staff
也应该被销毁。相反,调用staff.destroy
应该销毁相关的user
也是。这在 Rails 3.x 中效果很好,但在 Rails 4.0 中行为发生了变化(并在 4.1 中继续),因此形成了一个循环,最终你得到一个错误,“堆栈级别太深”。一种明显的解决方法是使用
before_destroy
创建自定义回调。或 after_destroy
手动销毁相关对象,而不是使用 dependent: :destroy
机制。甚至 issue in GitHub opened for this这种情况有几个人推荐这种解决方法。不幸的是,我什至无法让这种解决方法发挥作用。这就是我所拥有的:
class User < ActiveRecord::Base
has_one: :staff
after_destroy :destroy_staff
def destroy_staff
staff.destroy if staff and !staff.destroyed?
end
end
这不起作用的原因是
staff.destroyed?
总是返回 false
.于是就形成了一个循环。
最佳答案
如果循环的一侧只有一个回调,您可以替换 dependent: :destroy
之一与 dependent: :delete
class User < ActiveRecord::Base
# delete prevents Staff's :destroy callback from happening
has_one: :staff, dependent: :delete
has_many :other_things, dependent: :destroy
end
class Staff < ActiveRecord::Base
# use :destroy here so that other_things are properly removed
belongs_to :user, dependent: :destroy
end
对我来说效果很好,只要一侧不需要其他回调即可触发。
关于ruby-on-rails - 是否有 Rails 4 循环依赖 : :destroy workaround?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23208579/