2011-10-19 53 views
4

我有這樣的事情..多態「GET」使用Hibernate,多對一,InheritanceType.JOINED

有許多座位一個座位汽車類。座椅有一個子類LeatherSeat。

public class Car { 
    private Seat seat; 
    ... 
    @ManyToOne(fetch = FetchType.LAZY) 
    public Seat getSeat() { 
    return seat; 
    } 
    ... 
} 

@Entity 
@Inheritance(strategy=InheritanceType.JOINED) 
public class Seat { 
    private String id; 
    private String color; 
} 

@Entity 
public class LeatherSeat extends Seat { 
    private String leatherType; 
} 

當我創建我的車,讓我的車的座位上LeatherSeat它保存了所有正確的數據庫。當我想要獲得我的汽車(使用標準或查詢列表)並閱讀getSeat()時,座椅總是座椅,從不是皮革座椅。我不能施放(例外)並且看起來必須通過id手動獲取LeatherSeat。

這是使用連接繼承型還是我失去了一些東西的限制。我如何獲得座椅作爲皮革座椅?

回答

1

看來,如果你做一個懶惰的獲取,就像你與getSeat做,你將只得到父母,從來沒有子類。我試着用FetchType.EAGER和getSeat正確地返回一個LeatherSeat。

我不確定爲什麼Hibernate可以得到一輛帶有LeatherSeat時預先抓取,但冬眠似乎無法得到它做一個懶惰取時。似乎有什麼東西在那裏被打破。

有關於上InheritanceType.JOINED其中一點關於此情形作出鑑別列的車票。 https://hibernate.onjira.com/browse/ANN-140但票證被拒絕,表明hibernate過於優雅,無法爲InheritanceType.JOINED添加鑑別符。然而,它無法正確地返回延遲提取的子類。

那麼這張票https://hibernate.onjira.com/browse/HHH-271?focusedCommentId=44089#comment-44089是更具體到這個問題,答案是'我們如何知道什麼子類獲得懶惰的獲取?

這兩張票都是舊的並被拒絕。對我來說似乎是一個問題。但是現在你不得不改變爲不同的繼承類型或者使用渴望的獲取類型,因爲這是根據hibernate的設計而定的。

2

在遲緩情況下,座椅將是一個「代理」,當汽車被實例化被實例化。那時候,Hibernate並不知道這個座位是否是皮革的。

當你遍歷屬性,它是延遲加載,那麼Hibernate會知道,座椅的皮革,但是不能追溯改變類的代理權。但是,所有的數據都在那裏。如果您重寫了任何方法,座位將作爲LeatherSeat作出響應。

如果你真的需要施放此對象LeatherSeat,可以拆箱使用http://docs.jboss.org/hibernate/orm/3.2/api/org/hibernate/engine/PersistenceContext.html#unproxy(java.lang.Object)代理

看到這個博客要了解爲何代理將永遠是座椅,不LeatherSeat:http://sessionfactory.blogspot.co.uk/2010/08/hacking-lazy-loaded-inheritance.html

這在這裏Hibernate文檔簡要介紹了:http://docs.jboss.org/hibernate/core/3.3/reference/en/html/performance.html#performance-fetching-proxies