簡體   English   中英

為什么Hibernate(JPA)對於ManyToOne關系忽略FetchType.LAZY?

[英]Why does Hibernate (JPA) ignore FetchType.LAZY for ManyToOne relations?

我有這個實體,因此我希望多對一的關系變得懶惰。

@Entity
public class Product {
    @ManyToOne(fetch=FetchType.LAZY)
    @JoinColumn(name = "atc_code_id")
    private ATCCode atcCode;
}

@Entity
public class ATCCode {
    @OneToMany(mappedBy = "atcCode")
    private Set<Product> products;
}

我正在使用以下代碼加載產品:

Query q = entityManager.createQuery("select p from Product as p");
List<Product> products = q.getResultList();

從休眠日志的倒數第二行中,我可以看到發出了第二個選擇來初始化atcCode的代理。 為什么?

17925 07 Aug 2015 11:45:20 SQL DEBUG 352066 kb - select product0_.id ...
17926 07 Aug 2015 11:45:20 Loader DEBUG 348515 kb - Result set row: 0
17927 07 Aug 2015 11:45:20 Loader DEBUG 348515 kb - Result row: EntityKey[com.galexis.search.importer.search.searchdb.model.Product#1]
17928 07 Aug 2015 11:45:20 Loader DEBUG 348515 kb - Result set row: 1
17929 07 Aug 2015 11:45:20 Loader DEBUG 348515 kb - Result row: EntityKey[com.galexis.search.importer.search.searchdb.model.Product#2]
17929 07 Aug 2015 11:45:20 TwoPhaseLoad DEBUG 348515 kb - Resolving associations for [com.galexis.search.importer.search.searchdb.model.Product#1]
17931 07 Aug 2015 11:45:20 TwoPhaseLoad DEBUG 348515 kb - Done materializing entity [com.galexis.search.importer.search.searchdb.model.Product#1]
17931 07 Aug 2015 11:45:20 TwoPhaseLoad DEBUG 348515 kb - Resolving associations for [com.galexis.search.importer.search.searchdb.model.Product#2]
17931 07 Aug 2015 11:45:20 TwoPhaseLoad DEBUG 348515 kb - Done materializing entity [com.galexis.search.importer.search.searchdb.model.Product#2]
17931 07 Aug 2015 11:45:20 SessionImpl DEBUG 348515 kb - Initializing proxy: [com.galexis.search.importer.search.searchdb.model.ATCCode#100]
17931 07 Aug 2015 11:45:20 SQL DEBUG 348515 kb - select atccode0_.id  ...

我的期望是返回了atcCode的代理。 只要我不訪問atcCode,就不應從數據庫中加載它。

有什么想法為什么休眠初始化代理?

這是對問題的簡要說明。 實際上,我在產品上有很多多對一的關系。 他們都被宣布為懶惰。 但是,由於實際上它們加載得很重,因此我得到了很大的選擇N + 1性能損失。

經過大量搜索之后,我最終在org.hibernate.internal.SessionImpl中設置了一個斷點,其中生成了日志語句Initializing proxy: org.hibernate.internal.SessionImpl 在堆棧跟蹤中,我終於在Product找到了它:

@PostLoad
public void postLoad() {
    atcCode.getCode();
}

這將導致休眠初始化代理。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM