2012-08-13 64 views
0

我們正在向我們的應用程序添加修訂歷史記錄,並且我們遇到了有關將檔案文檔嵌入到歷史對象中的一些問題。我們的狀態如下這樣:在morphia中帶有@Id的嵌入對象

@ToString 
@EqualsAndHashCode 
@Entity("bookOrder") 
@Converters({DateTimeConverter.class, LocalDateConverter.class}) 
public class BookOrderState { 
    @Id 
    @Getter 
    private Long id; 

    @Indexed 
    @Getter 
    private final BookOrderStatus status; 

    @Getter private Long version; 
... 

和我們的歷史對象的樣子:

@ToString 
@Entity("bookOrderHistory") 
@Converters(DateTimeConverter.class) 
public class BookOrderStateHistory { 

    @Id 
    @Getter 
    private String id; 

    @Getter 
    private DateTime createdDate; 

    @Getter 
    private BookOrderState bookOrder; 
... 

當我們更新我們從數據庫中抓取其當前狀態的訂單包裹它的歷史對象都有自己的ID和時間戳並將新的bookOrderStateHistory和更新的bookOrderState保存到數據庫。此過程可正確寫入,但在檢索時,我們最終會得到多個具有相同bookOrderState的唯一歷史記錄對象。我們將其追溯到BookOrderState上的@Id。由於許多歷史對象的狀態對象具有相同的_id(但與對象的實際狀態有所不同),因此morphia似乎假定它們都應獲得相同的狀態對象。我們一起入侵了一種攔截嵌入式狀態對象的方法,並在寫入時將其_id切換爲id(並且在讀取時相反),但這種感覺不對。

Tl; dr:有一種簡單的方法可以防止當一個對象位於另一個文檔內時發生嗎啡嗎?

回答

1

我正在做幾乎完全一樣的事情使用Morphia,並沒有遇到任何問題。我在上面的代碼中沒有看到它,但是如果「bookOrder」屬性用@Reference註釋,那麼你會看到你描述的行爲。如果你不把@Reference放在你的位置,那麼Morphia默認爲@Embedded,所以你應該沒問題。
我有一個名爲「快照」,我使用的存儲對象的歷史簡單的類:

@Entity("snapshots") 
public class Snapshot<T> 
{ 
    @Id 
    protected ObjectId id; 

    @Embedded 
    protected T data; 
} 

當一個對象改變我創建它的快照和快照保存到數據庫中。使用下面的簡單的測試情況下,我似乎得到正確的行爲:

Point pt = new Point(); 
pt.setLatitude(40.0); 
pt.setLongitude(40.0); 

ds.save(pt); //ds is Datastore 

Snapshot<Point> ts1 = new Snapshot<Point>(); 
ts1.setData(pt); 
ds.save(ts1); 

pt.setLatitude(50.0); 
ds.save(pt); 

pt = ds.get(Point.class, pt.getId()); 

Snapshot<Point> ts2 = new Snapshot<Point>(); 
ts2.setData(pt); 

ds.save(ts2); 

ts1 = ds.get(Snapshot.class, ts1.getId()); 
ts2 = ds.get(Snapshot.class, ts2.getId()); 

Assert.assertEquals(40.0, ts1.getData().getLatitude()); 
Assert.assertEquals(50.0, ts2.getData().getLatitude()); 

Assert.assertEquals(40.0, ts1.getData().getLongitude()); 
Assert.assertEquals(40.0, ts2.getData().getLongitude()); 

在這兩個快照點具有相同的ObjectId作爲原點對象,但在「TS2」的點有50.0,而點緯度在「ts1」中的緯度爲40.0。當對象被插入數據庫並且永​​遠不會改變時,ObjectId值被分配(http://www.mongodb.org/display/DOCS/Object+IDs)。

對不起,我不確定你的問題到底是什麼,但想讓你知道我正在做一些非常相似的事情,它似乎在工作。也許嘗試在BookOrderStateHistory中添加@Embedded註釋到「bookOrder」?

祝你好運!