우리는 어제 querydsl의 기본적인 API들을 살펴보고 변경사항도 같이 살펴봤다.
이번시간은 간단한 동적쿼리와 join에 대해 알아보자. 심도있는 것은 나중에 살펴보도록하고..
일단 엔티티부터 코드로 보자. 아래 엔티티로 공부를 할 예정이라 포스팅도 같이 했다. 추가되면 그때 그때 추가 하겠다.
@Entity
public class Account {
@Id
@GeneratedValue
@Column(name = "ACCOUNT_ID")
private Long id;
private String name;
private String password;
private String email;
@OneToMany(mappedBy = "account")
private List<Order> orders = new ArrayList<>();
//getter setter hashcode equals etc..
}
@Entity
@Table(name = "ORDERS")
public class Order {
@Id
@GeneratedValue
@Column(name = "ORDER_ID")
private Long id;
@ManyToOne
@JoinColumn(name = "ACCOUNT_ID")
private Account account;
@OneToMany(mappedBy = "order")
private List<OrderItem> orderItems = new ArrayList<>();
@Temporal(TemporalType.TIMESTAMP)
private Date orderDate;
//getter setter hashcode equals etc..
}
@Entity
@Table(name = "ORDER_ITEM")
public class OrderItem {
@Id
@GeneratedValue
@Column(name = "ORDER_ITEM_ID")
private Long id;
@ManyToOne
@JoinColumn(name = "ITEM_ID")
private Item item;
@ManyToOne
@JoinColumn(name = "ORDER_ID")
private Order order;
private Integer orderPrice;
private Integer count;
//getter setter hashcode equals etc..
}
@Entity
public class Item {
@Id
@GeneratedValue
@Column(name = "ITEM_ID")
private Long id;
private String name;
private Integer price;
private Integer stockQuantity;
//getter setter hashcode equals etc..
}
데이터들은 각자 원하는 대로 넣어 보자.
Order라는 레파지토리를 만들어서 아래와 같이 하자.
@Override
public List<Order> orders(){
QOrder order = QOrder.order;
QAccount account = QAccount.account;
return from(order)
.leftJoin(order.account, account).fetchJoin()
.fetch();
}
이것은 order와 account 엔티티를 leftjoin 한것이다. fetchJoin을 쓴 이유는 한방쿼리를 위해.. N+1을 막을라고 한 것이다. 이 예제에선 그닥 필요 없을지도 모르지만 그냥 넣어 뒀다.
일반 sql문과 비슷하다. from부터 시작해서 leftjoin, innerjoin, rightJoin 기타 등등이 있다. leftjoin 조인을 했지만 innerjoin, rightJoin등 문법 자체는 비슷비슷하다. 다음시간엔 좀 더 구체적으로 알아보겠다.
이번에는 동적쿼리이다. 동적쿼리라 해서 뭐 대단한 것도 없다.
@Override
public List<Order> orders(Long id){
QOrder order = QOrder.order;
QAccount account = QAccount.account;
JPQLQuery query = from(order)
.leftJoin(order.account, account);
if(id != null){
query.where(account.id.goe(id));
}
return query
.fetchJoin().fetch();
}
약간 예제가 좀 그렇지만 id가 null이 아닐때 id보다 accountid 크거나 같은 것을 조회하는 동적쿼리이다. 예제가 썩 맘에 들진 않지만 그래도 이렇게 하는 것이다 이해정도만 하면 될 듯싶다. goe는 크거나 같음을 의미한다. 이외에도 lt, gt, loe, eq, ne, like, between, max, min 등등 여러가지가 존재한다. 이것은 너무 많으므로 생략.. 나중에 그냥 한번씩 살펴보는 정도면 될 듯싶다.
위와 같이 하는 것 말고도 다른 방법이 존재 한다. BooleanBuilder를 써도 가능하다.
@Override
public List<Order> orders(Long id){
QOrder order = QOrder.order;
QAccount account = QAccount.account;
JPQLQuery query = from(order)
.leftJoin(order.account, account).fetchJoin();
BooleanBuilder booleanBuilder = new BooleanBuilder();
if(id != null){
booleanBuilder.and(account.id.goe(id));
}
query.where(booleanBuilder);
return query.fetch();
}
위와 같이 BooleanBuilder를 써써 동적 쿼리를 가능하게 할 수 있다.
이번시간에는 join과 동적쿼리에 대해서 알아봤다. 간단하게 알아봤지만 다음시간에는 조금더 심도있게 알아볼 예정이다.
아니면 서브쿼리를 먼저 할까.. 아무튼 필자가 먼저 하고 싶은거를 선택해서 다음에 진행 하겠다.
엔티티는 이번시간에 했던 엔티티를 계속적으로 할 듯 싶다.