Rails: удаление в сопоставленной области ведет себя иначе, чем просто удаление из ассоциации - PullRequest
0 голосов
/ 31 мая 2018

У меня есть проект, основанный на Rails 4.2.

Я определил две модели, подобные этой:

class Option < ActiveRecord::Base
    has_many :item_options
    has_many :items, through: :item_options, source: :item 

    scope :materials, -> { where(category: 'material') }
    scope :types, -> { where(category: 'type') }

class Item < ActiveRecord::Base
    has_many :item_options
    has_many :options, through: :item_options

Я не могу удалить записи присоединения ассоциации через области действияМодель Option.

Если я сделаю:

Item.first.options.materials.delete_all

, то выполненный запрос будет:

DELETE FROM "options" WHERE "options"."id" IN (SELECT "options"."id" FROM "options" INNER JOIN "item_options" ON "options"."id" = "item_options"."option_id" WHERE "item_options"."item_id" = $1 AND "options"."category" = $2)

Это удаляет записи из модели Option, и это не то, что я ожидал.

Если я пытаюсь удалить записи ассоциации без использования области, например:

Item.first.options.delete_all

, которая правильно выполняет запрос:

DELETE FROM "item_options" WHERE "item_options"."item_id" = $1

Эффективное удаление толькообъединить записи.

Почему удаление ведет себя по-разному, если вызывается из области?

(отредактировано, содержит ошибку вставки со старым именем LabelItem для одной из моделей)

1 Ответ

0 голосов
/ 31 мая 2018

Когда вы вызываете метод materials в отношении options, он возвращает экземпляр отношения Option.Вот почему это не сработает.

Может сработать:

class Item < ActiveRecord::Base
    has_many :item_options
    has_many :options, through: :item_options
    has_many :material_options, -> { materials }, through: :item_options, source: :option

Тогда:

Item.first.material_options.delete_all

...