@ElementCollection暗示orphanRemoval?

问题描述:

根据这篇文章Difference between @OneToMany and @ElementCollection?我更喜欢@ElementCollection可嵌入的类型和@OneToMany的实体。但使用@OneToMany我可以添加设置选项orphanRemoval=true。我怎么能这样做@ElementCollection?它暗示了什么?@ElementCollection暗示orphanRemoval?

暗示。删除拥有实体也将删除@ElementCollection上的所有数据。如果Session尚未关闭,将Collection设置为空或更改Collection中的元素将导致更新。

的官方文档here这样说:

2.8.1。收藏作为一种价值型

价值和嵌入型收藏有类似的行为 简单的值类型,因为当被持久化对象引用 它们会自动持续和自动删除时 未引用。如果集合从一个持久对象传递到另一个持久对象,则其元素可能会从一个表移动到另一个表。
...
对于值类型集合,JPA 2.0定义了@ElementCollection 注释。价值类型集合的生命周期完全由其拥有的实体控制。

我跑这三个测试,以测试它:

@Test 
    public void selectStudentAndSetBooksCollectionToNull() { 
    Student student = studentDao.getById(3L); 
    List<String> books = student.getBooks(); 

    books.forEach(System.out::println); 

    student.setBooks(null); 

    em.flush(); // delete from student_book where student_id = ? 
    } 

    @Test 
    public void selectStudentAndAddBookInCollection() { 
    Student student = studentDao.getById(3L); 
    List<String> books = student.getBooks(); 

    books.add("PHP Book"); 

    books.forEach(System.out::println); 

    em.flush(); // insert into student_book(student_id, book) values(?, ?) 
    } 

    @Test 
    public void selectStudentAndChangeCollection() { 
    Student student = studentDao.getById(3L); 
    List<String> newBooks = new ArrayList<>(); 

    newBooks.add("Rocket Engineering"); 

    newBooks.forEach(System.out::println); 

    student.setBooks(newBooks); 

    em.flush(); // delete from student_book where student_id = ? 
    // insert into student_book(student_id, book) values(?, ?) 
    } 

这是Student类:

@Entity 
@Table(name = "student") 
public class Student { 

    @Id 
    @GeneratedValue(strategy = GenerationType.IDENTITY) 
    @Column(name = "student_id", nullable = false, insertable = false, updatable = false) 
    private Long id; 

    @Column(name = "name", nullable = false) 
    private String name; 

    @ElementCollection 
    @CollectionTable(
     name = "student_books", 
     joinColumns = @JoinColumn(name = "student_id", referencedColumnName = "student_id")) 
    @Column(name = "book") 
    private List<String> books = new ArrayList<>(); 

    // Getters & Setters 

} 
+0

但是这还不是orphanRemoval是怎么一回事。当然,如果您删除父项,则会以级联的方式删除子项,但如果您仅仅是失去了对子项的引用(例如,将其设置为空),那么该项不再可用? –

+1

是的,'@ ElementCollection'字段隐式具有'Cascasde.ALL' +'orphanRemoval = true' –