【问题标题】:Can't delete_all associated records with "has_many through"无法删除“has_many through”的所有关联记录
【发布时间】:2013-05-30 18:55:59
【问题描述】:

我有 3 个模型:

调度

belongs_to :service

服务

belongs_to :user, :foreign_key => "owner"
has_many :shedules, :dependent => :destroy

用户

has_many :services, :foreign_key => "owner", :dependent => :destroy
has_many :shedules, :through => :services, :foreign_key => "owner", :dependent => :destroy

然后我可以通过my_user.shedules看到所有用户的shedules

我的目标是删除所有用户,然后我尝试my_user.shedules.delete_all,但收到此错误:

ActiveRecord::HasManyThroughCantAssociateThroughHasOneOrManyReflection: 无法修改关联“用户#shedules”,因为源 反射类“Shedule”通过 :has_many 关联到“服务”。

经过一番谷歌搜索,我找到了this 和其他一些类似的帖子,但它们都不适合我的问题。

当然,我可以通过迭代用户服务来删除它

my_user.services.each do |s|
    s.shedules.delete_all
end

但我很有趣为什么 my_user.shedules.delete_all 不起作用。

谢谢!

【问题讨论】:

  • 尝试从has_many :shedules, :through => :services, :foreign_key => "owner", :dependent => :destroy中删除foreign_key
  • 不幸的是,同样的错误
  • stackoverflow.com/questions/1399394/… 使用destroy 来触发:dependent => :destroy的回调
  • 我只想删除shedules,而不是它们所属的服务。

标签: ruby-on-rails activerecord associations


【解决方案1】:

找到了一个比以前更简单的解决方案。

Schedule.merge(my_user.schedules).delete_all

我更喜欢这个,因为它只是一个数据库查询,我不必记住外键的名称。

之所以有效,是因为:

Schedule.merge(my_user.schedules).to_sql == my_user.schedules.to_sql

【讨论】:

    【解决方案2】:

    我不确定您是否可以使用关联删除schedules。您可以通过自己找到这些记录来删除它们。

    Shedule.where(service_id: user.services.pluck(&:id)).delete_all
    user.reload # optional
    

    如果你经常使用这个,你可以在User上定义一个方法

    def delete_schedules
      Shedule.where(service_id: user.services.pluck(&:id)).delete_all
    end
    

    【讨论】:

      【解决方案3】:

      试试:-

      my_user.shedules.destroy_all
      

      Shedule.delete_all(:owner => my_user.id)
      

      【讨论】:

      • 这个答案对我有用。您无法删除日程可能是因为您的日程也与服务相关联。
      • 您的表“Shedule”与“Service”以及“User”相关联,因此您无法使用 delete_all 或 destroy_all 删除 shedule。
      • 我不明白为什么。 Shedule 属于 Service,Service 属于 User。这意味着表 Shedules 具有字段 service_id。那么,如果没有任何依赖,为什么我不能删除所有的日程呢?
      • 就我想要的 SQL 而言:DELETE FROM shedules WHERE service_id in (SELECT id FROM services WHERE owner = ?)。我不明白为什么它不能删除shedules。
      • 试试这个:- Shedule.delete_all(:user_id => my_user.id)
      猜你喜欢
      • 2011-02-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-07-31
      • 2014-06-03
      • 2010-10-20
      • 2011-10-01
      • 1970-01-01
      相关资源
      最近更新 更多