2012-04-13 7 views
8

JPA基準に関する質問があります。ここでJPA Criteria query Path.get left join is possible

は私のJPA基準クエリです:

select 
     inventoryi1_.PRODUCT_ID as col_0_0_, 
     inventoryi1_.FACILITY_ID as col_1_0_, 
     inventoryi1_.CUSTOMER_ID as col_2_0_ 
    from 
     INVENTORY_ITEM_DETAIL inventoryi0_ 
    inner join 
     INVENTORY_ITEM inventoryi1_ 
      on inventoryi0_.INVENTORY_ITEM_ID=inventoryi1_.ID 
    inner join 
     PRODUCT product2_ 
      on inventoryi1_.PRODUCT_ID=product2_.ID 
    inner join 
     FACILITY facility3_ 
      on inventoryi1_.FACILITY_ID=facility3_.ID 
    inner join 
     CUSTOMER customer4_ 
      on inventoryi1_.CUSTOMER_ID=customer4_.ID 
    where 
     inventoryi0_.EFFECTIVE_DATE<= ? 
    group by 
     inventoryi1_.PRODUCT_ID , 
     inventoryi1_.FACILITY_ID , 
     inventoryi1_.CUSTOMER_ID 

しかし、私は次のクエリをしたいと思います:ここで

CriteriaBuilder criteriaBuilder = getEm().getCriteriaBuilder(); 
CriteriaQuery<InventoryItemSumReport> query = criteriaBuilder.createQuery(InventoryItemSumReport.class); 
Root<InventoryItemDetail> from = query.from(InventoryItemDetail.class);  

Join<InventoryItemDetail, InventoryItem> joinItem = from.join(InventoryItemDetail_.inventoryItem); 

Predicate where = criteriaBuilder.lessThanOrEqualTo(from.get(InventoryItemDetail_.effectiveDate), date); 

query.multiselect(joinItem.get(InventoryItem_.product),joinItem.get(InventoryItem_.facility),joinItem.get(InventoryItem_.customer)); 
query.groupBy(joinItem.get(InventoryItem_.product),joinItem.get(InventoryItem_.facility),joinItem.get(InventoryItem_.customer)); 
query.where(where); 

TypedQuery<InventoryItemSumReport> createQuery = getEm().createQuery(query);  
List<InventoryItemSumReport> resultList = createQuery.getResultList(); 

は、JPAプロバイダによって生成結果のクエリで

select 
     inventoryi1_.PRODUCT_ID as col_0_0_, 
     inventoryi1_.FACILITY_ID as col_1_0_, 
     inventoryi1_.CUSTOMER_ID as col_2_0_ 
    from 
     INVENTORY_ITEM_DETAIL inventoryi0_ 
    inner join 
     INVENTORY_ITEM inventoryi1_ 
      on inventoryi0_.INVENTORY_ITEM_ID=inventoryi1_.ID 
    inner join 
     PRODUCT product2_ 
      on inventoryi1_.PRODUCT_ID=product2_.ID 
    inner join 
     FACILITY facility3_ 
      on inventoryi1_.FACILITY_ID=facility3_.ID 
    left join 
     CUSTOMER customer4_ 
      on inventoryi1_.CUSTOMER_ID=customer4_.ID 
    where 
     inventoryi0_.EFFECTIVE_DATE<= ? 
    group by 
     inventoryi1_.PRODUCT_ID , 
     inventoryi1_.FACILITY_ID , 
     inventoryi1_.CUSTOMER_ID 

は参加しましたお客様にはも結果を取得するCustomersはnullです。
Customer,Product,Facilityはすべてentiteであり、InventoryItemSumReportはValueオブジェクトまたはDTOです。それが動作する、以下のように

public class InventoryItemSumReport implements Serializable { 

    private static final long serialVersionUID = 1L; 

    private Product product; 
    private Facility facility; 
    private Customer customer; 

    public InventoryItemSumReport(Product product, Facility facility, Customer customer) { 
     super(); 
     this.product = product; 
     this.facility = facility; 
     this.customer = customer; 
    } 
} 

答えて

8

は、私が見つかりました:

CriteriaBuilder criteriaBuilder = getEm().getCriteriaBuilder(); 
CriteriaQuery<InventoryItemSumReport> query = criteriaBuilder.createQuery(InventoryItemSumReport.class); 
Root<InventoryItemDetail> from = query.from(InventoryItemDetail.class);  

Join<InventoryItemDetail, InventoryItem> joinItem = from.join(InventoryItemDetail_.inventoryItem); 

Predicate where = criteriaBuilder.lessThanOrEqualTo(from.get(InventoryItemDetail_.effectiveDate), date); 

Join<InventoryItem, Customer> joinCustomer = joinItem.join(InventoryItem_.customer, JoinType.LEFT); 
query.multiselect(joinItem.get(InventoryItem_.product),joinItem.get(InventoryItem_.facility),joinItem.get(InventoryItem_.customer)); 
query.groupBy(joinItem.get(InventoryItem_.product),joinItem.get(InventoryItem_.facility),joinCustomer); 
query.where(where); 

TypedQuery<InventoryItemSumReport> createQuery = getEm().createQuery(query);  
List<InventoryItemSumReport> resultList = createQuery.getResultList();