신일현

신일현님의 아티클

신일현

신일현

Querydsl 동적 쿼리를 사용해보자!!

프로그램을 개발하다보면 조회 시점에 조회 조건이 동적으로 바뀌어야 하는 상황이 빈번하게 발생한다. (검색기능, 필터기능 등..)

DB에서 값을 조회 시 when/case 등의 문법을 사용하여 해결하는 경우가 있는데.. 개인적으로 when/case 문은 안티패턴이라고 생각한다.. (SQL 너무 복잡하게 만든다) 그래서 어플리케이션 계층에서 해결하는 등의 방식으로 해결해왔었다.

그런데 이런 동적 쿼리가 필요한 상황을 Querydsl을 사용하면 쉽고 효과적으로 해결할 수 있다.

Querydsl을 사용하여 동적 쿼리를 해결하는 두가지 방식이 있다.

  • BooleanBuilder

  • Where 다중 파라미터 사용 (BooleanExpression)

BooleanBuilder

BooleanBuilder를 이용해서 조건들을 이어 붙여 where문에 넣어주는 방식이다.
.and(), .or() 등을 이용해 조건을 추가할 수 있다.


private List<Member> searchMember1(String usernameCond, Integer ageCond) {
    
    BooleanBuilder builder = new BooleanBuilder();
    
    if (usernameCond != null) {
        builder.and(member.username.eq(usernameCond)); 
    }

    if (ageCond != null) { 
    	builder.and(member.age.eq(ageCond));
    }
    
    return queryFactory
        .selectFrom(member)
        .where(builder)
        .fetch();
}

Where 다중 파라미터 사용 (BooleanExpression)

BooleanExcpression 타입을 리턴하는 매서드를 만들어 조건을 추가하는 방식인데
매서드로 만들어서 사용하기 때문에 어떤 조건인지 명확히 알 수 있고 재사용도 가능하다.

 private List<Member> searchMember2(String usernameCond, Integer ageCond) {

     return queryFactory
          .selectFrom(member)
          .where(usernameEq(usernameCond),ageEq(ageCond))
          .fetch();
}

// 결과가 null 이면 where()에서 무시된다.
private BooleanExpression usernameEq(String usernameCond) {
    return usernameCond != null ? member.username.eq(usernameCond) : null;
}

private BooleanExpression ageEq(Integer ageCond) {
    return ageCond != null ? member.age.eq(ageCond) : null;
}

결론

Querydsl을 사용하여 동적 쿼리를 효과적으로 해결할 수 있었다.

특히 Where 다중 파라미터 사용 방식 BooleanExpression을 사용하면 코드 가독성 및 재사용의 이점이 있기 때문에 좋은 방법인 것 같다.

7
0