亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb

首頁 > 學院 > 開發設計 > 正文

《NHibernate One Session Per Request 簡單實現》勘誤

2019-11-17 03:49:50
字體:
來源:轉載
供稿:網友
使用 NHibernate 進行 Web 開發的朋友大多都知道 session-Per-Request 模式,但網上真正能夠正確使用的例子不多,網上包括園子里好多文章犯了同一個錯誤,而這個錯誤確一直在散播...

先來看園子里 Flyear 的一篇文章 《NHibernate One Session Per Request 簡單實現》。

首先對 NHibernate 進行配置沒有錯:

    <PRoperty name='current_session_context_class'>web</property>
錯誤在類 NHinbernateSessionFactory(類名都寫錯了) 中,NHinbernateSessionFactory.GetCurrentSession 不應包含對 HttpContext 的操作,GetCurrentSession 其實本應很簡單,請參見(類名改成 NHibernateHelper,簡短):

    public sealed class NHibernateHelper
    {
        public static readonly ISessionFactory SessionFactory;
        static NHibernateHelper()
        {
            SessionFactory = new Configuration()
                .Configure()
                .AddAssembly(/**/)
                .BuildSessionFactory();
        }
        public static ISession GetCurrentSession()
        {
            return SessionFactory.GetCurrentSession();
        }
    }
將 current_session_context_class 配置為 web,NHibernate 在初始化時會生成 NHibernate.Context.WebSessionContext 類的實例,WebSessionContext 類源碼如下:

    [Serializable]
    public class WebSessionContext : MapBasedSessionContext
    {
        // Fields
        private const string SessionFactoryMapKey = "NHibernate.Context.WebSessionContext.SessionFactoryMapKey";

        // Methods
        public WebSessionContext(ISessionFactoryImplementor factory) : base(factory)
        {  }

        protected override IDictionary GetMap()
        {
            return (HttpContext.Current.Items[SessionFactoryMapKey] as IDictionary);
        }

        protected override void SetMap(IDictionary value)
        {
            HttpContext.Current.Items[SessionFactoryMapKey] = value;
        }
    }
WebSessionContext 實現了 Session-Per-Request 模式,它封裝了 HttpContext ,因此我們不需要在我們的輔助類(NHibernateSessionFactory 或是 NHibernateHelper)中再對 HttpContext 進行操作。

我們只需要從 WebSessionContext 的實例中獲取 Session 即可。從WebSessionContext 類中獲取當前 ISession 相當簡單,因為 WebSessionContext 實現了 ICurrentSessionContext 接口:

    public interface ICurrentSessionContext
    {
        ISession CurrentSession();
    }


NHibernate.Context 命名空間中的類和接口

(說明:current_session_context_class 還可以配置為 Managed_web、Call、thread_static,分別對應類 ManagedWebSessionContext、CallSessionContext、ThreadStaticSessionContext)

在實際使用中我們并不需要直接調用 WebSessionContext 的 CurrentSession() 方法,因為 ISessionFactory 提供了一個更簡單的方法讓我們能一步獲取到 Session:

    public interface ISessionFactory : IDisposable
    {
        ISession GetCurrentSession();
        //......
    }


下面探討一下 ISessionFactory.GetCurrentSession 方法的具體實現:

Configuration.BuildSessionFactory 方法實際返回的是 SessionFactoryImpl 類的實例,讓我們簡單看一下 SessionFactoryImpl 的部分代碼吧:

1     public sealed class SessionFactoryImpl
2         : ISessionFactoryImplementor, IMapping, ISessionFactory, IDisposable, IObjectReference
3     {
4         private readonly ICurrentSessionContext currentSessionContext;
5
6         public ISession GetCurrentSession()
7         {
8             if (this.currentSessionContext == null)
9             {
10                 throw new HibernateException(
11                     "No CurrentSessionContext configured (set the property current_session_context_class)!");
12             }
13             return this.currentSessionContext.CurrentSession();
14         }
15
16         public ICurrentSessionContext CurrentSessionContext
17         {
18             get { return this.currentSessionContext; }
19         }
20
21         private ICurrentSessionContext BuildCurrentSessionContext()
22         {
23             string name = PropertiesHelper.GetString("current_session_context_class", this.properties, null);
24             string str2 = name;
25             if (str2 != null)
26             {
27                 if (str2 == "call") return new CallSessionContext(this);
28                 if (str2 == "thread_static") return new ThreadStaticSessionContext(this);
29                 if (str2 == "web") return new WebSessionContext(this);
30                 if (str2 == "managed_web") return new ManagedWebSessionContext(this);
31             }
32             else
33                 return null;
34             try
35             {
36                 Type type = ReflectHelper.ClassForName(name);
37                 return (ICurrentSessionContext)Environment.BytecodeProvider.ObjectsFactory
38                     .CreateInstance(type, new object[] { this });
39             }
40             catch (Exception exception)
41             {
42                 log.Error("Unable to construct current session context [" + name + "]", exception);
43                 return null;
44             }
45         }
46     //......
47     }

SessionFactoryImpl 在實例化時會調用 BuildCurrentSessionContext() 方法(行21)為 currentSessionContext 字段賦值,具體值有配置文件中的 current_session_context_class 決定。

ISessionFactory 的 GetCurrentSession()  調用的是 ICurrentSessionContext 的 CurrentSession()(行6) 方法。

上面的代碼相當簡單,想必大家都已經明明白白了。



《NHibernate One Session Per Request 簡單實現》 一文中還有兩處不太恰當的地方:

1. 并不是每一次請求都需要一個 Session 來訪問數據庫。文中 Global.asax 的代碼給所有的請求在開始的時候都進行WebSessionContext.Bind(),會照成很多 Session 的浪費,雖然 NHibernate 的 Session 是輕量級的,較為合理的做法是在“真正需要”時綁定。

2. 因為 WebSessionContext.Unbind 方法需要一個 ISessionFactory 接口的實例,迫使用我們的輔助類(NHibernateSessionFactory 或是 NHibernateHelper)公開 SessionFactory。

第一個問題比較容易解決,留在回復中和大家交流吧。

第二個問題我會在下一篇隨筆中解答。



本人學習 NHibernate 時間也不長,屬于新手,如有錯誤,歡迎指正!


發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
亚洲香蕉成人av网站在线观看_欧美精品成人91久久久久久久_久久久久久久久久久亚洲_热久久视久久精品18亚洲精品_国产精自产拍久久久久久_亚洲色图国产精品_91精品国产网站_中文字幕欧美日韩精品_国产精品久久久久久亚洲调教_国产精品久久一区_性夜试看影院91社区_97在线观看视频国产_68精品久久久久久欧美_欧美精品在线观看_国产精品一区二区久久精品_欧美老女人bb
欧美亚洲一区在线| 国产精品久久久久久中文字| 国产精品av电影| 最近中文字幕日韩精品| 久久精品国产2020观看福利| 日韩午夜在线视频| 欧美成人激情视频| 国产亚洲精品综合一区91| 日韩在线免费高清视频| 欧美做受高潮电影o| 亚洲精品电影在线| 亚洲欧洲午夜一线一品| xvideos亚洲| 国产+成+人+亚洲欧洲| 国产欧美精品日韩| 日韩在线观看免费全| 国产精品嫩草影院久久久| 人九九综合九九宗合| 日韩精品在线免费观看视频| 欧美在线播放视频| 国产精品夜色7777狼人| 人人做人人澡人人爽欧美| 欧美电影电视剧在线观看| 色综合久久中文字幕综合网小说| 国产综合在线观看视频| 欧美激情中文字幕在线| 777午夜精品福利在线观看| 少妇高潮 亚洲精品| 久久频这里精品99香蕉| 国语自产精品视频在线看抢先版图片| 欧美巨乳美女视频| 亚洲精品国产精品国自产在线| 亚洲国产美女久久久久| 欧美一级bbbbb性bbbb喷潮片| 国产不卡一区二区在线播放| 91九色综合久久| 久久这里只有精品99| 久久综合网hezyo| 色偷偷亚洲男人天堂| 国产精品91视频| 岛国av在线不卡| 91香蕉嫩草影院入口| 国产精品一二区| 久久亚洲春色中文字幕| 亚洲男人的天堂在线| 国产精品久久久久久久久久久久久| 一区二区在线视频| 成人a免费视频| 欧美重口另类videos人妖| 国产丝袜一区二区三区免费视频| 欧美极品xxxx| 中文字幕欧美视频在线| 日韩精品在线观看一区| 国产精品精品一区二区三区午夜版| 欧美色欧美亚洲高清在线视频| 国产精品久久久久77777| 日本欧美一二三区| 中文字幕亚洲国产| 91久久精品在线| 久久久久久久久久久久av| 久久精品国产久精国产思思| 日韩亚洲精品视频| 国自产精品手机在线观看视频| 精品国产999| 久久成年人视频| 日韩精品久久久久| 久久成人18免费网站| 日本精品久久久久影院| 深夜福利国产精品| 欧美电影在线观看完整版| 日韩黄在线观看| 亚洲精品成人久久久| 日韩中文字幕在线观看| 亚洲美女精品成人在线视频| 国产精品久久久久久影视| 国产999精品| 欧美一级电影在线| 性色av一区二区咪爱| 日韩av快播网址| 日韩中文在线中文网三级| 欧美性极品xxxx做受| 亚洲国产另类 国产精品国产免费| 欧美怡红院视频一区二区三区| 精品国内自产拍在线观看| 4k岛国日韩精品**专区| 色婷婷综合久久久久中文字幕1| 91视频免费在线| 国产欧美日韩精品丝袜高跟鞋| 久久艹在线视频| 亚洲成avwww人| 亚洲欧美另类人妖| 红桃av永久久久| 亚洲男人天堂网| 亚洲欧美国产视频| 欧美极品少妇xxxxⅹ裸体艺术| 欧美亚洲另类激情另类| 一本色道久久综合亚洲精品小说| 97在线视频免费| 国产欧美日韩中文| 欲色天天网综合久久| 欧美性69xxxx肥| 国产91网红主播在线观看| 亚洲第一免费播放区| 国产精品日韩一区| 亚洲天堂免费观看| 色中色综合影院手机版在线观看| 最近2019年日本中文免费字幕| 欧洲日韩成人av| 日韩精品极品视频免费观看| 国产一区二区三区18| 久久久久久综合网天天| 欧美精品久久久久久久久久| 中文字幕免费精品一区| 日产精品99久久久久久| 久久人人看视频| 国产成人在线一区二区| 国产欧美一区二区白浆黑人| 色哟哟亚洲精品一区二区| 欧美国产第二页| 成人国产精品久久久久久亚洲| 日本一区二区在线播放| 国产精品日日做人人爱| 欧美一性一乱一交一视频| 国产丝袜高跟一区| 国产精品专区第二| 国产在线观看精品| 亚洲欧美日韩精品| 国产精品黄视频| 国产精品亚洲综合天堂夜夜| 日韩精品在线影院| 色哟哟亚洲精品一区二区| 久久精品99无色码中文字幕| 国产精品久久久999| 午夜精品视频在线| 97超视频免费观看| 久久久久久尹人网香蕉| 成人黄色免费片| 国产精品久久久久久久av大片| 亚洲人成电影在线播放| 国模极品一区二区三区| 日韩成人av在线| 日韩www在线| 欧美午夜影院在线视频| 亚洲欧美日韩视频一区| 日韩精品中文字幕在线播放| 久久久亚洲国产| 色噜噜狠狠狠综合曰曰曰88av| 在线日韩精品视频| 91精品国产亚洲| 久久久久久久久国产| 国产精品午夜一区二区欲梦| 国产偷国产偷亚洲清高网站| 日韩精品极品在线观看播放免费视频| 97精品视频在线观看| 欧美丰满少妇xxxxx做受| 精品久久久久久久久中文字幕| 日韩网站免费观看高清| 国产精品无码专区在线观看| 久久久亚洲福利精品午夜| 亚洲第一网站免费视频| 精品色蜜蜜精品视频在线观看| 国产伦精品一区二区三区精品视频| 国产69精品久久久久99| 在线色欧美三级视频|