Hibernate.orgCommunity Documentation
Hibernate está diseñado para operar en muchos entornos diferentes y por lo tanto hay un gran número de parámetros de configuración. Afortunadamente, la mayoría tiene valores predeterminados sensibles y Hibernate se distribuye con un archivo hibernate.properties
de ejemplo en etc/
que muestra las diversas opciones. Simplemente ponga el fichero de ejemplo en su ruta de clase y personalícelo de acuerdo a sus necesidades.
Una instancia de org.hibernate.cfg.Configuration
representa un conjunto entero de mapeos de los tipos Java de una aplicación a una base de datos SQL. La org.hibernate.cfg.Configuration
se utiliza para construir una org.hibernate.SessionFactory
inmutable. Los mapeos se compilan desde varios archivos de mapeo XML.
Puede obtener una instancia de org.hibernate.cfg.Configuration
instanciándola directamente y especificando los documentos de mapeo XML. Si los archivos de mapeo están en la ruta de clase, utilice addResource()
. Por ejemplo:
Configuration cfg = new Configuration()
.addResource("Item.hbm.xml")
.addResource("Bid.hbm.xml");
Una manera opcional es especificar la clase mapeada y dejar que Hibernate encuentre el documento de mapeo por usted:
Configuration cfg = new Configuration()
.addClass(org.hibernate.auction.Item.class)
.addClass(org.hibernate.auction.Bid.class);
Luego Hibernate buscará los archivos de mapeo llamados /org/hibernate/auction/Item.hbm.xml
y /org/hibernate/auction/Bid.hbm.xml
en la ruta de clase. Este enfoque elimina cualquier nombre de archivo establecido manualmente.
Una org.hibernate.cfg.Configuration
también le permite especificar las propiedades de configuración. Por ejemplo:
Configuration cfg = new Configuration()
.addClass(org.hibernate.auction.Item.class)
.addClass(org.hibernate.auction.Bid.class)
.setProperty("hibernate.dialect", "org.hibernate.dialect.MySQLInnoDBDialect")
.setProperty("hibernate.connection.datasource", "java:comp/env/jdbc/test")
.setProperty("hibernate.order_updates", "true");
Esta no es la única manera de pasar propiedades de configuración a Hibernate. Algunas opciones incluyen:
Pasar una instancia de java.util.Properties
a Configuration.setProperties()
.
Colocar un archivo llamado hibernate.properties
en un directorio raíz de la ruta de clase.
Establecer propiedades System
utilizando java -Dproperty=value
.
Incluir los elementos <property>
en hibernate.cfg.xml
(esto se discute más adelante).
Si quiere empezar rápidamente hibernate.properties
es el enfoque más fácil.
La org.hibernate.cfg.Configuration
está concebida como un objeto de tiempo de inicio que se va a descartar una vez se crea una SessionFactory
.
Cuando la org.hibernate.cfg.Configuration
ha analizado sintácticamente todos los mapeos, la aplicación tiene que obtener una fábrica para las instancias org.hibernate.Session
. Esta fábrica está concebida para que todos los hilos de la aplicación la compartan:
SessionFactory sessions = cfg.buildSessionFactory();
Hibernate permite que su aplicación instancie más de una org.hibernate.SessionFactory
. Esto es útil si está utilizando más de una base de datos.
Se aconseja que la org.hibernate.SessionFactory
cree y almacene en pool conexiones JDBC por usted Si adopta este enfoque, el abrir una org.hibernate.Session
es tan simple como:
Session session = sessions.openSession(); // open a new Session
En el momento en que inicie una tarea que requiera acceso a la base de datos, se obtendrá una conexión JDBC del pool.
Para que esto funcione, primero necesita pasar algunas las propiedades de conexión JDBC a Hibernate. Todos los nombres de las propiedades de Hibernate y su semántica están definidas en la clase org.hibernate.cfg.Environment
. Ahora describiremos las configuraciones más importantes para la conexión JDBC.
Hibernate obtendrá y tendrá en pool las conexiones utilizando java.sql.DriverManager
si configura las siguientes propiedades:
Tabla 3.1. Propiedades JDBC de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.connection.driver_class | JDBC driver class |
hibernate.connection.url | JDBC URL |
hibernate.connection.username | database user |
hibernate.connection.password | database user password |
hibernate.connection.pool_size | maximum number of pooled connections |
Sin embargo, el algoritmo de pooling de la conexión propia de Hibernate es algo rudimentario. Está concebido para ayudarle a comenzar y no para utilizarse en un sistema de producción ni siquiera para pruebas de rendimiento. Para alcanzar un mejor rendimiento y estabilidad debe utilizar un pool de terceros. Sólo remplace la propiedad hibernate.connection.pool_size con configuraciones específicas del pool de conexiones. Esto desactivará el pool interno de Hibernate. Por ejemplo, es posible utilizar C3P0.
C3P0 es un pool de conexiones JDBC de código abierto distribuido junto con Hibernate en el directorio lib
. Hibernate utilizará su org.hibernate.connection.C3P0ConnectionProvider
para pooling de conexiones si establece propiedades hibernate.c3p0.*
. Si quiere utilizar Proxool refiérase a hibernate.properties
incluído en el paquete y al sitio web de Hibernate para obtener más información.
Aquí hay un archivo hibernate.properties
de ejemplo para c3p0:
hibernate.connection.driver_class = org.postgresql.Driver hibernate.connection.url = jdbc:postgresql://localhost/mydatabase hibernate.connection.username = myuser hibernate.connection.password = secret hibernate.c3p0.min_size=5 hibernate.c3p0.max_size=20 hibernate.c3p0.timeout=1800 hibernate.c3p0.max_statements=50 hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect
Para su utilización dentro de un servidor de aplicaciones, casi siempre usted debe configurar Hibernate para obtener conexiones de un javax.sql.Datasource
del servidor de aplicaciones registrado en JNDI. Necesitará establecer al menos una de las siguientes propiedades:
Tabla 3.2. Propiedades de la Fuente de Datos de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.connection.datasource | datasource JNDI name |
hibernate.jndi.url | URL del proveedor JNDI (opcional) |
hibernate.jndi.class | clase del JNDI InitialContextFactory (opcional) |
hibernate.connection.username | usuario de la base de datos (opcional) |
hibernate.connection.password | contraseña del usuario de la base de datos (opcional) |
He aquí un archivo hibernate.properties
de ejemplo para una fuente de datos JNDI provisto por un servidor de aplicaciones:
hibernate.connection.datasource = java:/comp/env/jdbc/test hibernate.transaction.factory_class = \ org.hibernate.transaction.JTATransactionFactory hibernate.transaction.manager_lookup_class = \ org.hibernate.transaction.JBossTransactionManagerLookup hibernate.dialect = org.hibernate.dialect.PostgreSQLDialect
Las conexiones JDBC obtenidas de una fuente de datos JNDI participarán automáticamente en las transacciones del servidor de aplicaciones administradas por el contenedor.
Pueden darse propiedades de conexión arbitrarias anteponiendo "hibernate.connnection
" al nombre de propiedad de la conexión. Por ejemplo, puede especificar una propiedad de conexión charSet
usando hibernate.connection.charSet.
Puede definir su propia estrategia plugin para obtener conexiones JDBC implementando la interfaz org.hibernate.connection.ConnectionProvider
y especificando su propia implementación personalizada por medio de la propiedad hibernate.connection.provider_class.
Hay otras propiedades que controlan el comportamiento de Hibernate en tiempo de ejecución. Todas son opcionales y tienen valores razonables por defecto.
Algunas de estas propiedades se encuentran a "nivel del sistema sólamente". Las propiedades a nivel del sistema sólamente se pueden establecer por medio de java -Dproperty=value
o hibernate.properties
. No se pueden establecer por medio de las técnicas descritas anteriormente.
Tabla 3.3. Propiedades de Configuración de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.dialect | El nombre de clase de un org.hibernate.dialect.Dialect de Hibernate, el cual le permite que genere un SQL optimizado para una base de datos relacional en particular. e.g. En la mayoría de los casos Hibernate podrá de hecho seleccionar la implementación |
hibernate.show_sql | Escribe todas las declaraciones SQL a la consola. Esta es una alternativa para establecer la categoria de registro org.hibernate.SQL a debug . e.g. |
hibernate.format_sql | Imprime el SQL en el registro y la consola. e.g. |
hibernate.default_schema | Califica los nombres de tabla sin calificar con el esquema/espacio de tabla dado en el SQL generado. e.g. |
hibernate.default_catalog | Califica los nombres de tabla sin calificar con el catálogo dado en el SQL generado. e.g. |
hibernate.session_factory_name | Automáticamente se vinculará el org.hibernate.SessionFactory a este nombre en JNDI después de que se ha creado. e.g. |
hibernate.max_fetch_depth | Establece una "profundidad" máxima del árbol de recuperación por unión externa (outer join) para asociaciones de un sólo extremo (uno-a-uno, muchos-a-uno). Un 0 deshabilita la recuperación por unión externa predeterminada. ej. los valores recomendados entre |
hibernate.default_batch_fetch_size | Establece un tamaño por defecto para la recuperación en lote de asociaciones de Hibernate. ej. valores recomendados |
hibernate.default_entity_mode | Establece un modo predeterminado de representación de entidades para todas las sesiones abiertas desde esta SessionFactory
|
hibernate.order_updates | Obliga a Hibernate a ordenar las actualizaciones SQL por el valor de la clave principal de los items a actualizar. Esto resultará en menos bloqueos de transacción en sistemas altamente concurrentes. e.g. |
hibernate.generate_statistics | De habilitarse, Hibernate colectará estadísticas útiles para la afinación de rendimiento. e.g. |
hibernate.use_identifier_rollback | De habilitarse, cuando se borren los objetos las propiedades identificadoras generadas se resetearán a losvalores establecidos por defecto. e.g. |
hibernate.use_sql_comments | De activarse, Hibernate generará comentarios dentro del SQL, para una depuración más fácil, por defecto es false . e.g. |
Tabla 3.4. Propiedades de JDBC y Conexiones de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.jdbc.fetch_size | Un valor distinto de cero que determina el tamaño de recuperación de JDBC (llama a Statement.setFetchSize() ). |
hibernate.jdbc.batch_size | Un valor distinto de cero habilita que Hibernate utilice las actualizaciones en lote de JDBC2. ej. valores recomendados entre |
hibernate.jdbc.batch_versioned_data | Set this property to true if your JDBC driver returns correct row counts from executeBatch() . It is usually safe to turn this option on. Hibernate will then use batched DML for automatically versioned data. Defaults to false . e.g. |
hibernate.jdbc.factory_class | Selecciona un org.hibernate.jdbc.Batcher personalizado. La mayoría de las aplicaciones no necesitarán esta propiedad de configuración. eg. |
hibernate.jdbc.use_scrollable_resultset | Habilita a Hibernate para utilizar los grupos de resultados deslizables de JDBC2. Esta propiedad sólamente es necesaria cuando se utilizan conexiones JDBC provistas por el usuario. En el caso contrario Hibernate utiliza los metadatos de conexión. e.g. |
hibernate.jdbc.use_streams_for_binary | Utiliza flujos (streams) al escribir/leer tipos binary o serializable a/desde JDBC. Propiedad a nivel de sistema e.g. |
hibernate.jdbc.use_get_generated_keys | Habilita el uso de PreparedStatement.getGeneratedKeys() de JDBC3 para recuperar claves generadas nativamente después de insertar. Requiere un controlador JDBC3+ y un JRE1.4+. Establézcalo como falso si su controlador tiene problemas con los generadores del identificador de Hibernate. Por defecto, se intenta determinar las capacidades del controlador utilizando los metadatos de conexión. e.g. |
hibernate.connection.provider_class | EL nombre de clase de un org.hibernate.connection.ConnectionProvider personalizado que proporcione conexiones JDBC a Hibernate. e.g. |
hibernate.connection.isolation | Establece el nivel de aislamiento de la transacción JDBC. Comprueba java.sql.Connection para valores significativos pero observe que la mayoría de las bases de datos no soportan todos los niveles de aislamiento y algunos definen nivekes de aislamiento adicionales y no estándares. e.g. |
hibernate.connection.autocommit | Habilita un guardado automático (autocommit) para las conexiones JDBC en pool (no se recomienda). e.g. |
hibernate.connection.release_mode | Especifica el momento en que Hibernate debe liberar las conexiones JDBC. Por defecto, una conexión JDBC es retenida hasta que la sesión se cierra o se desconecta explícitamente. Para una fuente de datos JTA del servidor de aplicaciones, debe utilizar after_statement para liberar agresivamente las conexiones después de cada llamada JDBC. Para una conexión no JTA, frecuentemente tiene sentido el liberar la conexión al final de cada transacción, el utilizarafter_transaction . auto escogerá after_statement para las estrategias de transacción JTA y CMT y after_transaction para la estrategia JDBC de transacción. e.g. This setting only affects |
hibernate.connection.<propertyName> | Pasar la propiedad JDBC <propertyName> a DriverManager.getConnection() . |
hibernate.jndi.<propertyName> | Pasar la propiedad <propertyName> al InitialContextFactory JNDI. |
Tabla 3.5. Propiedades de Caché de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.cache.provider_class
| El nombre de clase de un CacheProvider personalizado. e.g. |
hibernate.cache.use_minimal_puts
| Optimiza la operación del caché de segundo nivel para minimizar escrituras, con el costo de lecturas más frecuentes. Esta configuración es más útil para cachés en clúster y en Hibernate3, está habilitado por defecto para implementaciones de caché en clúster. e.g. |
hibernate.cache.use_query_cache
| Habilita el caché de consultas. Las consultas individuales todavía tienen que establecerse con cachés. e.g. |
hibernate.cache.use_second_level_cache
| Se puede utilizar para deshabilitar por completo el caché de segundo nivel, que está habilitado por defecto para clases que especifican un mapeo <cache> . e.g. |
hibernate.cache.query_cache_factory
| El nombre de clase de una interfaz QueryCache personalizada, por defecto al StandardQueryCache incorporado. e.g. |
hibernate.cache.region_prefix
| Un prefijo que se debe utilizar para los nombres de región del caché de segundo nivel. e.g. |
hibernate.cache.use_structured_entries
| Obliga a Hibernate a almacenar los datos en el caché de segundo nivel en un formato más amigable para personas. e.g. |
Tabla 3.6. Propiedades de Transacción de Hibernate
Nombre de la propiedad | Propósito |
---|---|
hibernate.transaction.factory_class
| El nombre de clase de un TransactionFactory a utilizar con la API de Transaction de Hibernate (por defecto es JDBCTransactionFactory ). e.g. |
jta.UserTransaction
| Un nombre JNDI utilizado por JTATransactionFactory para obtener la UserTransaction de JTA del servidor de aplicaciones. e.g. |
hibernate.transaction.manager_lookup_class
| El nombre de clase de un TransactionManagerLookup . Se requiere cuando el chaché a nivel de MVJ está habilitado o cuando se utiliza un generador alto/bajo en un entorno JTA. e.g. |
hibernate.transaction.flush_before_completion
| If enabled, the session will be automatically flushed during the before completion phase of the transaction. Built-in and automatic session context management is preferred, see Sección 2.5, “Sesiones contextuales”. e.g. |
hibernate.transaction.auto_close_session
| If enabled, the session will be automatically closed during the after completion phase of the transaction. Built-in and automatic session context management is preferred, see Sección 2.5, “Sesiones contextuales”. e.g. |
Tabla 3.7. Propiedades Misceláneas
Nombre de la propiedad | Propósito |
---|---|
hibernate.current_session_context_class
| Supply a custom strategy for the scoping of the "current" Session . See Sección 2.5, “Sesiones contextuales” for more information about the built-in strategies. e.g. |
hibernate.query.factory_class
| Elige la implementación de análisis sintáctico HQL. ej. |
hibernate.query.substitutions
| Se utiliza para mapear desde tokens en consultas Hibernate a tokens SQL. (por ejemplo, los tokens pueden ser nombres de función o literales). e.g. |
hibernate.hbm2ddl.auto
| Exporta o valida automáticamente DDL de esquema a la base de datos cuando se crea la SessionFactory . Con create-drop se desechará el esquema de la base de datos cuando la SessionFactory se cierre explícitamente. e.g. |
hibernate.bytecode.use_reflection_optimizer
|
Enables the use of bytecode manipulation instead of runtime reflection. This is a System-level property and cannot be set in e.g. |
hibernate.bytecode.provider
| Both javassist or cglib can be used as byte manipulation engines; the default is e.g. |
Siempre configure la propiedad hibernate.dialect
a la subclase correcta org.hibernate.dialect.Dialect
para su base de datos. Si especifica un dialecto, Hibernate utilizará valores predeterminados de manera sensible para algunas de las otras propiedades enumeradas anteriormente, ahorrándole el esfuerzo de especificarlas manualmente.
Tabla 3.8. Dialectos SQL de Hibernate(hibernate.dialect
)
RDBMS | Dialecto |
---|---|
DB2 | org.hibernate.dialect.DB2Dialect |
DB2 AS/400 | org.hibernate.dialect.DB2400Dialect |
DB2 OS390 | org.hibernate.dialect.DB2390Dialect |
PostgreSQL | org.hibernate.dialect.PostgreSQLDialect |
MySQL | org.hibernate.dialect.MySQLDialect |
MySQL con InnoDB | org.hibernate.dialect.MySQLInnoDBDialect |
MySQL con MyISAM | org.hibernate.dialect.MySQLMyISAMDialect |
Oracle (cualquier versión) | org.hibernate.dialect.OracleDialect |
Oracle 9i | org.hibernate.dialect.Oracle9iDialect |
Oracle 10g | org.hibernate.dialect.Oracle10gDialect |
Sybase | org.hibernate.dialect.SybaseDialect |
Sybase Anywhere | org.hibernate.dialect.SybaseAnywhereDialect |
Microsoft SQL Server | org.hibernate.dialect.SQLServerDialect |
SAP DB | org.hibernate.dialect.SAPDBDialect |
Informix | org.hibernate.dialect.InformixDialect |
HypersonicSQL | org.hibernate.dialect.HSQLDialect |
Ingres | org.hibernate.dialect.IngresDialect |
Progress | org.hibernate.dialect.ProgressDialect |
Mckoi SQL | org.hibernate.dialect.MckoiDialect |
Interbase | org.hibernate.dialect.InterbaseDialect |
Pointbase | org.hibernate.dialect.PointbaseDialect |
FrontBase | org.hibernate.dialect.FrontbaseDialect |
Firebird | org.hibernate.dialect.FirebirdDialect |
Si su base de datos soporta uniones externas del estilo ANSI, Oracle o Sybase, frecuentemente la recuperación por unión externa aumentará el rendimiento limitando el número de llamadas a la base de datos. La recuperación por unión externa permite que un gráfico completo de objetos conectados por asociaciones muchos-a-uno, uno-a-muchos, muchos-a-muchos y uno-a-uno sea recuperado en un sólo SELECT
SQL.
La recuperación por unión externa puede ser deshabilitada globalmente estableciendo la propiedad hibernate.max_fetch_depth
como 0
. Un valor de 1
o mayor habilita la recuperación por unión externa para asociaciones uno-a-uno y muchos-a-uno que hayan sido mapeadas con fetch="join"
.
See Sección 20.1, “Estrategias de recuperación” for more information.
Oracle limita el tamaño de arrays de byte
que se puedan pasar a/desde su controlador JDBC. Si desea utilizar instancias grandes de tipo binary
o serializable
, usted debe habilitar hibernate.jdbc.use_streams_for_binary
. Esta es una configuración a nivel de sistema sólamente.
The properties prefixed by hibernate.cache
allow you to use a process or cluster scoped second-level cache system with Hibernate. See the Sección 20.2, “El Caché de Segundo Nivel” for more information.
Puede definir nuevos tokens de consulta de Hibernate utilizando hibernate.query.substitutions
. Por ejemplo:
hibernate.query.substitutions true=1, false=0
Esto causaría que los tokens true
y false
sean traducidos a literales enteros en el SQL generado.
hibernate.query.substitutions toLowercase=LOWER
Esto le permitiría renombrar la función LOWER
de SQL.
Si habilita hibernate.generate_statistics
, Hibernate expondrá un número de métricas que son útiles al afinar un sistema en ejecución por medio de SessionFactory.getStatistics()
. Incluso se puede configurar Hibernate para exponer estas estadísticas por medio de JMX. Lea el Javadoc de las interfaces en org.hibernate.stats
para obtener más información.
Hibernate utiliza Simple Logging Facade for Java (SLF4J) con el fin de registrar varios eventos del sistema. SLF4J puede direccionar su salida de registro a varios marcos de trabajo de registro (NOP, Simple, log4j versión 1.2, JDK 1.4 logging, JCL o logback) dependiendo de su enlace escogido. Con el fin de configurar el registro necesitará slf4j-api.jar
en su ruta de clase junto con el archivo jar para su enlace preferido - slf4j-log4j12.jar
en el caso de Log4J. Consulte la documentación SLF4J para obtener mayores detalles. Para usar Log4j también necesitará poner un archivo log4j.properties
en su ruta de clase. Un archivo de propiedades de ejemplo se distribuye junto con Hibernate en el directorio src/
.
Le recomendamos bastante que se familiarice con los mensajes de registro de Hibernate. Se ha trabajado bastante para hacer que los registros de Hibernate sean tan detallados como sea posible, sin hacerlos ilegibles. Es un dispositivo esencial en la resolución de problemas. Las categorías de registro más interesantes son las siguientes:
Tabla 3.9. Categorías de Registro de Hibernate
Categoría | Función |
---|---|
org.hibernate.SQL | Registra todas las declaraciones DML de SQL a medida que se ejecutan |
org.hibernate.type | Registra todos los parámetros JDBC |
org.hibernate.tool.hbm2ddl | Registra todas las declaraciones DDL de SQL a medida que se ejecutan |
org.hibernate.pretty | Registra el estado de todas las entidades (máximo 20 entidades) asociadas con la sesión en tiempo de limpieza (flush) |
org.hibernate.cache | Registra toda la actividad del caché de segundo nivel |
org.hibernate.transaction | Registra la actividad relacionada con la transacción |
org.hibernate.jdbc | Registra toda adquisición de recursos JDBC |
org.hibernate.hql.ast.AST | Regista los ASTs de HQL y SQL, durante análisis de consultas. |
org.hibernate.secure | Registra todas las peticiones de autorización JAAS |
org.hibernate | Registra todo. Hay mucha información, pero es útil para la resolución de problemas |
Al desarrollar aplicaciones con Hibernate, casi siempre debe trabajar con debug
habilitado para la categoría org.hibernate.SQL
o, alternativamente, la propiedad hibernate.show_sql
habilitada.
La interfaz org.hibernate.cfg.NamingStrategy
le permite especificar un "estándar de nombrado" para objetos de la base de datos y los elementos del esquema.
Puede proveer reglas para generar automáticamente identificadores de la base de datos a partir de identificadores JDBC o para procesar nombres "lógicos" de columnas y tablas dadas en el archivo de mapeo en nombres "físicos" de columnas y tablas. Esta funcionalidad ayuda a reducir la verborragia del documento de mapeo, eliminando ruidos repetitivos (por ejemplo, prefijos TBL_
). Hibernate utiliza una estrategia por defecto bastante mínima.
Puede especificar una estrategia diferente llamando a Configuration.setNamingStrategy()
antes de agregar los mapeos:
SessionFactory sf = new Configuration()
.setNamingStrategy(ImprovedNamingStrategy.INSTANCE)
.addFile("Item.hbm.xml")
.addFile("Bid.hbm.xml")
.buildSessionFactory();
org.hibernate.cfg.ImprovedNamingStrategy
es una estrategia incorporada que puede ser un punto de partida útil para algunas aplicaciones.
Un enfoque alternativo de configuración es especificar una configuración completa en un archivo llamado hibernate.cfg.xml
. Este archivo se puede utilizar como un remplazo del archivo hibernate.properties
o en el caso de que ambos se encuentren presentes, para sobrescribir propiedades.
El archivo de configuración XML por defecto se espera en la raíz de su CLASSPATH
. Este es un ejemplo:
<?xml version='1.0' encoding='utf-8'?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<!-- a SessionFactory instance listed as /jndi/name -->
<session-factory
name="java:hibernate/SessionFactory">
<!-- properties -->
<property name="connection.datasource"
>java:/comp/env/jdbc/MyDB</property>
<property name="dialect"
>org.hibernate.dialect.MySQLDialect</property>
<property name="show_sql"
>false</property>
<property name="transaction.factory_class">
org.hibernate.transaction.JTATransactionFactory
</property>
<property name="jta.UserTransaction"
>java:comp/UserTransaction</property>
<!-- mapping files -->
<mapping resource="org/hibernate/auction/Item.hbm.xml"/>
<mapping resource="org/hibernate/auction/Bid.hbm.xml"/>
<!-- cache settings -->
<class-cache class="org.hibernate.auction.Item" usage="read-write"/>
<class-cache class="org.hibernate.auction.Bid" usage="read-only"/>
<collection-cache collection="org.hibernate.auction.Item.bids" usage="read-write"/>
</session-factory>
</hibernate-configuration
>
La ventaja de este enfoque es la externalización de los nombres de los archivos de mapeo a la configuración. El hibernate.cfg.xml
también es más práctico una vez que haya afinado el caché de Hibernate. Puede escoger ya sea hibernate.properties
o hibernate.cfg.xml
. Ambos son equivalentes, excepto por los beneficios de utilizar la sintaxis XML que mencionados anteriormente.
Con la configuración XML, iniciar Hibernate es tan simple como:
SessionFactory sf = new Configuration().configure().buildSessionFactory();
Puede seleccionar un fichero de configuración XML diferente utilizando:
SessionFactory sf = new Configuration()
.configure("catdb.cfg.xml")
.buildSessionFactory();
Hibernate tiene los siguientes puntos de integración con la infraestructura J2EE:
Fuentes de datos administrados por el contenedor: Hibernate puede utilizar conexiones JDBC administradas por el contenedor y provistas a través de JNDI. Usualmente, un TransactionManager
compatible con JTA y un ResourceManager
se ocupan de la administración de transacciones (CMT), especialmente del manejo de transacciones distribuídas a través de varias fuentes de datos. También puede demarcar los límites de las transacciones programáticamente (BMT) o puede que quiera utilizar para esto la API opcional de Transaction
de Hibernate para mantener portátil su código.
Vinculación Automática JNDI: Hibernate puede vincular sus SessionFactory
a JNDI después del inicio.
Vinculación de Sesión JTA: La Session
de Hibernate se puede vincular automáticamente al ámbito de transacciones JTA. Simplemente busque la SessionFactory
de JNDI y obténga la Session
actual. Deje que Hibernate se ocupe de vaciar y cerrar la Session
cuando se complete su transacción JTA. La demarcación de transacción puede ser declarativa (CMT) o programática (BMT/UserTransaction).
Despliegue JMX: Si tiene un servidor de aplicaciones con capacidad para JMX (por ejemplo, JBoss AS), puede escoger el desplegar Hibernate como un MBean administrado. Esto le ahorra el código de una línea de inicio para construir su SessionFactory
desde una Configuration
. El contenedor iniciará su HibernateService
, e idealmente también cuidará de las dependencias entre servicios (la fuente de datos debe estar disponible antes de que Hibernate inicie, etc).
Dependiendo de su entorno, podría tener que establecer la opción de configuración hibernate.connection.aggressive_release
como true si su servidor de aplicaciones muestra excepciones "contención de conexión".
La API de Session
de Hibernate es independiente de cualquier demarcación de transacción en su arquitectura. Si deja que Hibernate utilice JDBC directamente, a través de un pool de conexiones, puede comenzar y acabar sus transacciones llamando la API de JDBC. Si ejecuta en un servidor de aplicaciones J2EE, puede que quiera utilizar transacciones administradas por bean y llamar la API de JTA y UserTransaction
cuando sea necesario.
Para mantener su código portable entre estos dos (y otros) entornos le recomendamos la API de Transaction
de Hibernate, que envuelve y oculta el sistema subyacente. Tiene que especificar una clase fábrica para las instancias de Transaction
estableciendo la propiedad de configuración hibernate.transaction.factory_class
de Hibernate.
Existen tres opciones estándares o incorporadas:
org.hibernate.transaction.JDBCTransactionFactory
delega a transacciones de bases de datos (JDBC) (por defecto)
org.hibernate.transaction.JTATransactionFactory
delega a transacciones administradas por el contenedor si una transacción existente se encuentra en proceso en este contexto (por ejemplo, un método de bean de sesión EJB). De otra manera, se inicia una nueva transacción y se utilizan las transacciones administradas por bean.
org.hibernate.transaction.CMTTransactionFactory
delega a transacciones JTA administradas por el contenedor
También puede definir sus propias estrategias de transacción (por ejemplo, para un servicio de transacción CORBA).
Algunas funcionalidades en Hibernate (por ejemplo, el caché de segundo nivel, las sesiones contextuales, etc.) requieren acceso al TransactionManager
de JTA en un entorno administrado. En un servidor de aplicaciones tiene que especificar cómo Hibernate debe obtener una referencia al TransactionManager
, ya que J2EE no estandariza un sólo mecanismo:
Tabla 3.10. TransactionManagers de JTA
Transaction Factory | Servidor de Aplicaciones |
---|---|
org.hibernate.transaction.JBossTransactionManagerLookup | JBoss |
org.hibernate.transaction.WeblogicTransactionManagerLookup | Weblogic |
org.hibernate.transaction.WebSphereTransactionManagerLookup | WebSphere |
org.hibernate.transaction.WebSphereExtendedJTATransactionLookup | WebSphere 6 |
org.hibernate.transaction.OrionTransactionManagerLookup | Orion |
org.hibernate.transaction.ResinTransactionManagerLookup | Resin |
org.hibernate.transaction.JOTMTransactionManagerLookup | JOTM |
org.hibernate.transaction.JOnASTransactionManagerLookup | JOnAS |
org.hibernate.transaction.JRun4TransactionManagerLookup | JRun4 |
org.hibernate.transaction.BESTransactionManagerLookup | Borland ES |
Una SessionFactory
de Hibernate vinculada a JNDI puede simplificar la búsqueda de la fábrica y la creación de nuevas Session
es. Sin embargo, esto no se relaciona con un Datasource
vinculado a JNDI; simplemente que ambos utilizan el mismo registro.
Si desea tener la SessionFactory
vinculada a un espacio de nombres de JNDI, especifique un nombre (por ejemplo, java:hibernate/SessionFactory
) utilizando la propiedad hibernate.session_factory_name
. Si se omite esta propiedad, la SessionFactory
no será vinculada a JNDI. Esto es particularmente útil en entornos con una implementación JNDI de sólo lectura por defecto (por ejemplo, en Tomcat).
Al vincular la SessionFactory
a JNDI, Hibernate utilizará los valores de hibernate.jndi.url
, hibernate.jndi.class
para instanciar un contexto inicial. Si éstos no se especifican, se utilizará el InitialContext
por defecto.
Hibernate colocará automáticamente la SessionFactory
en JNDI después de que llame a cfg.buildSessionFactory()
. Esto significa que tendrá al menos esta llamada en algún código de inicio o clase de utilidad en su aplicación, a menos de que utilice el despliegue JMX con el HibernateService
(esto se discute más adelante en mayor detalle).
Si utiliza una SessionFactory
JNDI, un EJB or cualquier otra clase puede llegar a obtener el SessionFactory
utilizando una búsqueda JNDI.
Le recomendamos que vincule el SessionFactory
a JNDI en un entorno administrado y que de otra manera, use un singleton static
. Para proteger su código de aplicación de estos detalles, también le recomendamos que esconda el código de búsqueda real para una SessionFactory
en una clase de ayuda como HibernateUtil.getSessionFactory()
. Note que dicha clase también es una manera práctica de iniciar Hibernate— vea el capítulo 1.
The easiest way to handle Sessions
and transactions is Hibernate's automatic "current" Session
management. For a discussion of contextual sessions see Sección 2.5, “Sesiones contextuales”. Using the "jta"
session context, if there is no Hibernate Session
associated with the current JTA transaction, one will be started and associated with that JTA transaction the first time you call sessionFactory.getCurrentSession()
. The Session
s retrieved via getCurrentSession()
in the "jta"
context are set to automatically flush before the transaction completes, close after the transaction completes, and aggressively release JDBC connections after each statement. This allows the Session
s to be managed by the life cycle of the JTA transaction to which it is associated, keeping user code clean of such management concerns. Your code can either use JTA programmatically through UserTransaction
, or (recommended for portable code) use the Hibernate Transaction
API to set transaction boundaries. If you run in an EJB container, declarative transaction demarcation with CMT is preferred.
La línea cfg.buildSessionFactory()
todavía se tiene que ejecutar en algún sitio para obtener una SessionFactory
en JNDI. Puede hacer esto ya sea en un bloque inicializador static
(como aquel en HibernateUtil
) o bien puede desplegar Hibernate como un servicio administrado.
Hibernate se distribuye con org.hibernate.jmx.HibernateService
para desplegar en un servidor de aplicaciones con capacidades JMX, como JBoss AS. El despliegue y la configuracón reales son específicos del vendedor. He aquí un ejemplo de jboss-service.xml
para JBoss 4.0.x:
<?xml version="1.0"?>
<server>
<mbean code="org.hibernate.jmx.HibernateService"
name="jboss.jca:service=HibernateFactory,name=HibernateFactory">
<!-- Required services -->
<depends
>jboss.jca:service=RARDeployer</depends>
<depends
>jboss.jca:service=LocalTxCM,name=HsqlDS</depends>
<!-- Bind the Hibernate service to JNDI -->
<attribute name="JndiName"
>java:/hibernate/SessionFactory</attribute>
<!-- Datasource settings -->
<attribute name="Datasource"
>java:HsqlDS</attribute>
<attribute name="Dialect"
>org.hibernate.dialect.HSQLDialect</attribute>
<!-- Transaction integration -->
<attribute name="TransactionStrategy">
org.hibernate.transaction.JTATransactionFactory</attribute>
<attribute name="TransactionManagerLookupStrategy">
org.hibernate.transaction.JBossTransactionManagerLookup</attribute>
<attribute name="FlushBeforeCompletionEnabled"
>true</attribute>
<attribute name="AutoCloseSessionEnabled"
>true</attribute>
<!-- Fetching options -->
<attribute name="MaximumFetchDepth"
>5</attribute>
<!-- Second-level caching -->
<attribute name="SecondLevelCacheEnabled"
>true</attribute>
<attribute name="CacheProviderClass"
>org.hibernate.cache.EhCacheProvider</attribute>
<attribute name="QueryCacheEnabled"
>true</attribute>
<!-- Logging -->
<attribute name="ShowSqlEnabled"
>true</attribute>
<!-- Mapping files -->
<attribute name="MapResources"
>auction/Item.hbm.xml,auction/Category.hbm.xml</attribute>
</mbean>
</server
>
Este archivo se implementa en un directorio llamado META-INF
y se encuentra empacado en un archivo JAR con la extensión .sar
(archivo de servicio). También necesita empacar Hibernate, sus bibliotecas de terceros requeridas, sus clases persistentes compiladas, así como sus archivos de mapeo en el mismo archivo. Sus beans empresariales (usualmente beans de sesión) se pueden dejar en su propio archivo JAR, pero puede incluir este archivo EJB JAR en el archivo de servicio principal para obtener una unidad desplegable en vivo (sin apagarlo). Consulte la documentación de JBoss AS para obtener más información sobre el servicio JMX y la implementación de EJB.
Copyright © 2004 Red Hat, Inc.