• nHibernate学习小结及代理模板


      近日为学习Spring.net,开始上手nHibernate,其间遇到不少问题,但也小有收获,毕竟学习新框架是有曲线的

    现小结一下,算是汇报:

    1、关于配置文件
    在web项目中,大部分的配置都是在web.config中进行部署,这样的好处是整合了各种应用的配置,维护比较集中。
    由于使用的nHibernate为1.2.1GA,故而它对应的urn(统一资源名称,Uniform Resource Name, URN)为:“nhibernate-configuration-2.2”,这个常识性问题曾经困扰了我很久,运行时经常出现的异常诸如“not found section:'session-factory'”,其实是由于使用CodeSmith生成的模板文件(hbm.xml)中声明的urn为“nhibernate-configuration-2.0”所致。
    在web.config中,进行这样的配置,是正确的:

      <configSections>
        
    <section
                
    name="hibernate-configuration"
                type
    ="NHibernate.Cfg.ConfigurationSectionHandler, NHibernate" />
      
    </configSections>
      
    <hibernate-configuration xmlns="urn:nhibernate-configuration-2.2">
        
    <session-factory xmlns="urn:nhibernate-configuration-2.2">
          
    <property name="hibernate.connection.provider">NHibernate.Connection.DriverConnectionProvider</property>
          
    <property name="hibernate.connection.driver_class">NHibernate.Driver.SqlClientDriver</property>
          
    <property name="hibernate.connection.connection_string">Server=Locke.mo;database=woodigg;User Id=locke;Password=locke</property>
          
    <property name="hibernate.dialect">NHibernate.Dialect.MsSql2000Dialect</property>
          
    <property name="show_sql">false</property>
          
    <property name="use_proxy_validator">false</property>
          
    <property name="use_outer_join">true</property>
        
    </session-factory>
      
    </hibernate-configuration>

    2、使用Session的Load方法获取的对象只是个代理对象!
    这意味着这个对象,你只能在Session的生命周期内使用它,一旦Session关闭,此对象也终止服务,如果此后试图访问它,将抛出“Exception initializing proxy”异常。
    因为,在整个Session范围内,应用程序没有访问过这个代理类对象,那么代理类的实例一直不会被初始化,Hibernate不会执行任何select语句。(来自JavaEye)
    我的解决办法是,强制其实例化:     
      //在Session范围内显式初始化代理类实例
      if (!NHibernateUtil.IsInitialized(t))
        NHibernateUtil.Initialize(t);

    3、在《Spring in Action》一书中,作者提到Spring和其他数据持久化框架集成时,都提供了强大的模板类(如JdbcTemplate、HibernateTemplate等),真是令人羡慕的功能,毕竟大部分的DAO类里有着很多重复繁冗的代码,而这80%的代码其实是与具体业务无关的!
       既然现在还未到集成Spring.Net的地步,那就先为nHibernate单独实现一个模板吧:

    using System;
    using System.Collections.Generic;
    using System.Text;
    using NHibernate;
    using log4net;

    namespace woodigg.DAO
    {
        
    /// <summary>
        
    /// 增删改模板
        
    /// </summary>

        public class HibernateTemplate
        
    {
            
    /// <summary>
            
    /// 泛型读取
            
    /// </summary>
            
    /// <param name="obj"></param>
            
    /// <param name="id"></param>

            public static T LoadFromId<T>(object id)
            
    {
                ISession session 
    = Sessions.GetSession();
                
    try
                
    {
                    T t 
    = session.Load<T>(id);
                    
    //在Session范围内显式初始化代理类实例
                    if (!NHibernateUtil.IsInitialized(t))
                        NHibernateUtil.Initialize(t);
                    
    return t;
                }

                
    catch (Exception ex)
                
    {
                    ILog log 
    = LogManager.GetLogger(typeof(HibernateTemplate));
                    log.Error(ex.Message, ex);
                    
    return default(T);
                }

                
    finally
                
    {
                    session.Close();
                }

            }


            
    /// <summary>
            
    /// 存
            
    /// </summary>
            
    /// <param name="obj"></param>

            public static bool Save(object obj)
            
    {
                ISession session 
    = Sessions.GetSession();
                ITransaction trans 
    = null;
                
    try
                
    {
                    trans 
    = session.BeginTransaction();
                    session.Save(obj);
                    trans.Commit();
                    
    return true;
                }

                
    catch (Exception ex)
                
    {
                    ILog log 
    = LogManager.GetLogger(typeof(HibernateTemplate));
                    log.Error(ex.Message, ex);
                    trans.Rollback();
                    
    return false;
                }

                
    finally
                
    {
                    session.Close();
                }

            }


            
    /// <summary>
            
    /// 更新
            
    /// </summary>
            
    /// <param name="obj"></param>

            public static bool Update(object obj)
            
    {
                ISession session 
    = Sessions.GetSession();
                ITransaction trans 
    = null;
                
    try
                
    {
                    trans 
    = session.BeginTransaction();
                    session.Update(obj);
                    trans.Commit();
                    
    return true;
                }

                
    catch (Exception ex)
                
    {
                    ILog log 
    = LogManager.GetLogger(typeof(HibernateTemplate));
                    log.Error(ex.Message, ex);
                    trans.Rollback();
                    
    return false;
                }

                
    finally
                
    {
                    session.Close();
                }

            }


            
    /// <summary>
            
    /// 删
            
    /// </summary>
            
    /// <param name="obj"></param>

            public static bool Delete(object obj)
            
    {
                ISession session 
    = Sessions.GetSession();
                ITransaction trans 
    = null;
                
    try
                
    {
                    trans 
    = session.BeginTransaction();
                    session.Delete(obj);
                    trans.Commit();
                    
    return true;
                }

                
    catch (Exception ex)
                
    {
                    ILog log 
    = LogManager.GetLogger(typeof(HibernateTemplate));
                    log.Error(ex.Message, ex);
                    trans.Rollback();
                    
    return false;
                }

                
    finally
                
    {
                    session.Close();
                }

            }


            
    /// <summary>
            
    /// 查询
            
    /// </summary>
            
    /// <param name="obj"></param>

            public static IList<T> Seek<T>(string where)
            
    {
                ISession session 
    = Sessions.GetSession();
                
    try
                
    {
                    
    //模板反射
                    T obj = (T)System.Reflection.Assembly.GetAssembly(typeof(T)).CreateInstance(typeof(T).ToString());

                    
    string hql = string.Format("from {0} {1}",
                        obj.GetType().ToString(),
                        
    where.ToUpper().StartsWith("WHERE"? where : "WHERE " + where);

                    IQuery query 
    = session.CreateQuery(hql);

                    IList
    <T> list = query.List<T>();
                    
    return list;
                }

                
    catch (Exception ex)
                
    {
                    ILog log 
    = LogManager.GetLogger(typeof(HibernateTemplate));
                    log.Error(ex.Message, ex);
                    
    return null;
                }

                
    finally
                
    {
                    session.Close();
                }

            }

        }

    }


    差点忘了,它用到的SessionFactory:
    using System;
    using System.Collections.Generic;
    using System.Text;
    using System.Reflection;
    using NHibernate;
    using NHibernate.Cfg;

    namespace woodigg.DAO
    {
        
    public class Sessions
        
    {
            
    private static readonly object lockObj = new object();          // 用于singleton模式进行锁定
            private static ISessionFactory _factory;                        // sesssion 工厂

            
    public Sessions()
            
    {
            }


            
    /// <summary>
            
    /// 单一静态工厂
            
    /// </summary>

            public static ISessionFactory Factory
            
    {
                
    get {
                    
    if (_factory == null)
                    
    {
                        
    lock (lockObj)          // 保证线程安全
                        {
                            
    if (_factory == null)
                            
    {
                                
    // 查找hibernate.cfg.xml
                                Configuration cfg = new Configuration().Configure();
                                
    // 不需要mapping,直接获取当前运行程序集
                                cfg.AddAssembly(Assembly.GetExecutingAssembly());
                                _factory 
    = cfg.BuildSessionFactory();
                            }

                        }

                    }

                    
    return _factory;
                }

            }


            
    /// <summary>
            
    /// 打开一个会话连接
            
    /// </summary>
            
    /// <returns></returns>

            public static ISession GetSession()
            
    {
                
    return Factory.OpenSession();
            }

        }

    }
    Creative Commons License
    本作品采用知识共享署名-非商业性使用-相同方式共享 3.0 Unported许可协议
    欢迎转载,但必须保留文章的署名老莫的帐本子
    并保留此链接:http://moye.cnblogs.com/
    如有疑问请发邮件:moyerock@gmail.com
  • 相关阅读:
    C#中如何求时间间隔?
    Ilist<T> 转换成 DataSet
    EditPlus 快捷键
    Array和ArrayList的异同点
    sql server 查询数据库中有多少个表
    jquery + Css 模式对话框
    paddingtop、margintop和top的区别
    JQuery之ContextMenu(右键菜单)
    关于TextBox的Enable与ReadOnly属性
    AjaxToollit 3.5 使用整理
  • 原文地址:https://www.cnblogs.com/moye/p/1240792.html
Copyright © 2020-2023  润新知