: 스펙을 생성하다 보면 다음 코드처럼 조건에 따라 스펙을 조합해야할 때가 있다.
Specification<MemberData> spec = Specification.where(null);
if(searchRequest.isOnlyNotBlocked()) {
spec = spec.and(MemberDataSpecs.nonBlocked());
}
if(StringUtils.hasText(searchRequest.getName())) {
spec = spec.and(MemberDataSpecs.nameLike(searchRequest.getName()));
}
List<MemberData> results = memberDataDao.findAll(spec, PageRequest.of(0, 5));
Java
복사
: 이 코드는 if와 각 스펙을 조합하는 코드가 섞여있어 혼동하기 좋고 복잡한 구조를 갖는다. 이를 보완하기 위해 스펙 빌더를 만들어 사용한다.
Specification<MemberData> spec = SpecBuilder.builder(MemberData.class)
.ifTrue(searchRequest.isOnlyNotBlocked(),
() -> MemberDataSpecs.nonBlocked())
.ifHasText(searchRequest.getName(),
name -> MemberDataSpecs.nameLike(searchRequest.getName()))
.toSpec();
List<MemberData> result = memberDataDao.findAll(spec, PageRequest.of(0, 5));
Java
복사
: if 블록을 사용할 때와 비교해서 코드 양은 비슷한데, 메서드를 사용해서 조건을 표현했고 메서드 호출 체인으로 연속된 변수 할당을 줄여 코드 가독성을 높이고 구조가 단순해졌다.
: 스펙 빌더는 and(), ifHasText(), ifTrue() 메서드가 있는데 이외에 필요한 메서드는 추가해서 사용하면 된다.