Я нахожу, что сиротские записи не удаляются при удалении из коллекции в Hibernate. Я должен делать что-то простое неправильно (это Hibernate-101!), Но я не могу его найти.
Учитывая следующее:
public class Book {
@ManyToOne
@NotNull
Author author;
}
public class Author
{
@OneToMany(cascade={CascadeType.ALL})
List<Book> books;
}
И следующий код обновления:
Author author = authorDAO.get(1);
Book book = author.getBooks().get(0);
author.getBooks().remove(0);
authorDAO.update(author);
Отпечаток AuthorDAO:
@Override
public void update(T entity) {
getSession().update(entity);
}
Следующий тест: сбой:
Author author = author.get(1);
assertEquals(0,author.getBooks().size()); // Passes
Book dbBook = bookDAO.get(book.getId())
assertNull(dbBook); // Fail! dbBook still exists!
assertFalse(author.getBooks().contains(dbBook) // Passes!
В заключение, я нахожу:
- В то время как книга удалена из коллекции авторов, она все еще существует в базе данных
- Если я исследую
book.getAuthor().getBooks()
, книга не существует в этой коллекции
Это "чувствует", как будто я не очищаю сессию или не корректирую соответствующее обновление, но я не уверен, где я должен это делать. Вдоль этого жила другие моменты, которые могут влиять:
- Я выполняю вышеуказанное в тесте JUnit, украшенном
@RunWith(SpringJUnit4ClassRunner.class)
- Я первоначально ударил эту проблему внутри процедуры обновления, которая украшена
@Transactional
, однако я с тех пор воссоздал ее в обычном старом тесте JUnit.
Любые советы будут очень признательны!
EDIT: Спасибо за все отзывы. В дополнение к комментариям ниже, я добавил @Cascade(org.hibernate.annotations.CascadeType.DELETE_ORPHAN)
к родительскому, так что теперь:
public class Author
{
@OneToMany(cascade={CascadeType.ALL})
@Cascade(org.hibernate.annotations.CascadeType.DELETE_ORPHAN)
List<Book> books;
}
Я все еще нахожу те же результаты. Я ДОЛЖЕН пропустить что-то простое.