2015-05-09 34 views
0

有一個沒有關係的表和一個整數主鍵。使用NHibernate我想重新填充表在一個事務中,像這樣:NHibernate清除/截斷表和重新填充單個事務

  • openTrans
  • 刪除所有行
  • 插入新行(很多人都會有相同的ID與以前刪除)
  • commitTrans

然而,NHibernate拋出'具有相同標識符值的不同對象已與會話相關聯',我嘗試保存新實體。這是有道理的,因爲我實際上已經創建了一個具有相同Id的新實體。我嘗試通過覆蓋實體類上的GetHashCode和Equals來欺騙NHibernate,以便兩個具有相同ID的對象「相等」,但我得到相同的結果。

我可以採取的另一種方法是更新已存在的實體,刪除不在新數據集中的現有實體並添加新實體,但這是我希望避免的很多工作,因爲故事只是重新填充桌子。我當然可以在兩個會話中做到這一點,但我希望整個操作都是原子的。

+0

你能不能不要在此處使用NHibernate的? –

+0

我正在使用NHibernate。我現在已經實施了第二個選項,它給了我需要的確切行爲,儘管需要更多的努力。 –

+0

使用createsql和truncate刪除行。然後插入。那樣有用嗎? – Rippo

回答

2

選項1

session.Clear(); // to get rid associations of the objects in memory 
session.CreateQuery("delete from MyClass").ExecuteUpdate(); 
foreach(var entity in CreateNew()) 
    session.Save(entity); 

選項2

session.CreateQuery("delete from MyClass where Id not in (:ids)") 
    .SetParameterList("ids", newIds) 
    .ExecuteUpdate(); 
foreach (var id in newIds) 
{ 
    var entity = session.Get<MyClass>(id); // returns the cached instance if present or the database instance or null if non existant 
    if (entity == null) 
    { 
     entity = new MyClass { Id = id }; 
     session.Save(entity); 
    } 
    Populate(entity); 
} 

選項3

var newEntities = CreateNew(); 

session.CreateQuery("delete from MyClass where Id not in (:ids)") 
    .SetParameterList("ids", newEntities.Select(x => x.Id).ToArray()) 
    .ExecuteUpdate(); 

foreach(var entity in newEntities) 
    session.Merge(entity); // will get the object with the same id and copies over properties over 
+0

是查詢字符串文字還是NHibernate翻譯它的目標數據庫平臺?我假設字符串的格式可能會因不同的平臺而有所不同。我想盡可能保持代碼平臺不可知。 –

+0

文字是HQL,它是對象查詢語言和平臺無關的。我認爲'刪除MyClass的地方不在(:IDS)'也應該工作 – Firo

相關問題