首页 > 解决方案 > 在Hibernate中删除@OneToMany中的父记录时将子记录外键设置为null

问题描述

我有 2 个实体,部门和员工,一个部门可以有很多员工。员工表有一个外键,DEPT_ID。我想删除一个特定部门并将该部门的所有员工的外键设置为空。相反,我的代码正在删除子记录(即员工),即使我只是将 DEPT_ID 设置为 null。

@Entity
@Table(name = "MY_DEPARTMENT")
public class Department {

    @Id
    @GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "sequence1")
    @SequenceGenerator(name = "sequence1", sequenceName = "SEQ_DEP")
    @Column(name = "DEPARTMENT_ID")
    private long departmentId;
    
    @Column(name = "DEPARTMENT_NAME")
    private String departmentName;
    
    @Column(name = "DEPARTMENT_LOCATION")
    private String departmentLocation;
    
    @OneToMany(mappedBy = "department")
    private List<Employee> employees;
}

@Entity
@Table(name = "MY_EMPLOYEE")
public class Employee {

    @Id
    @GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "sequence2")
    @SequenceGenerator(name = "sequence2", sequenceName = "SEQ_EMP")
    @Column(name = "EMPLOYEE_ID")
    private long employeeId;
    
    @Column(name = "EMPLOYEE_NAME")
    private String employeeName;
    
    private int salary;
    
    private String email;
    
    @ManyToOne
    @JoinColumn(name = "DEPT_ID")
    private Department department;

}

        Session session = sessionFactory.getCurrentSession();
        Department department = session.get(Department.class, 3102l);
        List<Employee> list = department.getEmployees();
        for (Employee employee : list) {
            employee.setDepartment(null);
        }
        session.delete(department); 

注意:我启用了 show_sql = true,我可以看到首先为 EMPLOYEE 表触发 UPDATE 查询,我认为该表将所有员工的 DEPT_ID 设置为 null,然后我可以看到触发的 DELETE 查询删除了部门记录。

我正在使用 Oracle 数据库,外键定义为 ON DELETE RESTRICT。

标签: hibernate

解决方案


在删除之前将部门对象中的员工设置为空

Session session = sessionFactory.getCurrentSession();
        Department department = session.get(Department.class, 3102l);
        List<Employee> list = department.getEmployees();
        for (Employee employee : list) {
            employee.setDepartment(null);
        }
        department.setEmployees(null);
        session.delete(department);

推荐阅读