2011-12-01 88 views
0

我正在構建的Web應用程序中使用NHibernate。用戶可以下標零個或多個郵件列表(共有8個)。這在屏幕上用每個郵件列表的複選框表示。NHibernate - 我如何一次更新多個布爾型字段

我想用NHibernate來一次更新這些。一個非常簡單的SQL查詢將是:

update mail_subscriptions set subscribed = true where mailing_list_id in (21,14,15,19) and user_id = 'me' 

什麼是NHibernate的通過執行此更新,這樣我可以做一個往返到數據庫的乾淨的方式? 在此先感謝

JP

回答

2

NHibernate的可能無法更新你上面顯示的方式mail_subscriptions但它可以使用批量查詢,做到在單次往返到數據庫。

此示例考慮Subscriptions映射爲一個Component使用HasMany雖然大致相同的技術可以如果映射只是一個普通的HasMany使用。我還假設每個用戶已經在mail_subscriptions表中爲subscribed的每個郵寄列表設置爲false

public class User{ 
    public virtual string Id {get; set;} 
    public virtual IList<MailSubscription> Subscriptions {get; set;} 
} 

public class MailSubscription{ 
    public virtual int ListId {get; set;} 
    public virtual bool Subscribed {get; set;} 
} 

public void UpdateSubscriptions(string userid, int[] mailingListIds){ 
    var user = session.Get<User>(userid); 
    foreach(var sub in 
     user.Subscriptions.Where(x=> mailingListIds.Contains(x.ListId))){ 
     sub.Subscribed=true; 
    } 
    session.Update(user); 
} 

現在當工作單元完成後,您應該看到像這樣產生的SQL作爲單次往返數據庫發送。

update mail_subscriptions set subscribed=true where user_id='me' and listid=21 
update mail_subscriptions set subscribed=true where user_id='me' and listid=14 
update mail_subscriptions set subscribed=true where user_id='me' and listid=15 
update mail_subscriptions set subscribed=true where user_id='me' and listid=19 
2

我認爲NHibernate的功能,你追求的是被稱爲可執行DML

Ayende的博客文章舉例爲http://ayende.com/blog/4037/nhibernate-executable-dml

根據您的實體及其屬性的名稱,並假設你有一個叫做會話的ISession實例變量,你將需要執行一個HQL查詢類似:

session.CreateQuery("update MailSubscriptions set Subscribed = true where MailingList.Id in (21,14,15,19) and User.Id = 'me'") 
    .ExecuteUpdate(); 

現在,話雖如此,我想在你描述的用例中(更新一個集合根集合中的一些條目),不需要使用可執行的DML。馬克佩裏有正確的想法 - 你應該簡單地修改適當的實體上的布爾值,並以通常的方式刷新會話。如果ADO.NET批處理配置適當,則子條目將導致多個更新語句在單個數據庫調用中發送到RDBMS。

相關問題