Возможно ли массовое удаление из ассоциации «многие-многие» с HQL?

И если да, то каков синтаксис?

Предположим, я хочу, чтобы экземпляр Foo не был связан со всеми экземплярами Bar: в SQL это будет просто:

delete from FOO_BAR_MAPPING
where FOO_ID = ?

В HQL я предполагал, что это будет что-то вроде:

delete from Bar.foos foos
where foos.id = :id

(где foos — сопоставленная коллекция Foo)

Но кажется неправильным, давая:

org.hibernate.hql.ast.QuerySyntaxException: Bar.foos is not mapped

Возможно ли это даже с HQL?


person ireddick    schedule 29.07.2009    source источник


Ответы (2)


Чтобы ответить на ваш конкретный вопрос, нет, насколько я знаю, это невозможно с HQL.

Я думаю, вы немного смешиваете SQL и HQL. В SQL вы действительно «удаляете» записи, и, конечно же, спящий режим в конечном итоге сделает это. Однако Hibernate/HQL разработан с учетом объектно-ориентированного мышления, поэтому «удалить» в этом контексте означает, что вы удаляете объекты, а не ассоциации. Обычно вы делаете что-то вроде следующего:

Foo f = session.get(Foo.class, id);
f.getBars().clear();
session.merge(f);

Это извлекает объект по указанному вами идентификатору и удаляет все ассоциации Bar, очищая его коллекцию. Очевидно, что вам нужно, чтобы ассоциация Foo-Bars отображалась в правильном направлении, чтобы это работало.

person Matt S.    schedule 29.07.2009
comment
Обратите внимание, что это удалит только запись в таблице ассоциаций, а не элемент в конце. Для этого вам нужно включить удаление сирот. - person aperkins; 29.07.2009

Самостоятельное удаление ассоциаций невозможно с помощью HQL. Однако вы можете сделать следующее:

A) Предполагая, что вы делаете это для одного Foo и ваш каскад настроен соответствующим образом, вы можете загрузить этот экземпляр Foo, очистить его коллекцию bars и сохранить его.

Б) Если вы пытаетесь очистить bars от нескольких Foos, вы можете сопоставить SQL-запрос вместо HQL.

person ChssPly76    schedule 29.07.2009