Hibernate3.3用户手册摘要-1-辅助类,session

 1.1.6. 启动和辅助类

是时候来加载和储存一些 Event 对象了,但首先我们得编写一些基础的代码以完成设置。我们必须启动 Hibernate,此过程包括创建一个全局的 SessoinFactory,并把它储存在应用程序代码容易访问的地方。SessionFactory 可以创建并打开新的 Session。一个 Session 代表一个单线程的单元操作,org.hibernate.SessionFactory 则是个线程安全的全局对象,只需要被实例化一次。

我们将创建一个 HibernateUtil 辅助类(helper class)来负责启动 Hibernate 和更方便地操作 org.hibernate.SessionFactory。让我们来看一下它的实现:

 1 package org.hibernate.tutorial.util;
 2 
 3 
 4 import org.hibernate.SessionFactory;
 5 
 6 import org.hibernate.cfg.Configuration;
 7 
 8 
 9 public class HibernateUtil {
10 
11 
12     private static final SessionFactory sessionFactory = buildSessionFactory();
13 
14 
15     private static SessionFactory buildSessionFactory() {
16 
17         try {
18 
19             // Create the SessionFactory from hibernate.cfg.xml
20 
21             return new Configuration().configure().buildSessionFactory();
22 
23         }
24 
25         catch (Throwable ex) {
26 
27             // Make sure you log the exception, as it might be swallowed
28 
29             System.err.println("Initial SessionFactory creation failed." + ex);
30 
31             throw new ExceptionInInitializerError(ex);
32 
33         }
34 
35     }
36 
37 
38     public static SessionFactory getSessionFactory() {
39 
40         return sessionFactory;
41 
42     }
43 
44 
45 }

把这段代码保存为 src/main/java/org/hibernate/tutorial/util/HibernateUtil.java

这个类不但在它的静态初始化过程(仅当加载这个类的时候被 JVM 执行一次)中产生全局的 org.hibernate.SessionFactory,而且隐藏了它使用了静态 singleton 的事实。它也可能在应用程序服务器中的 JNDI 查找 org.hibernate.SessionFactory

如果你在配置文件中给 org.hibernate.SessionFactory 一个名字,在 它创建后,Hibernate 会试着把它绑定到 JNDI。要完全避免这样的代码,你也可以使用 JMX 部署,让具有 JMX 能力的容器来实例化 HibernateService 并把它绑定到 JNDI。这些高级可选项在后面的章节中会讨论到。

再次编译这个应用程序应该不会有问题。最后我们需要配置一个日志(logging)系统 — Hibernate 使用通用日志接口,允许你在 Log4j 和 JDK 1.4 日志之间进行选择。多数开发者更喜欢 Log4j:从 Hibernate 的发布包中(它在 etc/ 目录下)拷贝 log4j.properties 到你的 src 目录,与 hibernate.cfg.xml 放在一起。看一下配置示例,如果你希望看到更加详细的输出信息,你可以修改配置。默认情况下,只有 Hibernate 的启动信息才会显示在标准输出上。 

示例的基本框架完成了 — 现在我们可以用 Hibernate 来做些真正的工作。

2.5. Contextual sessions  sessions的上下文

Most applications using Hibernate need some form of "contextual" session, where a given session is in effect throughout the scope of a given context. However, across applications the definition of what constitutes a context is typically different; different contexts define different scopes to the notion of current. Applications using Hibernate prior to version 3.0 tended to utilize either home-grown ThreadLocal-based contextual sessions, helper classes such as HibernateUtil, or utilized third-party frameworks, such as Spring or Pico, which provided proxy/interception-based contextual sessions.

 使用Hibernate的大多数应用程序需要某种形式的“上下文相关的”session,特定的session在整个特定的上下文范围内始终有效。大多数应用在使用Hibernate时,需要一些方式来获取可以贯穿给定作用域环境的"上下文"session。然而,对不同类型的应用程序而言,要为什么是组成这种“上下文”下一个定义通常是困难的;不同的上下文对“当前”这个概念定义了不同的范围。然而对贯穿应用的定义常常不尽相同,不同的上下文的定义导致了对应不同的作用域3.0版本之前,使用原生自行编写的ThreadLocal的上下文session,或者使用HibernateUtil这样的工具类,或者使用Spring、Pico这样的第三方框架(他们提供了基于代理/拦截的上下文session)

 Starting with version 3.0.1, Hibernate added the SessionFactory.getCurrentSession() method. Initially, this assumed usage of JTA transactions, where the JTA transaction defined both the scope and context of a current session. Given the maturity of the numerous stand-alone JTA TransactionManager implementations, most, if not all, applications should be using JTA transaction management, whether or not they are deployed into a J2EE container. Based on that, the JTA-based contextual sessions are all you need to use.

 从Hibernate3.01开始,Hibernate新增了SessionFactory.getCurrentSession()方法。最初它假定被运用到JTA的事务处理(JTA事务中支持了上下文和当前session两种。)它给了许多JTA事务的实现一个成熟的解决方案。无论是否部署于一个J2EE容器,大部分应用应该使用JTA事务管理。所以,基于JTA的上下文session可以满足你的所有需求。Hibernate开发团队坚信,因为有好几个独立的JTA TransactionManager实现了稳定可用,不论是否被部署到一个J2EE容器中,大多数(假若不是所有的)应用程序都应该采用JTA事务管理。基于这一点,采用JTA的上下文相关session可以满足你一切需要。

 However, as of version 3.1, the processing behind SessionFactory.getCurrentSession() is now pluggable. To that end, a new extension interface, org.hibernate.context.CurrentSessionContext, and a new configuration parameter, hibernate.current_session_context_class, have been added to allow pluggability of the scope and context of defining current sessions.

 3.1版本中的SessionFactory.getCurrentSession()是由用户选用的。为此,延伸了一个新的接口org.hibernate.context.CurrentSessionContext。它是一种新的configuration参数。配置hibernate.current_session_context_class后就可以使得

 更好的是,从3.1开始,SessionFactory.getCurrentSession()的后台实现是可拔插的。因此,我们引入了新的扩展接口(org.hibernate.context.CurrentSessionContext)和新的配置参数(hibernate.current_session_context_class),以便对什么是“当前session”的范围和上下文 (scopeand context)的定义进行拔插

请参阅 org.hibernate.context.CurrentSessionContext 接口的 ,那里有关于它的契约的详细讨论。它定义了单一的方法,currentSession(),特定的实现用它来负责跟踪当前的上下文相关的会话。Hibernate 内置了此接口的三种实现:

  • org.hibernate.context.JTASessionContext:当前会话根据 JTA 来跟踪和界定。这和以前的仅支持 JTA 的方法是完全一样的。详情请参阅 Javadoc。

  • org.hibernate.context.ThreadLocalSessionContext:当前会话通过当前执行的线程来跟踪和界定。详情也请参阅 Javadoc。

  • org.hibernate.context.ManagedSessionContext:当前会话通过当前执行的线程来跟踪和界定。但是,你需要负责使用这个类的静态方法将 Session 实例绑定、或者取消绑定,它并不会打开(open)、flush 或者关闭(close)任何 Session

The first two implementations provide a "one session - one database transaction" programming model. This is also known and used as session-per-request. The beginning and end of a Hibernate session is defined by the duration of a database transaction. If you use programmatic transaction demarcation in plain JSE without JTA, you are advised to use the Hibernate Transaction API to hide the underlying transaction system from your code. If you use JTA, you can utilize the JTA interfaces to demarcate transactions. If you execute in an EJB container that supports CMT, transaction boundaries are defined declaratively and you do not need any transaction or session demarcation operations in your code. Refer to 第 13 章 事务和并发 for more information and code examples.

这两种实现都提供了“每数据库事务对应一个session”的编程模型,也称作每次请求一个session。Hibernate session的起始和终结由数据库事务的生存来控制。假若你采用自行编写代码来管理事务(比如,在纯粹的J2SE,或者JTA/UserTransaction/BMT),建议你使用Hibernate Transaction API来把底层事务实现从你的代码中隐藏掉

如果你在支持CMT的EJB容器中执行,事务边界是声明式定义的,你不需要在代码中进行任何事务或session管理操作。请参阅第 11 章 事务和并发一节来阅读更多的内容和示例代码。

hibernate.current_session_context_class 配置参数定义了应该采用哪个org.hibernate.context.CurrentSessionContext实现。注意,为了向下兼容,如果未
配置此参数,但是存在org.hibernate.transaction.TransactionManagerLookup的配置,Hibernate会采用org.hibernate.context.JTASessionContext。一般而言,此参数的值指明了要使用的实现类的全名,但那两个内置的实现可以使用简写,即"jta"和"thread"。

原文地址:https://www.cnblogs.com/redcoatjk/p/3581335.html