728x90
프로젝트를 진행하다 보면, CRUD 작업을 하는 경우가 많다. 특히 Update 작업을 하는 경우, 개발하는 과정에서 Setter의 사용을 지양하라고는 하는데, 도대체 왜일까?
객체의 불변성이 깨질 수 있다.
Setter를 사용하는 경우, 객체의 상태가 변할 수 있기 때문에 객체지향 설계 원칙인 개방-폐쇄의 원칙(OCP)에 어긋나게 된다. OCP는 확장에 대해서 개방되어야 하나 수정에 대해서는 폐쇄적이어야 한다는 것으로, Setter를 사용하게 되면 수정에 대해 문제가 발생할 수 있다는 점을 알아야 한다. 예시 코드를 함께 보자.
public class PersonService {
private PersonRepository personRepository;
public PersonService(PersonRepository personRepository) {
this.personRepository = personRepository;
}
public void updatePerson(Long id, String newName, int newEmail) {
Person person = personRepository.findById(id);
if (person != null) {
person.setName(newName);
person.setAge(newEmail);
personRepository.save(person);
} else {
throw new IllegalArgumentException(id + "에 해당하는 사람이 없습니다.");
}
}
}
Setter를 사용하여 update를 하는 메소드이다. 객체의 속성을 직접 변경하기 때문에 외부에서 언제든지 객체의 속성을 변경할 수 있는 상태가 된다. 같은 로직을 Builder로도 한번 보자.
public class PersonService {
private PersonRepository personRepository;
public PersonService(PersonRepository personRepository) {
this.personRepository = personRepository;
}
public void updatePerson(Long id, String newName, int newEmail) {
Person person = personRepository.findById(id);
if (person != null) {
person = new Person.Builder()
.id(person.getId()) // 기존의 id 유지
.name(newName)
.age(newEmail)
.build();
personRepository.save(person);
} else {
throw new IllegalArgumentException(id + "에 해당하는 사람이 없습니다.");
}
}
}
Builder를 사용하면 업데이트 로직이 Setter보다 명확하다는 것을 알 수 있다. 코드에서 알 수 있듯이, 객체의 일부 속성만 설정하는 것도 가능하기 때문에 객체 생성 과정을 유연하게 만든다.
객체 생성 중 중간 관계가 노출될 수 있다.
Builder의 특징 중 하나는 chaining 기법을 사용하기 때문에 최종 연산인 .build() 메소드가 호출되어야 객체가 생성된다. 따라서 중간 상태가 노출되는 것을 방지할 수 있고, 객체의 불변성과 안정성을 유지할 수 있다.
그래서, Builder 사용을 지향하는 이유는?
Builder 사용을 지향하는 이유를 정리해보자면 다음과 같다.
- 객체 생성 과정을 단순화하고, 가독성을 높일 수 있다.
- 객체의 일부만 속성을 설정할 수 있다.
- chaining을 통해 여러 메소드 호출을 연결할 수 있기 때문에 중간 상태가 노출되는 것을 방지할 수 있다.
이제 Setter 사용법의 지양 이유를 알았으니 생성자나 Builder를 주로 사용해야겠다.
728x90
'Back-End > Spring Boot' 카테고리의 다른 글
[Spring Boot] Spring AOP (0) | 2024.10.10 |
---|---|
[Spring Boot] 스크래핑 비동기 처리 (6) | 2024.10.09 |
[Spring Boot] N+1 문제 (1) | 2024.10.05 |
[Spring Boot] JPA 쿼리 최적화 (1) | 2024.10.04 |
[Spring Boot] Logging 처리 (0) | 2023.11.27 |