簡體   English   中英

JPA Hibernate Lazy多對一提取代理

[英]JPA Hibernate Lazy many-to-one fetch proxy

我正在使用JPA 2.1和Hibernate 4.3.7

我試圖調整我的應用程序,所以我將關系變為懶惰,只獲取我需要的東西

我有多對一關系的問題,當我再次加載實體時轉向懶惰Hibernate通過代理替換實體即使我獲取實體並且此代理不在視圖部分(JSF)中工作應用程序。 當多對一處於急切模式時,問題會消失,但即使我不需要它們,休眠也會為每個多對一執行一個選擇

@Entity
public class Department {
    @Id
    private Integer id;

    //...
}

1 /

@Entity
public class Employee {
    @Id
    private Integer id;

    @ManyToOne(fetch = FetchType.LAZY, optional = true)
    @JoinColumn(name = "id_department", referencedColumnName = "id")
    private Department department;

    //...
}

JPQL查詢:

SELECT e FROM Employee e LEFT JOIN FETCH e.department WHERE e.id=:id

=>一個選擇查詢=>更快但部門的類型為Department _ $$ _ jvst3ac_5f(employee.getDepartment()。getClass()。getCanonicalName())並且此代理在應用程序的視圖部分不起作用

2 /

@Entity
public class Employee {
    @Id
    private Integer id;

    @ManyToOne(fetch = FetchType.EAGER, optional = true)
    @JoinColumn(name = "id_department", referencedColumnName = "id")
    private Department department;

    //...
}

JPQL查詢:

SELECT e FROM Employee e WHERE e.id=:id

=>兩個選擇=>較慢但部門作為部門加載,一切都在應用程序的視圖部分正常

這種關系是單向的,Department沒有提及emplyees

使用FETCH JOIN時,這可能是沒有代理的部門嗎?


在Luiggi的響應之后,我將使用懶惰的多對一+獲取連接來獲取數據。 當我做employee.getDepartment()。toString()我有部門{id = 11,...}但是這個部門的類仍然是Department _ $$ _ jvst3ac_5f。 由於我不知道,即使獲取數據,JSF / PrimeFaces selectOneMenu組件也無法正常運行HibernateProxy

除了@ManyToOne(fetch = FetchType.LAZY)之外,我還嘗試使用Hibernate注釋@LazyToOne(LazyToOneOption.FALSE),但結果類似於@ManyToOne(fetch = FetchType.EAGER)...

問題是,當您使用延遲加載時,您將獲得該類的代理(如您所述),並且只有在hibernatesession仍處於打開狀態時 ,此代理才能從數據庫中獲取數據。 在將數據返回到視圖時,似乎關閉了會話,因此在嘗試使用視圖中的延遲加載字段時,您將獲得異常。

可能的解決方案:

  • 將字段保持為fetch急切並為每個查詢支付實體的開銷(可能這不好並且可能影響性能,但是是一種解決方案)。
  • 將您的字段保持為惰性並在關閉Hibernate會話之前使用正確的get方法,以便代理在會話關閉后檢索要使用的相關數據。

暫無
暫無

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

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