对象映射关系分为单向关系和双向关系,单向关系只在一方对象上存在对方对象,双向关系是在双方对象上存在彼此对象。
public class Department implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer departmentId;
    private String departmentCode;
    
    @OneToMany(cascade = {CascadeType.ALL})
    @JoinColumn
    private List<Employee> employeeList;
} 
  在没有 @JoinColumn 时,将多增加一个中间关系表,由此表来维护两个对象关系,增加之后只有两个表,由 Employee 表维护关系。默认情况下jpa会使用主键来做关联,并在子表中增加外键约束。 
在设计表结构时,主键一般会使用自增ID,但在做子表关联时由于分布式结构原因不想使用自增ID来做关系维护,则可自定义字段 code 来维护关系,如下:
public class Department implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer departmentId;
    private String departmentCode;
    @OneToMany(cascade = {CascadeType.ALL})
    @JoinColumn(name = "departmentCode", referencedColumnName = "departmentCode")
    private List<Employee> employeeList;
} 
 在employee表中会增加一个 department_code 字段来维护关联关系。
注意:从add操作中的SQL可以看出,employee是先insert之后,再去update关系字段的,多一步update。
Hibernate: insert into department (department_code, department_name) values (?, ?) Hibernate: insert into employee (employee_code, employee_name) values (?, ?) Hibernate: insert into employee (employee_code, employee_name) values (?, ?) Hibernate: update employee set department_code=? where employee_id=? Hibernate: update employee set department_code=? where employee_id=?
public class Department implements Serializable {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer departmentId;
    private String departmentCode;
    @OneToMany(cascade = {CascadeType.ALL}, mappedBy = "department")
    private List<Employee> employeeList;
}
public class Employee {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer employeeId;
    private String employeeCode;
    @ManyToOne
    private Department department;
} 
  使用 mappedBy 将去掉中间关系表,由employee维护department的关系。 
注意事项:
1.在add操作中子对象employee必须设置主对象,否则数据库层面是没有维护外键关系的,如:
@Test
public void add(){
    Department department = Department.builder()
            .departmentCode("D001")
            .departmentName("部门1")
            .build();
    Employee employee = Employee.builder()
            .employeeCode("E001")
            .employeeName("员工1")
            .build();
    // 如无此操作,将无关联关系        
    employee.setDepartment(department);
    
    List<Employee> employeeList = new ArrayList<>();
    employeeList.add(employee);
    department.setEmployeeList(employeeList);
    departmentRepository.save(department);
} 
 2.此种设置是不需要额外update关系的
Hibernate: insert into department (department_code, department_name) values (?, ?) Hibernate: insert into employee (department_department_id, employee_code, employee_name) values (?, ?, ?) Hibernate: insert into employee (department_department_id, employee_code, employee_name) values (?, ?, ?)
3.关闭子对象中的父对象toString,避免无限循环调用
同单向关系类似,且有额外的update操作
code关联,使用JoinColumn时不可同时使用mappedBy
CascadeType.REMOVE:级联删除
orphanRemoval = true
https://gitee.com/hypier/barr...