2012-04-02 91 views
4

我觀察的讀取與條件查詢列表屬性時,我認爲是在JPA 2意外的行爲。JPA標準中獲取列表查詢重複值

我的查詢如下(它的提取物):

CriteriaBuilder b = em.getCriteriaBuilder(); 
CriteriaQuery<MainObject> c = b.createQuery(MainObject.class); 
Root<MainObject> root = c.from(MainObject.class); 
Join<MainObject, FirstFetch> firstFetch = (Join<MainObject, FirstFetch>) root.fetch(MainObject_.firstFetch); 
firstFetch.fetch(FirstFetch_.secondFetch); //secondFetch is a list 
c.select(root).distinct(true); 

(所以我們可以說,我取一個列表作爲一個對象的屬性的屬性。)

事情是當查詢返回多個結果時,secondFetch值會重複多次以返回行。每個firstFetch應該只有一個secondFetchñ代替。 我在這種情況下看到的唯一特別之處在於所有MainObjects碰巧有相同FirstFetch實例。 所以我的猜測是連接正在越過,這是正常的,但隨後JPA未能將secondFetch對象分配給每個firstFetchs

映射應該不會太特別,the're或多或少這樣

@Entity 
@Table(name="mainobject") 
public class MainObject{ 
    //... 
    private FirstFetch firstFetch; 

    @ManyToOne(fetch=FetchType.LAZY) 
    @JoinColumn(name="mainObject_column") 
    public FirstFetch getFirstFetch() { 
    return firstFetch; 
    } 
} 

@Entity 
@Table(name="firstFetch") 
public class FirstFetch{ 
    //... 
    private List<SecondFetch> secondFetch; 

    @OneToMany(mappedBy="secondFetch") 
    public List<SecondFetch> getSecondFetch() { 
     return secondFetch; 
    } 
} 

&終於

@Entity 
@Table(name="secondFetch") 
public class SecondFetch { 
    //.... 
    private FirstFetch firstFetch; //bidirectional 

    @ManyToOne 
    @JoinColumn(name="column") 
    public FirstFetch getFirstFetch() { 
     return firstFetch; 
    } 
} 

我一直在尋找某種截然不同的句子適用到取,但有沒有(本來是一個「補丁」反正...)

如果我改變

List<SecondFetch> 

Set<SecondFetch> 

我會得到預期的結果歸功於套',所以我確實覺得這是JPA列表中的一種不當行爲。

我不是專家,不過,所以我可以perfectlly可以使得在映射或查詢的一些錯誤。 任何反饋都非常歡迎幫助清除此問題。 謝謝。

+0

您使用的是JPA提供程序?可能是一個錯誤。 – James 2012-04-03 14:22:28

+0

我正在使用JBoss 6.1.0的默認提供程序,如果我沒有錯,這將是Hibernate 3.6.6 Final。 – 2012-04-05 13:21:04

+0

我有完全相同的問題。 我使用標準api來獲取像這樣的(第二個)列表: d.fetch(FirstFetch_.secondFetch,JoinType.LEFT); – Jens 2012-04-19 07:50:27

回答

3

我有完全相同的問題,但我使用JPA標準API做查詢。

經過一番研究,我發現,你已經提到的(但不可用,因爲你沒有使用標準的API)的解決方案:使用distinct

使用JPA標準,它應該是這樣的:

CriteriaQuery<FirstFetch> query = cb.createQuery(FirstFetch.class); 
Root<AbschnittC> root = query.from(FirstFetch.class); 
root.fetch(FirstFetch_.secondFetch, JoinType.LEFT); 
query.distinct(true); 

不使用query.distinct(true);結果集與對象在secondFetch列表中的量成倍增加。

休眠確實有像DISTINCT_ROOT_ENTITY這聽起來比只是設置一個查詢不同。但我沒有進一步調查這一點。我也使用Hibernate作爲JPA提供者。也許在JPA中設置query截然不同,它使用與Hibernates DISTINCT_ROOT_ENTITY相同的代碼?

+0

感謝您的反饋,我會看看這個DISTINCT_ROOT_ENTITY並儘快更新 – 2012-04-23 21:52:03

+0

您的示例只能執行一次fetch();我不認爲它和上面描述的一樣。 – rakslice 2014-07-16 18:36:38