orphanRemoval 在 OneToOne 关系中不起作用

问题描述 投票:0回答:1

我在Java中有这两个类

@Entity
@Table(name = "user")
public class UserDb {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @OneToOne(mappedBy = "user", cascade = CascadeType.ALL, orphanRemoval = true)
    private BorrowerDb borrowerDb;
}

@Entity
@Table(name = "borrower")
public class BorrowerDb {
   @Id
   @GeneratedValue(strategy = GenerationType.IDENTITY)
   private Long id;

   @MapsId
   @OneToOne(fetch = FetchType.LAZY, optional = false, cascade = CascadeType.REMOVE)
   @JoinColumn(name = "id", nullable = false)
   private UserDb user;
}

当我尝试调用“从 id = ... 的用户中删除”时,我收到下一个错误:

java.sql.SQLIntegrityConstraintViolationException: Cannot delete or update a parent row: a foreign key constraint fails (`test`.`borrower`, CONSTRAINT `FK_7x1elq6p8384hj65g38w08jsm` FOREIGN KEY (`id`) REFERENCES `user` (`id`))

但是,为什么呢?我还需要删除子实例“Borrower”。

谢谢!

java hibernate jpa one-to-one cascading-deletes
1个回答
0
投票

从以下基本示例开始:

@Entity
@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
public class Parent {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;

    private String parentName;

    @OneToOne(cascade = CascadeType.ALL, orphanRemoval = true)
    @JoinColumn(name = "child_id")
    private Child child;

}
@Entity
@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
public class Child {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;

    private String childName;

    @OneToOne(mappedBy = "child")
    private Parent parent;

}
public interface ParentRepository extends JpaRepository<Parent, Integer> {
}

public interface ChildRepository extends JpaRepository<Child, Integer> {
}
@SpringBootTest
class Q78188732ApplicationTests {

    @Autowired
    private ParentRepository parentRepository;

    @Autowired
    private ChildRepository childRepository;

    @Test
    void persistAndRemoveParentTest() {
        Child child = new Child();
        child.setChildName("child");

        Parent parent = new Parent();
        parent.setParentName("parent");
        parent.setChild(child);

        parentRepository.save(parent);

        assertEquals(1, parentRepository.count());
        assertEquals(1, childRepository.count());

        Optional<Parent> persistedParent = parentRepository.findAll().stream().findFirst();

        assertTrue(persistedParent.isPresent());
        assertEquals("parent", persistedParent.get().getParentName());
        assertEquals("child", persistedParent.get().getChild().getChildName());

        Optional<Child> persistedChild = childRepository.findAll().stream().findFirst();

        assertTrue(persistedChild.isPresent());
        assertEquals("child", persistedChild.get().getChildName());
        assertEquals("parent", persistedChild.get().getParent().getParentName());

        parentRepository.deleteById(persistedParent.get().getId());

        assertEquals(0, parentRepository.count());
        assertEquals(0, childRepository.count());
    }

    @Test
    void persistAndRemoveChildTest() {
        Child child = new Child();
        child.setChildName("child");

        Parent parent = new Parent();
        parent.setParentName("parent");
        parent.setChild(child);

        parentRepository.save(parent);

        Optional<Parent> persistedParent = parentRepository.findAll().stream().findFirst();

        assertTrue(persistedParent.isPresent());

        persistedParent.get().setChild(null);
        parentRepository.save(persistedParent.get());

        assertEquals(0, childRepository.count());
        assertEquals(1, parentRepository.count());
    }

}
© www.soinside.com 2019 - 2024. All rights reserved.