Cómo está organizado este libro El libro se presenta en ocho cap'tulos simples. 0ada cap'tulo se ocupará de uno o dos temas espec'fcos. 3odos los cap'tulos son presentados con "ra&mentos de códi&o para ilustrar la tecnolo&'a en detalle. sted debe descar&ar y trabajar en estrecha colaboración con el códi&o "uente !ue acompa4a. 8a or&aniación y los objetivos de los cap'tulos son los si&uientes-
Capítulo 1, Fundamentos En este cap'tulo se establece el escenario para el uso de Hibernate. 9efnimos el dominio del problema, encontrar una solución utiliando 59:0, y re dise4ar el problema empleando Hibernate. 3endremos el &usto del Framework de un nivel muy alto.
Capítulo 2, Fundamentos sted aprendió sobre el problema de Hibernate está tratando de resolver en el primer cap'tulo. 6!u', en el se&undo cap'tulo, nos sumer&imos en el Framework de e#plorar sus partes móviles y su trabajo en la acción. 0aminamos a trav)s de Hibernate pieas "undamentales en detalle.
Capítulo 3, notaciones En este cap'tulo, nos centraremos en la creación de aplicaciones de Hibernate utiliando anotaciones. Este cap'tulo cubre los aspectos básicos de las anotaciones, saltar a las anotaciones de Hibernate !ue vamos a estar utiliando en el resto del libro.
Capítulo !, persistiendo Colecciones 8a persistencia de las colecciones es una tarea di"'cil para los desarrolladores. Este cap'tulo está dedicado a ayudar a entender la mecánica de la persistencia y la "orma de trabajar con las colecciones.
Capítulo ", sociaciones sted aprenderá acerca de la compatibilidad de Hibernate para las asociaciones y relaciones en este cap'tulo. 0ubre las asociaciones "undamentales, como uno;a; muchos y muchos;a;muchos, con ejemplos pertinentes. 3rat) de mantener este cap'tulo tan del&ado como sea posible, pero dada la ma&nitud del material pertinente, me perd' un poco mi objetivo$
Capítulo #, Conceptos $anzados Este cap'tulo trata de unos conceptos avanados tales como el almacenamiento en cach), estrate&ias de herencia, tipos y fltros. 9ebe ejecutar este cap'tulo para obtener una mejor comprensión de la estructura y lo !ue o"rece en relación a la herencia, el almacenamiento en cach), y otras caracter'sticas.
Capítulo %, &ibernate Quer' (anguage 9e manera similar a S<8, Hibernate e#pone su propio len&uaje de consulta para trabajar con objetos. Este cap'tulo es una introducción a H<8 y le &u'a a trav)s de la 6=> con ejemplos.
Capítulo ), *a$a Persistence P+
Este cap'tulo se centra en un estándar en el mundo 5ava =ersistence, 5=6, a la vista de hibernate. Se discute el apoyo de Hibernate en la aplicación de las normas de la 6== y cómo podemos utiliarlas en nuestras aplicaciones.
tilizando -.emplos de código 2aterial Suplementario (ejemplos de códi&o, ejercicios, etc.+ está disponible para su descar&a en https-??&ithub.com?madhusudhankonda?jh.&it. Este libro está a!u' para ayudarle a hacer su trabajo. En &eneral, los ejemplos de códi&o !ue se o"recen con este libro, usted puede utiliarlos en sus pro&ramas y la documentación.
Capítulo 1 Fundamentos Hay dos mundos de so"tware di"erentes- uno es el mundo 5ava, donde nada menos !ue los objetos son conocidos, mientras !ue el otro es el mundo base de datos relacional, donde los datos es el rey. 8os desarrolladores de 5ava siempre "uncionan con objetos !ue representan el estado y el comportamiento modelado de problemas del mundo real. 8a persistencia de objetos es un re!uisito "undamental de las aplicaciones 5ava. El estado es el modelo !ue se persiste en el almacenamiento duradero por lo !ue será permanente. =or otro lado, cuando es hora de almacenar los datos, tenemos !ue confar en las bases de datos relacionales, donde los datos se representan tradicionalmente en un "ormato de fla;columna con las relaciones y asociaciones. 8levar objetos 5ava en el mundo relacional es siempre una tarea di"'cil y compleja para los desarrolladores de 5ava. Este proceso se refere a menudo como el mapeo objeto;relacional (@A2+. En este cap'tulo se establecen los "undamentos para nuestra discusión de Hibernate, primero buscando en el dominio del problema de la persistencia de objetos. Bamos a e#plorar las tecnolo&'as y herramientas, tales como 59:0 e Hibernate, !ue nos ayudan a hacer "rente a este desa"'o. Bamos a comparar y contrastar estas dos tecnolo&'as y aprender como Hibernate lo&ra mapeo objeto;relacional de persistencia con "acilidad y comodidad.
/acimiento de &ibernate 9i&amos !ue estamos dise4ando un sistema de banca en l'nea. Esperamos !ue el banco para mantener una copia de se&uridad de nuestras cuentas, datos personales, pre"erencias y transacciones. Esto si&nifca, con el fn de ser duraderos, los datos de aplicación debe ser persistió a un espacio de almacenamiento permanente. En el conte#to de esta aplicación bancaria, por los datos persistentes me refero a los clientes, dirección, cuenta y otros objetos de dominio !ue podemos haber modelados en nuestro dise4o. 8os datos !ue se ha persistido por su aplicación sobrevivirá a la aplicación en s', por ejemplo, !ue puede haberse movido "uera de l'nea para la banca tele"ónica, pero los datos creados por nuestra aplicación banco a7n debe ser visible o disponible si se re!uiere. 6s' !ue, ahora sabemos !ue la persistencia de los objetos (su estado es el dato !ue tenemos !ue persistir+ es un re!uisito "undamental para la mayor'a de aplicaciones del mundo real. =ara &uardar los datos, necesitamos espacios de almacenamiento duraderos llamados bases de datos. Hay una &ran cantidad de proveedores de bases de datos (tales como @racle, 2yS<8, 9:C, 5ava 9:, y otros+ con una lar&a lista de comodidades y lujos.
D0ómo podemos persistir un &ráfco de objetos a una base de datos 8as empresas emplean len&uajes orientados a objetos (como 5ava+ como sus plata"ormas de pro&ramación y bases de datos relacionales (como @racle, 2yS<8, Sybase, etc.+ para el almacenamiento de datos. 8a e#istencia de estas dos tecnolo&'as de so"tware es una necesidad para la mayor'a de aplicaciones del mundo real, a pesar de la llamada impedancia desajuste objeto;relacional. Bamos a hablar de la "alta de coincidencia en el pró#imo cap'tulo en detalle, pero para darle una introducción, voy a e#plicar sus principales puntos a!u'G 8a herencia es el principio "undamental de la pro&ramación orientada a objetos sin el cual las asociaciones de objetos ser'a imposible dise4ar. 8as bases de datos no entienden la herencia. G 0uando se trata del rico conjunto de asociaciones de objetos como uno;a;uno, uno;a;muchos y muchos;a;muchos, bases de datos decae, ya !ue no pueden soportar todo tipo de relaciones. G =or 7ltimo, tambi)n hay una "alta de coincidencia de identidad- los objetos llevan tanto una identidad y la i&ualdad, mientras !ue los re&istros de base de datos se identifcan con sus valores de columna. 9esarrolladores miti&an estas di"erencias mediante el empleo de diversos Frameworks de cosecha propia y otras soluciones t)cnicas y estrate&ias. 5ava tiene una herramienta estándar establecido para el acceso a bases de datos. Se llama el 5ava 9atabase 0onnectivity (59:0+ >nter"a de pro&ramación de aplicaciones (6=>+. El 6=> "ue muy bien utiliado en aplicaciones 5ava hasta hace poco. 2ientras !ue el 6=> es muy adecuado para pe!ue4os proyectos, se convierte bastante en&orroso (y a veces "uera de la mano+ como el modelo de dominio aumenta en la complejidad. 8a 6=> tambi)n incluye una &ran cantidad de códi&o repetitivo, lo !ue re!uiere el desarrollador para hacer un montón de codifcación manual. 6demás, el manejo del mapeo objeto;relacional es demasiado torpe$ Este "ue el punto de dolor para los desarrolladores- !ue todos deseamos una sencilla herramienta para persistir los datos sin tanta molestia. El e!uipo de Hibernate encontró los huecos en el espacio de mapeo @A2 y aprovechó mediante la creación de un Framework sencillo !ue har'a !ue "ácil el desarrollo de aplicaciones. Fue entonces cuando nació Hibernate$ Hibernate se convirtió en un )#ito instantáneo y es sin duda la herramienta de códi&o abierto más popular en el dominio de las herramientas @A2. El Framework "ue adoptado durante la noche por la comunidad por su sencille y potentes caracter'sticas.
0mbito del problema 6ntes de saltar a la e#ploración de Hibernate en detalle, vamos a ver un ejemplo del tipo de problema !ue Hibernate se inventó para resolver. 3odos nosotros (bueno, al menos la mayor'a de nosotros$+ 8e encanta ver pel'culas. @bviamente, no tenemos todo el tiempo del mundo para ver esas pel'culas cuando lle&an a la pantalla. 6s' creamos una lista de deseos de las pel'culas !ue nos &ustar'a ver. =or esta raón, nos despertamos una ma4ana y decidimos escribir una sencilla aplicación llamada 5ust2ovie$ Se trata de una aplicación basada en web !ue permite a los usuarios suscribirse por cuenta propia para crear su lista de pel'culas deseadas por ver. =ueden volver a la pá&ina web en cual!uier momento para a&re&ar, modifcar o eliminar las pel'culas en su lista de deseos. 0omo tenemos !ue almacenar la lista de cada usuario, es imprescindible !ue almacenamos esta lista de deseos en el almacenamiento duradero, como una base de datos.
=rimero vamos a crear una aplicación 5ava sencilla para almacenar y recuperar pel'culas desde una base de datos.
plicación o$ieanager 0onsidere la posibilidad de una aplicación 5ava llamada 2ovie2ana&er cuyo trabajo principal es &uardar, encontrar y recuperar las pel'culas desde una base de datos. 6demás de la codifcación de la aplicación 5ava, necesitamos una tabla de base para almacenar la in"ormación de la pel'cula. Esta tabla 2@B>ES almacenará los datos sobre pel'culas como flas, como se muestra en la 3abla ;.
0ada fla representará Banilla2ovie2ana&er.
una instancia de la pel'cula en
nuestra
aplicación
Ha&amos de cuenta !ue vivimos en un mundo sin Hibernate. Bamos a escribir un códi&o de ejemplo utiliando 59:0 !ue, con suerte, cumplir con nuestros re!uisitos.
-l uso de *C El primer paso en cual!uier aplicación de base de datos es establecer una cone#ión con la base de datos. na cone#ión es una puerta de entrada a la base de datos para la realiación de las operaciones sobre los datos de una aplicación 5ava. 59:0 proporciona una 6=> de cone#ión para crear cone#iones basadas en las propiedades de base de datos !ue nos o"recen. 8os proveedores de bases de datos suelen implementar una clase !ue tiene el mecanismo de ejemplo para la cone#ión de base de datos, para la base de datos '4Q(, esta clase es com5m'sql5.dbc5ri$er y de la base de datos *a$a (derb'+ es org5apac6e5derb'5.dbc5-mbeddedri$er5 3en&a en cuenta !ue utiliamos la base de datos 2yS<8 a trav)s del libro. 0onsulte 0onf&uración de Hibernate en la pá&ina para obtener detalles sobre cómo conf&urar el proyecto y las bases de datos. El m)todo CreateConnection , !ue se muestra en el si&uiente "ra&mento, demuestra el procedimiento para crear una cone#ión de base de datospublic class 7anillao$ieanager I pri$ate 0onnection connection J null% // Database properties
pri$ate Strin& url J jdbc-mys!l-??localhost-KK/L?5H% pri$ate Strin& driver0lass J com.mys!l.jdbc.9river% pri$ate Strin& username J mkonda% pri$ate Strin& password J mypass% ...
pri$ate 0onnection &et0onnection(+ I tr' I 0lass."or1ame(driver0lass+.new>nstance(+% connection J 9river2ana&er.&et0onnection(url, username, password+% M catc6 (E#ception e#+ I System.err.println(E#ception-N e#.&et2essa&e(++% M return connection% M M
En este "ra&mento, primero se &enera una instancia de la clase del controlador y, a continuación, obtener una cone#ión utiliando el 9river2ana&er. na ve !ue hemos establecido nuestra cone#ión con la base de datos con )#ito, nuestro si&uiente paso es escribir un m)todo para persistir y consultar una entidad de la pel'cula. 8a mayor parte de los m)todos deben conocer si ha tenido al&una e#periencia con códi&o 59:0. 0ontinuando con nuestro desarrollo de la aplicación, vamos a a4adir un par de m)todos !ue &uardara las pel'culas y recuperarlas de la base de datos. 8lamamos a estos m)todos como persist2ovie y !uery2ovies, respectivamente. 8a aplicación de estos m)todos se muestra en el si&uiente listado de códi&opublic class 7anillao$ieanager I pri$ate Strin& insertS!l J >1SEA3 >13@ 2@B>ES B68ES (,,,+% pri$ate Strin& selectS!l J SE8E03 O FA@2 2@B>ES% ...
pri$ate $oid persist2ovie(+ I tr' I =reparedStatement pst J &et0onnection(+.prepareStatement(insertS!l+% pst.set>nt(, //+% pst.setStrin&(C, 3op Pun+% pst.setStrin&(K, 6ction Film+% pst.setStrin&(, 3ony Scott+% // Execute the statement
pst.e#ecute(+% System.out.println(2ovie persisted success"ully$ +% M catc6 (S<8E#ception e#+ I System.err.println(e#.&et2essa&e(++% e#.printStack3race(+% M
M
pri$ate $oid !uery2ovies(+ I tr' I Statement st J &et0onnection(+.createStatement(+% AesultSet rs J st.e#ecuteES+% 86ile (rs.ne#t(++ I System.out.println(2ovie Found- N rs.&et>nt(>9+ N , 3itle- N rs.&etStrin&(3>38E++% M
M
catc6 (S<8E#ception e#+
I System.err.println(e#.&et2essa&e(++% M
M M
Esto es lo !ue hemos hecho en el códi&o de ejemplo anterior. Hemos creado un =reparedStatement de la cone#ión con la cadena S<8 >1SEA3. C. Hemos establecido la declaración con valores (valores de columna contra n7meros de columna- es >9, C es el t'tulo, etc.+. K. Hemos ejecuta la sentencia !ue debe insertar la pel'cula en la tabla. . Hemos pre&unt) la base de datos para todas las pel'culas y los imprimimos a la consola. 8os pasos son bastante auto;e#plicativo. 0reamos una declaración preparada y ejecutarlo despu)s de establecer los valores apropiados en )l para cada columna. na ve !ue sabemos !ue la ejecución trabajó, consultamos la base de datos con una
instrucción SE8E03 con el fn de obtener todas los pel'culas disponibles e imprimirlos a la consola. Sin embar&o, hay al&unas cosas a tener en cuentaG tiliamos una declaración S<8 predefnida para insertar (o seleccione+ los valores de columna. G Establecemos la columna con valores uno por uno usando el n7mero de posición (o el nombre de la columna+. G 0o&emos la S<8E#ception si el códi&o se porta mal. =ara pro&ramas sencillos, esta "orma de creación de los estados con los valores y la ejecución de ellos está muy bien. Sin embar&o, los tipos de pro&ramas !ue tenemos !ue tratar en el mundo real son mucho más complejos. 59:0 "uncionará, si usted está dispuesto y capa de escribir y manejar una &ran cantidad de códi&o no comercial. 6demás, el uso de 59:0 podr'a plantear un reto cuando se tiene una &ran cantidad de tablas o relaciones complejas entre los objetos.
+mpro$isando la plicación de la película D1o ser'a ideal para llamar a un m)todo como persisten ( + en una clase de utilidad para !ue el objeto de la pel'cula se conserva en se&uida =ara lo&rar este objetivo, vamos a crear un objeto viejo y simple de 5ava (=@5@+ en representación de una pel'cula. =ara cada pel'cula !ue se libera (o a7n no se ha lanado+, tendremos un nuevo objeto de pel'cula creado. 8a pel'cula =@5@ se defne a!u'public class o$ie I pri$ate int id J /% pri$ate Strin& title J null% pri$ate Strin& synopsis J null% pri$ate Strin& director J null% ... // Setters and getters omitted
M
=or lo tanto, todo lo !ue necesitamos ahora es !ue una instalación de persistir este objeto =@5@ en nuestra 3abla 2@B>ES en esencia de bases de datos !ue convierten el modelo de objetos (objeto =el'cula+ a un (fla de la tabla+ modelo relacional. Bamos a crear una clase 2ovie=ersistor !ue podr'a hacer este trabajo // Pseudocode
public class o$iePersistor I public $oid persist(2ovie movie+ I // Persisting a movie goes here
M
public $oid "etch(Strin& title+ I // Fetching a movie by title goes here
M ... M
1o hemos escrito el persisten o ir a buscar la "uncionalidad todav'a% ese no es el tema del pro&rama. 6hora vamos a ver lo "ácil !ue es persistir cual!uier pel'cula utiliando la clase de utilidad 2ovie=ersistor, como se demuestra en esta prueba de la muestra //Pseudocode
2ovie=ersistor movie=ersistor J ne8 2ovie=ersistor (+% 2ovie movie J ne8 2ovie(+% movie.set>d(+% movie.set3itle(5aws+% movie.set9irector(Steven Spielber&+%
movie.setSynopsis(Story o" a &reat white shark$+% movie=ersistor.persist(movie+%
D0uán &enial es eso n =@5@ !ue representa una pel'cula se conserva como una fla de e#pedientes en un modelo de tabla a objetos de base de datos de modelo relacional a trav)s de una clase de utilidad$ Eso es todo bien, e#cepto por el actual persisten a buscar implementaciones de m)todo. =ara implementar esta "uncionalidad, no sólo necesitamos la instalación de la cone#ión a una base de datos, tambi)n necesitamos un mecanismo para convertir el objeto a una fla (como la carto&ra"'a de nuestras propiedades de objeto a las columnas de base de datos+. =odr'amos escribir nuestro propio "ramework de clases para ocultar el meollo de estas conversiones y mecanismos de persistencia (!ue pueden utiliar buenas declaraciones 59:0 detrás de las escenas+. 6un!ue la redacción de este "ramework no es ciencia de cohetes, ser'a una p)rdida de tiempo y es"uero en&orroso para empear. 0on el tiempo, los re!uisitos de persistencia de una or&aniación pueden cambiar o incluso puede mi&rar la base de datos, por ejemplo, @racle a 2yS<8. Esto si&nifca !ue el "ramework tendr'a !ue ser muy &en)rica y dar cuenta de una &ran cantidad de re!uisitos "uncionales y t)cnicos antes de &olpear el suelo. En mi e#periencia, estos "ramework de cosecha propia son inmanejables, inQe#ible, inescalable, y a veces "uera de "echa tambi)n$ 6 menos !ue el re!uisito está ape&ado espec'fcamente a una or&aniación (la or&aniación puede !uerer persistir datos a 2arte$+, 8e recomiendo encarecidamente !ue usted busca en >nternet para ele&ir uno !ue satis"a&a estrechamente nuestros predicados. =ero antes de ir en su manera de empear a escribir el códi&o, !uiero ser el portador de buenas noticias (si a7n no lo ha de haber escuchado esto+- ya hay un &ran "ramework !ue hace e#actamente esto, persistencia de objetos a una base de datos relacional, llamado Hibernate$ 6hora !ue tenemos un "ramework de persistencia, vamos a ver cómo el mismo m)todo !ue persiste nuestra pel'cula se puede re"actoriar trav)s de Hibernatepublic class asico$ieanager I pri$ate $oid persist2ovie(2ovie movie+ I Session session J sessionFactory.&et0urrentSession(+% ... session.save(movie+% M ... M
D3e diste cuenta de !ue nos ahorramos la instancia de la pel'cula a una base de datos por una ejecución de una sola l'nea de códi&o- Session.save (movie+ D1o es esto lo !ue hab'a deseado antes, una clase !ue simplemente &uardar los objetos persistentes de una manera orientada a objetos 8as clases de la 6=> de Hibernate e#ponen varios m)todos para manipular los objetos 5ava con "acilidad y comodidad. 1osotros no tenemos !ue escribir pá&inas y pá&inas de códi&o utiliando 59:0 ni doblar las man&as y escribir un "ramework mientras se la pasa rascando la cabea y tra&ar litros de ca"e'na$ Hibernate proporciona la capacidad de persistencia de objetos% Sin embar&o, hay una conf&uración de una sola ve y el mapeo tenemos !ue dejar !ue Hibernate sabe
nuestras intenciones. 1os adentramos en estos detalles en un nivel muy alto en el pró#imo par de secciones.
-l uso de &ibernate 8as medidas estándar a se&uir en la creación de una aplicación de Hibernate son. 0onf&urar la cone#ión de base de datos. C. 0ree defniciones de asi&nación. K. =ersistir las clases. Estos son los pasos comunes !ue intervienen en el desarrollo de la versión 5ava Hibernate de nuestra aplicación 2ovie2ana&er. 0rear un objeto de dominio =el'cula (dominio =@5@s modelo !ue representan las tablas de datos+. C. 0rear archivos de conf&uración como propiedades de Hibernate y archivos de asi&nación. K. 0rear un cliente de prueba !ue administra (insertar ? actualiar ? borrar ? bus!ueda+ las pel'culas. Ra hemos preparado un =@5@ pel'cula, como se muestra en "ra&mentos anteriores, por lo !ue no tiene !ue ir sobre ella de nuevo. El coraón de cual!uier aplicación Hibernate está en su conf&uración. Hay dos pieas de conf&uración re!ueridos en cual!uier aplicación Hibernate- uno crea las cone#iones de base de datos, y la otra crea el mapeo de objetos a la tabla. 6l i&ual !ue con 59:0, tenemos !ue proporcionar la in"ormación de la base de datos de nuestra aplicación por lo !ue se abrirá una cone#ión para la manipulación de los datos. 8os defne la conf&uración de mapeo !ue se oponen propiedades se asi&nan a las columnas de la tabla. 1o vamos a entrar en detalles acerca de ellos a!u', ya !ue el objetivo de este cap'tulo es !ue pueda empear rápidamente$ Echemos un vistao a los pasos estándar para la creación de una aplicación de Hibernate en las si&uientes secciones.
Con9gure la cone:ión con la base =ara crear una cone#ión con la base de datos, Hibernate debe conocer los detalles de nuestras bases de datos, tablas, clases y otros mecánicos. Esta in"ormación está defnida en un archivo 28 (&eneralmente llamado hibernate.c"&.#ml+ o como un archivo de te#to simple con pares nombre ? valor (hibernate.properties+. =ara este ejercicio, se utilia el estilo 28. 1ombramos este archivo hibernate.c"&.#ml por lo !ue el marco puede car&ar este archivo automáticamente. El si&uiente "ra&mento describe un archivo de este tipo de conf&uración. =or!ue yo estoy usando 2yS<8 como base de datos, los detalles de la cone#ión de la base de datos 2yS<8 se declaran en este archivo hibernate.c"&.#ml;6ibernateactor'= ;propert' nameJconnection.url= jdbc-mys!l-??localhost-KK/L?5H ;?propert'= ;propert' nameJconnection.driverTclass=com.mys!l.jdbc.9river;?propert'= ;propert' nameJconnection.username=mkonda;?propert'= ;propert' nameJconnection.password=password ;?propert'= ;propert' nameJdialect=or&.hibernate.dialect.2yS<8U9ialect;?propert'= ;mapping resourceJ2ovie.hbm.#ml ?= ;?session<>actor'= ;?6ibernate
Este archivo tiene sufciente in"ormación para obtener una cone#ión en directo a una base de datos 2yS<8. 8as propiedades anteriores tambi)n se pueden e#presar como pares de nombre ? valor. =or ejemplo, a!u' está la misma in"ormación representada como pares nombre ? valor en un archivo de te#to hibernate.properties tituladashibernate.connection.driverTclass J com.mys!l.jdbc.9river hibernate.connection.url J jdbc-mys!l-??localhost-KK/L?5H hibernate.dialect J or&.hibernate.dialect.2yS<8U9ialect connection.url indica
la A8 a la !ue debemos estar conectados, driverTclass representa la clase del controlador correspondiente para hacer una cone#ión, y el dialect indica !ue la base de datos dialecto !ue estamos utiliando (2yS<8, en este caso+. Si usted está si&uiendo el en"o!ue archivo hibernate.properties, ten&a en cuenta !ue todas las propiedades tienen el prefjo hibernate, y si&uen un patrón de Hibernate. O =ropiedades, por instancia. 2ás allá de proporcionar las propiedades de conf&uración, tambi)n tenemos !ue proporcionar archivos de asi&nación y sus ubicaciones. 0omo se mencionó anteriormente, un archivo de asi&nación indica el mapeo de las propiedades de los objetos a los valores de columna de fla. Esta asi&nación se realia en un archivo separado, por lo &eneral sufjo .hbm.#ml. 9ebemos dejar !ue Hibernate sepa de nuestros archivos de defnición de asi&nación mediante la inclusión de una propiedad mapeo elemento en el archivo de conf&uración anterior, como se muestra a!u';6ibernateactor'= ...
;mapping resourceJ2ovie.hbm.#ml ?= ;mapping resourceJ6ccount.hbm.#ml ?= ;mapping resourceJ3rade.hbm.#ml ?= ;?session<>actor'= ;?6ibernate
El atributo d resource indica el nombre del recurso de mapeo !ue Hibernate debe car&ar. En este caso, 2ovie.hbm.#ml es el archivo de asi&nación y consta de detalles sobre cómo un objeto de 2@B>E se asi&na a una 3abla 2@B>E. sted puede ver a los demás, as', como 6ccount.hbm.#ml y 3rade.hbm.#ml. Bamos a ver estos archivos de asi&nación en un minuto. Ddealmente 9ebemos crear un 7nico SessionFactory y compartirlo a trav)s de la aplicación. 3en&a en cuenta !ue una SessionFactory se defne por una, y sólo una, la base de datos. =or ejemplo, si usted tiene otra base de datos junto a 2yS<8, debe defnir la conf&uración relevante en hibernate.hbm.#ml crear una SessionFactory separado para esa base de datos tambi)n. El objetivo de la SessionFactory es crear objetos Session. Sesión es una puerta de entrada a nuestra base de datos. Es el trabajo de la Sesión a car&o de todas las operaciones de base de datos como el insertar, car&a y recuperación de los re&istros de las tablas correspondientes. El "ramework tambi)n mantiene un medio transaccional alrededor de nuestra aplicación. 8as operaciones !ue implican el acceso a la base de datos están envueltos en una sola unidad de trabajo llamada transacción. 6s', todas las operaciones en esa transacción son ya sea e#itosa o se deshace. 3en&a en cuenta !ue la conf&uración se utilia para crear una sesión a trav)s de una instancia SessionFactory. 6ntes de continuar, ten&a en cuenta !ue los objetos de sesión no se thread;sa"e y por lo tanto no deben ser compartidos a trav)s de
di"erentes clases. Bamos a ver los detalles de la "orma en !ue deben utiliarse a medida !ue avanamos en este libro.
Crear de9niciones de asignación na ve !ue tenemos la conf&uración de cone#ión lista, el si&uiente paso es preparar el archivo 2ovie.hbm.#ml !ue consiste en las defniciones de mapeo objeto;tabla. El si&uiente "ra&mento de 28 defne el mapeo de nuestro objeto de pel'cula contra la 3abla 2@B>ES;6ibernateES= ;id nameJid columnJ>9= ;generator classJnative?= ;?id= ;propert' nameJtitle columnJ3>38E?= ;propert' nameJdirector columnJ9>AE03@A?= ;propert' nameJsynopsis columnJSR1@=S>S?= ;?class= ;?6ibernate
Hay mucho !ue hacer en este archivo de asi&nación. El elemento hibernate;mappin& tiene todas las defniciones de asi&nación de clase en tabla. 6si&naciones individuales por objeto se declaran bajo el elemento de clase. El atributo name de la eti!ueta de la clase se refere a nuestra clase de dominio =@5@ com.madhusudan.jh.domain.2ovie, mientras !ue el atributo table se refere a la tabla a la !ue se conservaran los objetos en :9. 8as propiedades restantes indican la correspondencia entre las variables del objeto a las columnas de la tabla (por ejemplo, la identifcación se asi&na a >9, el t'tulo a t'tulo, director de 9>AE03@A, etc.+. 0ada objeto debe tener un identifcador similar a una clave principal en la tabla 7nica. Hemos creado este identifcador de la aplicación de la eti!ueta de la identifcación mediante una estrate&ia nativa. 1o prestar demasiada atención a este >9 y la estrate&ia de &eneración todav'a. Bamos a discutir en detalle en los pró#imos cap'tulos.
Persistencia de los ob.etos 6hora !ue la conf&uración está "uera de nuestro camino, vamos a crear un cliente !ue persiste los objetos con la ayuda de Hibernate. 1ecesitamos la instancia SessionFactory desde el !ue creamos un objeto Session. El si&uiente "ra&mento muestra la conf&uración inicial para la creación de la clase SessionFactorypublic class asico$ieanager I pri$ate SessionFactory sessionFactory J null% // Creating SessionFactory using 4.2 version o !ibernate
pri$ate $oid initSessionFactory (+I 0onf&uration conf& J ne8 0onf&uration(+.conf&ure(+% // "uild a #egistry $ith our con%guration properties
ServiceAe&istry serviceAe&istry J ne8 ServiceAe&istry:uilder(+.applySettin&s( conf&.&et=roperties(++.buildServiceAe&istry(+% // create the session actory
sessionFactory J conf&.buildSessionFactory (serviceAe&istry+% M ... M
3en&a en cuenta !ue no tenemos !ue mencionar e#pl'citamente el mapeo o archivos de conf&uración o propiedades, ya !ue el tiempo de ejecución de Hibernate busca nombres de archivo por de"ecto, como hibernación.c"&.#ml o hibernate.properties, en la ruta de clase y los car&a. Si tenemos un nombre no predeterminado, ase&7rese de !ue pase eso como un ar&umento de conf&ure similar (my;hib.c"&.#ml+, por ejemplo.
8os ajustes anteriores para inicialiar la clase SessionFactory son para la versión más reciente de hibernate en el momento de escribir estas l'neas, .C. 8a versión .# Hibernate introdujo re&istros de servicio, !ue veremos en cap'tulos posteriores. En las versiones K.#, el m)todo conf&ure hur&a a trav)s de la ruta de clases buscando un archivo llamado hibernate.c"&.#ml (o hibernate.properties+ para crear un objeto de conf&uración. Este objeto de conf&uración se utilia para crear una instancia de SessionFactory. Si está utiliando una versión pre;.# de Hibernate, utilice el si&uiente códi&o para inicialiar el SessionFactory //Creating SessionFactory using &.x version o !ibernate
pri$ate $oid initK#(+I
sessionFactory J ne8 0onf&uration(+.conf&ure(+.buildSessionFactory (+% M
En las versiones .#, esto se modifcó li&eramente por la introducción de Service Ae&istry, !ue toma un mapa de las propiedades !ue se pueden alimentar desde un objeto de conf&uración, simplemente ha mostrado. Sea cual sea la versión !ue elija, la SessionFactory as' creado es el mismo y tambi)n lo son las Sesiones.
Creación del étodo de Persistencia 6hora el "uncionamiento real de la clase básica 2ovie2ana&er. El m)todo de persistencia se defne en la clase de persistir 2ovie utiliando el m)todo de &uardar Sesión. Esto se muestra en el si&uiente "ra&mentopublic class asico$ieanager I pri$ate $oid persist2ovie(2ovie movie+ I Session session J sessionFactory.&et0urrentSession(+% session.be&in3ransaction(+% session.save(movie+% session.&et3ransaction(+.commit(+% M M
=arece sencillo, Dno 1o escribimos códi&o innecesario o repetitivo en absoluto, pero concentrado en la "unción de ne&ocio de &uardar el objeto. En el "ra&mento anterior, lo primero !ue a&arramos es una Sesión de la "ábrica. 8ue&o creamos un objeto de transacción (vamos a aprender más sobre las transacciones en cap'tulos posteriores+, y persistir el objeto =el'cula entrante utiliando el m)todo Session.save. =or 7ltimo, nos comprometemos la transacción, y la pel'cula se almacena de "orma permanente en nuestra base de datos.
Prueba de la datos persistentes 3enemos dos "ormas de visualiar los datos persistentes- ejecutar una consulta S<8 nativo en la base de datos, o crear un cliente de prueba. =odemos ejecutar la consulta S<8 en la base de datos usando al&o como 4-(-C@ A FB 7+-4, !ue recupera todos los re&istros almacenados por nuestra apli cación. 8a consulta de selección S<8 imprime la salida, como se muestra en la 3abla ;C.
6lternativamente, podemos crear otro m)todo en nuestro cliente de pr ueba, decir fnd2ovie. Este m)todo se utilice el m)todo de car&a de la Sesión a buscar el re&istro de la base de datos. >nvocamos el m)todo fnd2ovie, pasando el >9 de la pel'cula como el ar&umento, se ha podido recuperar la pel'culapublic class asico$ieanager I ...
pri$ate $oid fnd2ovie(int movie>d+ I Session session J sessionFactory.&et0urrentSession(+% session.be&in3ransaction(+% 2ovie movie J (2ovie+session.load(2ovie.class, movie>d+% System.out.println(2ovie-Nmovie+% session.&et3ransaction(+.commit(+% M M
El m)todo de car&a en el 6=> Sesión obtiene el objeto de pel'cula apropiada para un identifcador dado. Si usted está pensando !ue Hibernate puede utiliar una instrucción SE8E03 detrás de las escenas, estás en lo correcto$ Si usted desea a buscar todas las pel'culas de la tabla, se crea un objeto de consulta con la cadena de consulta sencilla de pel'culas y ejecutarlo. El m)todo de la lista en la consulta (creada mediante session.create
pri$ate $oid fnd6ll(+ I Session session J sessionFactory.&et0urrentSession(+% session.be&in3ransaction(+% 8istV2ovieW movies J session.create
M
Con9guración de &ibernate 8a creación de un proyecto de Hibernate es "ácil. El proyecto !ue he preparado para este libro es un códi&o basado en 2aven desarrollado en 1et:eans >9E. 1o voy a entrar en detalles sobre la conf&uración del entorno, pero los si&uientes pasos deber'a ayudarle. 6un!ue he utiliado 1et:eans para el desarrollo de códi&o, puede utiliar cual!uiera de sus >9Es "avoritos para trabajar en este proyecto. 3ambi)n, usted puede intercambiar 2yS<8 con otras bases de datos, incluidos los de la memoria como 9erby o HyperS<8. En primer lu&ar, debe conf&urar el entorno de desarrollo esencial consiste en 59X U./ y versiones posteriores, 1et:eans >9E, 2aven, y la base de datos 2yS<8 (!ue puede haber tenido este entorno ya$+. He utiliado 59X Y, 1et:eans L.K, 2aven K.C y 2yS<8 U.C para desarrollar el códi&o y la versión Hibernate es .C.K.Final. na ve !ue ten&a el entorno dev ordenados, el si&uiente paso es crear un proyecto 2aven en 1et:eans (o Eclipse+. 64adir las dependencias de Hibernate apropiadas para el archivo pom.#ml como se muestra a!u'-
;pro.ect #mlnsJhttp-??maven.apache.or&?=@2?././ #mlns-#siJhttp-??www.wK.or&?C//?28Schema;instance #si-schema8ocationJhttp-??maven.apache.or&?=@2?././ http-??maven.apache.or&?#sd?maven;././.#sd= ;model7ersion=././;?model7ersion= ;group+d=com.madhusudhan;?group+d= ;arti>act+d= just;hibernate;?arti>act+d= ;$ersion=/./.;S16=SH@3;?$ersion=
;dependencies= ;dependenc'= ;group+d=or&.hibernate ;?group+d= ;arti>act+d=hibernate;core ;?arti>act+d= ;$ersion=.C.K.Final ;?$ersion= ;?dependenc'= ;dependenc'= ;group+d=mys!l;?group+d= ;arti>act+d=mys!l;connector;java ;?arti>act+d= ;$ersion=U..Z;?$ersion= ;?dependenc'= ...
;?pro.ect=
2aven resolverá las dependencias relacionadas en la construcción del proyecto. Aecomiendo descar&ar el códi&o "uente del libro y de importar el proyecto en su >9E "avorito. El si&uiente paso es la creación de su base de datos. Si usted ya tiene una base de datos, puede omitir este paso. Estoy utiliando la base de datos 2yS<8. 9escar&ue el 7ltimo pa!uete 2yS<8 e instalarlo en su e!uipo (puede !ue ten&a !ue pasar por el manual para conf&urar esto correctamente+. sted puede probar los ejemplos de este libro utiliando cual!uier otra base de datos. na ve !ue ten&a 2yS<8 (o cual!uier otra base de datos+ instalado, ase&7rese de crear un es!uema llamado 5H, como se muestra a!u'0AE63E S0HE26 5H%
8a mayor'a de las tablas de este proyecto "ue auto &enerada por Hibernate% es decir, Hibernate crear'a sobre la marcha (si no e#isten+ mediante la lectura de la conf&uración. 3enemos !ue establecer una propiedad, hbmCddl.auto, en el archivo de conf&uración de Hibernate (hibernación c"&.#ml.+ 6l valor apropiado para esta &eneración automática a suceder, de la si&uiente manera;propert' nameJhbmCddl.auto=update;?propert'=
0uando establecimos esta propiedad, las tablas se crean automáticamente si no e#isten o se actualian si hay un cambio en el es!uema de la tabla. 1unca utilice la propiedad hbmCddl.auto en la producción$ 9ebe crear un es!uema con todas las defniciones de tabla y desple&ar a la producción a trav)s de un proceso de liberación adecuado. *Eso es practicamente todo$ 1os hubiera &ustado un mecanismo !ue se esconde el meollo de la cuestión de las declaraciones 59:0 torpes y cone#iones. So4amos con la creación de m)todos de instalación !ue almacenar un objeto =@5@ directamente a la base de datos sin la molestia de establecer ? obtener las columnas. Hemos cumplido nuestros sue4os y deseos, abraando Hibernate$ sted puede tener un montón de pre&untas, pero le desmitifcado a medida !ue avanamos a trav)s de nuestro viaje, as' !ue estar atentos$
Besumen En este cap'tulo, aprendimos sobre el dominio del problema objeto;relacional;modelo caminando a trav)s de un ejemplo. 6un!ue podemos utiliar 59:0 para el acceso a datos, se encontró !ue se re!uiere una &ran cantidad de mapeo manual y códi&o innecesariamente repetitivo. 1os tomamos un pe!ue4o paso y presentó Hibernate para resolver el problema de la persistencia objeto a relacional de datos. 6 partir de un alto nivel, tomamos un vistao a los conceptos de Hibernate SessionFactory y Sesiones. Ae"actoriamos el ejemplo de 59:0 para usar el "ramework de Hibernate y con )#ito persistió y pre&unt) los =@5@s como se esperaba. En el pró#imo cap'tulo, vamos a ir a trav)s de los "undamentos de la hibernación en detalle.
-.emplo cone:ión con *C pacDage cadillacs.e#ample.jdbc%
import java.s!l.0onnection% import java.s!l.=reparedStatement% import java.s!l.AesultSet% import java.s!l.S<8E#ception% import cadillacs.beans.2ovie% public class 59:0e#ample I public static @racle0onnection conexion'racle J ne8 @racle0onnection(+% public static 0onnection conn% public static $oid main(Strin&[\ ar&s+ t6ro8s E#ception I ?? 0onecction conn J conexion'racle.&et@racle0onnection(+% System.out .println(0one#ion e#itosa...+% ?? insert movie table2ovie movie J ne8 2ovie(+% movie.set>d2ovie(+% movie.set3itle(3he 3hin&+% movie.setSynopsis(habia una ve...+% movie.set9irector(=edrito 5r.+% ?? insert2ovie(movie+% System.out .println(Se inserto re&istro e#itosamente.+% ?? read (select+ (uery)ovies(+% ?? update ?? ... ?? read (select+ ?? ... ?? delete ?? ... conn.close(+%
System.out .println(0one#ion cerrada.+% M
pri$ate static $oid !uery2ovies(+ I tr' I =reparedStatement pstmt J conn
.prepareStatement(Select O "rom movies order by moviesTid+% AesultSet rset J pstmt.e#ecute
86ile (rset.ne#t(++ I System.out .println(rset.&et>nt(+ N . 2ovie- N rset.&etStrin&(C++% M M catc6 (S<8E#ception e#+ I System.err .println(e#.&et2essa&e(++% M M
public static $oid insert2ovie(2ovie movie+ t6ro8s S<8E#ception I =reparedStatement pst J conn .prepareStatement(insert into movies (moviesTid, title, director, synopsis+ values(moviesTse!uence.1E3B68,,,++% pst.setStrin&(, movie.&et3itle(++% pst.setStrin&(C, movie.&et9irector(++% pst.setStrin&(K, movie.&etSynopsis(++% pst.e#ecute(+% pst.close(+% M
public static $oid &et2ovies(2ovie movie+ t6ro8s S<8E#ception I =reparedStatement pst J conn .prepareStatement(insert into movies (moviesTid, title, director, synopsis+ values(moviesTse!uence.1E3B68,,,++% pst.setStrin&(, movie.&et3itle(++% pst.setStrin&(C, movie.&et9irector(++% pst.setStrin&(K, movie.&etSynopsis(++% pst.e#ecute(+% pst.close(+% M M
-.emplo cone:ión con &ibernate 35: