테이블 수준 관계

두 테이블을 다시 살펴보겠습니다.

ID 이름 직업 샐러리 나이 가입 날짜
1 이바노프 이반 프로그램 제작자 100000 25 2012-06-30
2 페트로프 페트르 프로그램 제작자 80000 23 2013-08-12
이바노프 세르게이 시험 장치 40000 서른 2014-01-01
4 라비노비치 모이샤 감독 200000 35 2015-05-12
5 키리엔코 아나스타샤 사무실 관리자 40000 25 2015년 10월 10일
6 바스카 고양이 1000 2018-11-11

직원 테이블:

이 테이블에는 다음 열이 있습니다.

  • ID INT
  • 이름 VARCHAR
  • 직업 바차
  • 급여 INT
  • 나이 INT
  • 가입 날짜 날짜

직원의 작업이 포함된 작업 테이블은 다음과 같습니다 .

ID employee_id 이름 마감 시간
1 1 프런트엔드의 버그 수정 2022-06-01
2 2 백엔드의 버그 수정 2022-06-15
5 커피를 사다 2022-07-01
4 5 커피를 사다 2022-08-01
5 5 커피를 사다 2022-09-01
6 (없는) 사무실을 청소하다 (없는)
7 4 즐거운 삶 (없는)
8 6 즐거운 삶 (없는)

이 테이블에는 4개의 열만 있습니다.

  • id 는 작업(및 테이블의 행)의 고유 번호입니다.
  • employee_id - 작업이 할당된 직원 테이블의 직원 ID입니다.
  • 이름 - 작업의 이름과 설명입니다.
  • 기한 - 작업을 완료해야 하는 시간입니다.

직원 테이블의 단일 항목은 작업 테이블의 여러 행에서 참조할 수 있습니다. 이러한 테이블 수준 관계를 일대다 라고 합니다 .

Java 클래스 수준과의 관계

그리고 우리 클래스인 Employee 클래스는 다음과 같습니다.

@Entity
@Table(name="user")
class Employee {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String name;

   @Column(name="occupation")
   public String occupation;

   @Column(name="salary")
   public Integer salary;

   @Column(name="join_date")
   public Date join;
}

그리고 원래 형식의 EmployeeTask 클래스:

@Entity
@Table(name="task")
class EmployeeTask {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String description;

   @Column(name="employee_id")
   public Integer employeeId;

   @Column(name="deadline")
   public Date deadline;
}

@OneToMany 주석

다른 방식으로 Entity 클래스 간의 통신을 조정할 수 있습니다.

부모 클래스에서 자식 개체의 컬렉션을 만들 때 사용한 @ElementCollection 주석을 기억하십니까 ? @OneToMany 주석을 사용하여 비슷한 작업을 수행할 수 있습니다 . 이번에만 Employee 클래스가 변경됩니다 .

@Entity
@Table(name="user")
class Employee {
   @Column(name="id")
   public Integer id;

   @OneToMany(cascade = CascadeType.ALL)
   @JoinColumn(name = "employee_id")
   private Set<EmployeeTask> tasks = new HashSet<EmployeeTask>();
}

@OneToMany 주석을 사용하여 객체가직원많은 EmployeeTask 개체를 저장할 수 있습니다 . 또한 @JoinColumn 주석을 사용하여 개체 ID가 저장된 작업 테이블의 열을 표시했습니다.직원.

그러나 EmployeeTask 클래스는 일반적으로 employee_id 열을 참조하는 필드를 포함하지 않습니다. 예:

@Entity
@Table(name="task")
class EmployeeTask {
   @Column(name="id")
   public Integer id;

   @Column(name="name")
   public String description;

   @Column(name="deadline")
   public Date deadline;
}

employee_id 필드는 서비스 필드로 간주되며 해당 값은 Hibernate에 의해 제어됩니다.

요청 예시

작업자에게 작업을 추가하려면 다음과 같은 코드를 작성해야 합니다.

EmployeeTask task1 = new EmployeeTask();
task1.description = "Do Something Important";
session.persist(task1);

EmployeeTask task2 = new EmployeeTask();
task2.description = "Nothing to do";
session.persist(task2);
session.flush();

Employee director = session.find(Employee.class, 4);
director.tasks.add(task1);
director.tasks.add(task2);

session.update(director);
session.flush();

먼저 EmployeeTask 객체 2개를 생성하여 데이터베이스에 저장하고 flush() 메서드를 호출하여 INSERT 작업을 수행하고 객체에 ID를 부여합니다.

그런 다음 데이터베이스에서 감독을 찾고 그에게서 작업 필드를 가져와 두 개의 작업을 추가합니다. 그런 다음 디렉터를 데이터베이스에 저장합니다. 그런 다음 직원 테이블의 이사 ID인 employee_id 열의 새 작업에 대해 데이터베이스에 값 4가 나타납니다.

중요한! 데이터베이스의 테이블은 @ManyToOne@OneToMany 주석 에 대해 동일합니다 . 그러나 이러한 테이블에 대한 Java 클래스는 다릅니다.