우선 @Entity 코드를 먼저 봐보자.
@Entity
@NoArgsConstructor(access = AccessLevel.PROTECTED)
public class TransferHistory extends BaseEntity {
@Id
@GeneratedValue
private Long id;
@Column(length = 10)
private String withdrawalAccountNumber;
@Column(length = 10)
private String depositAccountNumber;
private BigDecimal transferAmount;
private BigDecimal amountAfterWithdrawal;
private BigDecimal amountAfterDeposit;
@Builder
public TransferHistory(
final String withdrawalAccountNumber,
final String depositAccountNumber,
final BigDecimal transferAmount,
final BigDecimal amountAfterWithdrawal,
final BigDecimal amountAfterDeposit
) {
this.withdrawalAccountNumber = withdrawalAccountNumber;
this.depositAccountNumber = depositAccountNumber;
this.transferAmount = transferAmount;
this.amountAfterWithdrawal = amountAfterWithdrawal;
this.amountAfterDeposit = amountAfterDeposit;
}
}
클래스 상단 부분에 @NoArgsConstructor 어노테이션을 선언해주었다.
@NoArgsConstructor(access = AccessLevel.PROTECTED)
🔎 꼬리에 꼬리를 무는 질문
Q. 왜 @NoArgsConstructor 어노테이션을 사용할까?
@NoArgsConstructor 어노테이션을 사용하는 궁극적인 이유는 @Entity 어노테이션을 사용할 때, 기본 생성자가 필수로 선언이 되어 있어야 한다.
Q. 왜 기본 생성자가 필수로 선언되어 있어야할까?
Hibernate는 일반적으로 get() 메서드 또는 load() 메서드를 호출할 때 Reflection API를 사용하여 Entity bean의 인스턴스를 만든다. Class.newInstance() 메서드가 인스턴스를 만드는데 사용되고 no-args 생성자가 필요하다. 또한 지연로딩에 필요한 프록시 객체를 생성할 때, 기본 생성자를 사용한다.
Hibernate 공식문서
Q. 그럼 매번 엔티티를 선언해줄 때, @NoArgsConstructor가 필요한가?
자바 클래스에서 생성자가 하나도 선언되지 않으면, 컴파일러는 자동으로 인자가 없는 기본 생성자를 추가하므로, @NoArgsConstructor 어노테이션을 사용하지 않아도 된다.
Q. 왜 @NoArgsConstructor(access = AccessLevel.PROTECTED)를 사용할까?
우선 @NoArgsConstructor(access = AccessLevel.PROTECTED)를 해석해보면, @NoArgsConstructor는 인수가 없는 생성자를 의미하고, access = AccessLevel.PROTECTED는 허용 레벨을 protected로 한다는 의미이다. 코드로 말하면, 아래와 같은 접근 제어자를 protected로 하는 생성자를 생성해준다.
protected TransferHistory() {}
기본 생성자의 접근 제어자가 private인 경우, 프록시 객체를 생성하거나 Entity bean의 인스턴스를 생성할때, 기본 생성자에 접근 자체가 불가능하다. 이러한 이유로 접근 제어자는 public, protected가 되어야 한다.
궁극적으로 protected 접근제어자를 설정하는 이유는 객체의 무분별한 생성을 제한하며, 클래스의 상태 변화를 보다 엄격하게 관리하기 위한 좋은 설계 방법이다.
Q. protected의 접근 범위는 어디까지 인가?
protected 접근 제한자는 같은 패키지 내의 클래스와 상속받은 하위 클래스에서 접근이 가능
'Java' 카테고리의 다른 글
🔎 synchronized는 정말 동기화를 해주는가? (0) | 2024.07.19 |
---|---|
@SoftAssertions를 사용하는 이유 (0) | 2024.07.17 |
@NotBlank과 @NotNull를 사용하는 이유 (0) | 2024.07.17 |
BigDecimal의 compareTo 메서드 파헤치기 (0) | 2024.07.17 |
🔎 SoftAssertions의 각 Assertions는 독립적인가? (0) | 2024.07.16 |