zoukankan      html  css  js  c++  java
  • 如何理解Hibernate中的HibernateSessionFactory类

    package com.zz.util;
    
    import org.hibernate.HibernateException;
    import org.hibernate.Session;
    import org.hibernate.cfg.Configuration;
    
    /**
     * Configures and provides access to Hibernate sessions, tied to the
     * current thread of execution.  Follows the Thread Local Session
     * pattern, see {@link http://hibernate.org/42.html }.
     */
    public class HibernateSessionFactory {
    
        /** 
         * Location of hibernate.cfg.xml file.
         * Location should be on the classpath as Hibernate uses  
         * #resourceAsStream style lookup for its configuration file. 
         * The default classpath location of the hibernate config file is 
         * in the default package. Use #setConfigFile() to update 
         * the location of the configuration file for the current session.   
         */
    	private static final ThreadLocal<Session> threadLocal = new ThreadLocal<Session>();
        private static org.hibernate.SessionFactory sessionFactory;
    	
        private static Configuration configuration = new Configuration();
        private static String CONFIG_FILE_LOCATION = "/hibernate.cfg.xml";
        private static String configFile = CONFIG_FILE_LOCATION;
    
    	static {
        	try {
    			configuration.configure(configFile);
    			sessionFactory = configuration.buildSessionFactory();
    		} catch (Exception e) {
    			System.err.println("%%%% Error Creating SessionFactory %%%%");
    			e.printStackTrace();
    		}
        }
        private HibernateSessionFactory() {
        }
    	
    	/**
         * Returns the ThreadLocal Session instance.  Lazy initialize
         * the <code>SessionFactory</code> if needed.
         *
         *  @return Session
         *  @throws HibernateException
         */
        public static Session getSession() throws HibernateException {
            Session session = (Session) threadLocal.get();
    
    		if (session == null || !session.isOpen()) {
    			if (sessionFactory == null) {
    				rebuildSessionFactory();
    			}
    			session = (sessionFactory != null) ? sessionFactory.openSession()
    					: null;
    			threadLocal.set(session);
    		}
    
            return session;
        }
    
    	/**
         *  Rebuild hibernate session factory
         *
         */
    	public static void rebuildSessionFactory() {
    		try {
    			configuration.configure(configFile);
    			sessionFactory = configuration.buildSessionFactory();
    		} catch (Exception e) {
    			System.err.println("%%%% Error Creating SessionFactory %%%%");
    			e.printStackTrace();
    		}
    	}
    
    	/**
         *  Close the single hibernate session instance.
         *
         *  @throws HibernateException
         */
        public static void closeSession() throws HibernateException {
            Session session = (Session) threadLocal.get();
            threadLocal.set(null);
    
            if (session != null) {
                session.close();
            }
        }
    
    	/**
         *  return session factory
         *
         */
    	public static org.hibernate.SessionFactory getSessionFactory() {
    		return sessionFactory;
    	}
    
    	/**
         *  return session factory
         *
         *	session factory will be rebuilded in the next call
         */
    	public static void setConfigFile(String configFile) {
    		HibernateSessionFactory.configFile = configFile;
    		sessionFactory = null;
    	}
    	/**
         *  return hibernate configuration
         *
         */
    	public static Configuration getConfiguration() {
    		return configuration;
    	}
    
    }

    HibernateSessionFactory类是自定义的SessionFactory,名字可以根据自己的喜好来决定。这里用的是HibernateSessionFactory,其内容及解释。上述代码是由myeclipse 自动生成的;也可以根据自己的情况写出:

    package com.zz.util;
     
    import org.hibernate.SessionFactory;
    import org.hibernate.cfg.Configuration;
     
    //在使用hibernate开发项目,请一定保证只有一个SessionFactory
    //一个数据库对应一个SessionFactory 对象.
    final public class MySessionFactory {
     
        private static SessionFactory sessionFactory=null;
         
        private MySessionFactory(){
             
        }
         
        static{
             
            sessionFactory =new Configuration().configure("com/zz/config/hsp.cfg.xml").buildSessionFactory(); 
            System.out.println("sessionFactory 类型"+sessionFactory);
        }
         
        public static SessionFactory getSessionFactory(){
            return sessionFactory;
        }
         
    }
    


     

    Hibernate中,Session负责完成对象持久化操作。该文件负责创建Session对象,以及关闭Session对象。从该文件可以看出,Session对象的创建大致需要以下3个步骤:

    ① 初始化Hibernate配置管理类Configuration

    ② 通过Configuration类实例创建Session的工厂类SessionFactory

    ③ 通过SessionFactory得到Session实例。

    ³1. Configuration接口

    Configuration负责管理Hibernate的配置信息。Hibernate运行时需要一些底层实现的基本信息。这些信息包括:数据库URL、数据库用户名、数据库用户密码、数据库JDBC驱动类、数据库dialect。用于对特定数据库提供支持,其中包含了针对特定数据库特性的实现,如Hibernate数据库类型到特定数据库数据类型的映射等。

    使用Hibernate必须首先提供这些基础信息以完成初始化工作,为后续操作做好准备。这些属性在Hibernate配置文件hibernate.cfg.xml中加以设定,当调用:

    Configuration config=new Configuration().configure();

    时,Hibernate会自动在目录下搜索hibernate.cfg.xml文件,并将其读取到内存中作为后续操作的基础配置。

    ³ 2. SessionFactory接口

    SessionFactory负责创建Session实例,可以通过Configuration实例构建SessionFactory

    Configuration config=new Configuration().configure();

    SessionFactorysessionFactory=config.buildSessionFactory();

    Configuration实例config会根据当前的数据库配置信息,构造SessionFacory实例并返回。SessionFactory一旦构造完毕,即被赋予特定的配置信息。也就是说,之后config的任何变更将不会影响到已经创建的SessionFactory实例sessionFactory。如果需要使用基于变更后的config实例的SessionFactory,需要从config重新构建一个SessionFactory实例。

    SessionFactory保存了对应当前数据库配置的所有映射关系,同时也负责维护当前的二级数据缓存和Statement Pool。由此可见,SessionFactory的创建过程非常复杂、代价高昂。这也意味着,在系统设计中充分考虑到SessionFactory的重用策略。由于SessionFactory采用了线程安全的设计,可由多个线程并发调用。

    ³3. Session接口

    SessionHibernate持久化操作的基础,提供了众多持久化方法,如saveupdatedelete等。通过这些方法,透明地完成对象的增加、删除、修改、查找等操作。

    同时,值得注意的是,HibernateSession的设计是非线程安全的,即一个Session实例同时只可由一个线程使用。同一个Session实例的多线程并发调用将导致难以预知的错误。

    Session实例由SessionFactory构建:

    Configuration config=new Configuration().configure();

    SessionFactorysessionFactory=config.buldSessionFactory();

    Session session=sessionFactory.openSession();

    ³4. Transaction接口

    TransactionHibernate中进行事务操作的接口,Transaction接口是对实际事务实现的一个抽象,这些实现包括JDBC的事务、JTA中的UserTransaction,甚至可以是CORBA事务。之所以这样设计是可以让开发者能够使用一个统一的操作界面,使得自己的项目可以在不同的环境和容器之间方便地移值。事务对象通过Session创建。例如以下语句:

    Transaction ts=session.beginTransaction();

    ³5. Query接口

    Hibernate 2.x中,find()方法用于执行HQL语句。Hibernate 3.x废除了find()方法,取而代之的是Query接口,它们都用于执行HQL语句。QueryHQL是分不开的。

    Query query=session.createQuery(“fromtable where id=1”);

    例如以下语句:

    Query query=session.createQuery("fromtable whereid=?");

    就要在后面设置其值:

    Query.setString(0,"要设置的值");

    上面的方法是通过“?”来设置参数,还可以用“:”后跟变量的方法来设置参数,如上例可以改为:

    Query query=session.createQuery("fromtable whereid=:1");

    Query.setString("kchValue","要设置的课程号值");

    其使用方法是相同的,例如:

    Query.setParameter(0,"要设置的值");

    Query还有一个list()方法,用于取得一个List集合的示例,此示例中包括可能是一个Object集合,也可能是Object数组集合。例如:

    Query query=session.createQuery("fromtable whereid=1");

    List list=query.list();

  • 相关阅读:
    asp:时间的计算
    彻底理解position与anchorPoint
    关于写代码的一些心得总结2014-12-28 23:49:39
    C#如何将线程中的代码抛到主线程去执行
    pac 文件使用到的javascript函数
    webview改变网页宽度
    iOS按钮长按
    ios 页面滑入滑出
    UILable自适应frame
    制作静态库文件(.a文件)
  • 原文地址:https://www.cnblogs.com/dyllove98/p/3243769.html
Copyright © 2011-2022 走看看