Te agrego algo mas:

La solucion q te propongo es la nro 2 tuya, revisada:
  2. Uso los id numericos pero en hash code y equal uso los
identificadores naturales MAS LOS IDENTIFICADORES NUMERICOS.

El ID numerico q te propone el Hibernate seria algo asi como el DNI de cada
objeto de la clase.
Imaginate si nosotros en la vida diaria usaramos el nombre o la direccion
como identificadores de nuestra persona, los lios q se harian si alguien se
muda, o resulta q te anotan mal el nombre en algun lugar =P

Te cuento experiencias laborales trabajando con modelos de datos q llevaban
por PK algun "identificador natural":

Cliente > id natural: CUIT.
Luego de realizar varias operaciones en el sistema con un cliente X, un
usuario te dice "che, hay q cambiar el cuit de X pues esta mal cargado."
Rta: ayy...no  se puede...pues es la PK de la tabla Cliente y todas las
operaciones joinean por el CUIT..."

Producto > id natural: Cod Producto
Luego de realizar varias campañas con un catalogo de productos, vienen y te
dicen "para la proxima campaña vamos a anteponerle a todos los codigos de
producto un XX- pues tenemos otro sistema para contabilidad y necesitamos
que sea asi..."
Grrrrr....updates masivos por todos lados....dolores de cabeza, etc...

y asi, mil casos mas...

Saludos!
MA_Xx


2009/5/25 Maximiliano Milicich <[email protected]>

> Mi sugerencia por experiencia:  NO USES COMO PK CAMPOS DE DATOS !! Mantene
> como PK de cada objeto el ID numerico que asigna Hibernate...
> Luego, como dice Carlos Charlie, si realmente necesitas asegurar la
> unicidad de los datos, agregas constraints unique
>
> Tambien citando a Charlie, si la PK de un registro es uno o mas campos de
> datos, estos se van a replicar en otras tablas que refieran al registro
> (como FK)...si luego necesitas actualizar alguno de estos campos de datos,
> es un dolor de cabeza mantener la integridad...
>
> Es decir, como regla de oro: el campo de identificacion unica de una tabla
> NO debe ser un campo que tenga datos del negocio...
> Ahora cuando lo estas construyendo, hay ciertos campos de datos que
> "parecen ser inmutables y unicos", pero luego el negocio cambia, y ahi el
> modelo de datos ya queda inmantenible.
>
> Con respecto a hashcode() y equals(): podes sobreescribirlos, agregandoles
> la validacion de unicidad de tus campos.
> Es decir (sorry, no recuerdo java muy bien), algo asi como:
>
> public class Cliente {
> /*
> ....
> */
> public boolean equals(Object b) {
>    return (super.equals(b) && this.getCUIT().equals(b.getCUIT()));
> }
>
> };
>
> Saludos!!
> MA_Xx
>
> 2009/5/25 Carlos Charlie <[email protected]>
>
>  Pensa a nivel base de datos, suponete que usas un codigo alfanumerico
>> como PK de una tabla. Si tuvieras otra tabla con una FK a la primera, este
>> seria un campo alfanumerico tambien y de esa manera estas ocupando mas
>> espacio que el que ocuparia un long. Ademas las comparaciones de las
>> consultas tardan mas tiempo cuando se trata de comparar campos
>> alfanumericos. Es por eso que generalmente se usa un long ya que no molesta
>> y te ahorras problemas, pero bien podrias usar un PK compuesta si quisieras
>> aunque en lineas generales no tienen ventaja alguna.
>>
>> Tu problema particular de que si usas un long como PK no podes validar
>> naturalmente que un campo sea unico se resuelve si usar equals, no hace
>> falta que un campo sea PK para que sea UNIQUE, o sea si queres que tu campo
>> nombre sea unico y no pertenezca a tu clave primaria simplemente agrega en
>> tu base de datos una constraint unique al campo nombre y listo. Eso en la
>> entidad se ve reflejado colocando una annotation de JPA en donde indicas que
>> ese campo es unique, incluso creo que esa misma annotation podes usarla con
>> Hibernate Validator para hacer las validaciones de negocio, pero nunca
>> investigue demasiado.
>>
>> Siempre fijate si podes evitar el equals, por ejemplo tal vez no haga
>> falta usar un contains de una coleccion para saber si un elemeno esta o no,
>> tal vez te convenga directamente ejecutar una query con algun WHERE y si la
>> coleccion que te retorna esta vacia es porque el elemento no existe. Al
>> reducir al minimo el uso del equals vas a llegar a la conclusion que con un
>> equals que solo analiza id alcanza, si no es asi entonces yo escogeria tu
>> opcion numero 3 en donde en lugar de implementar mi metodo equals2
>> implementaria un metodo que valide cada regla de validacion en particular
>> para que esas reglas de validacion se vean claramente reflejadas en el
>> codigo, esos metodos los pondria en una clase aparte que llamaria Validator.
>>
>>
>> ------------------------------
>> Date: Mon, 25 May 2009 14:21:18 -0300
>> Subject: Re: [Prog] Base de datos + Id numerico en vez de identificador
>> natural de la entidad + java
>> From: [email protected]
>> To: [email protected]
>>
>>
>> Hace rato que no uso Hibernate, pero si no mal recuerdo, una de las buenas
>> razones para usar un id por separado,
>> era que le podías indicar a Hibernate que lo asigne automáticamente. De
>> esta manera, te desligás de la tarea de mantener la consistencia en la base
>> de datos desde tu código de entidad.
>> De hacerlo así, no deberías usar el id de la base en el equals/hash, por
>> que estos se generarán una vez que persistas el objeto (y realmente no
>> tienen significado "de negocio"). Acá se discute esto:
>> https://www.hibernate.org/109.html
>>
>> Saludos.
>>
>> El 25 de mayo de 2009 13:07, Victor Del Rio <[email protected]
>> > escribió:
>>
>> Buenas, estoy trabajando con un modelo en java que va a persistir con
>> hibernate y me surgio una duda:
>>
>> 1. ¿Porque usar un id numerico (ej: Long id) envez de usar los campos
>> que realmente identifican a la entidad?
>>
>>   Yo me imagino que sera por el tema de el tamaño que tomaría la base
>> de datos.
>>
>>   Pero el tema es que eso, y usar el hashCode y equals con el id no
>> me permiten validar naturalmente
>>   algunas reglas del negocio como por ejemplo si yo no quiero que
>> haya dos o mas entidades del mismo
>>   nombre (porque ese era su identificador natural) ya no me sirve el
>> equals, ni el contains de
>>   collection ni nada.
>>
>>   Entonces me surgen tres opciones de las cuales no se cual es mas
>> conveniente, talvez inclusive alguna no sea valida:
>>
>>   1. No uso id numerico sino que uso los identificadores naturales
>> (ej: nombre, dni) y uso tambien estos
>>      para el hash code y equals.
>>
>>   2. Uso los id numericos pero en hash code y equal uso los
>> identificadores naturales.
>>
>>   3. Uso los id numericos, tambien en el hash code y equals, pero
>> agrego un metodo mas a las clases entidad que
>>      compare por los identificadores naturales (algo asi como
>> "obj.igualSegunNegocio(otroObj)") y uso ese metodo
>>      para comparar en el modelo.
>>
>> Bueno agradezco cualquier sugerencia, saludos.
>>
>> _______________________________________________
>> Lista de correo Programacion.
>> [email protected]
>> http://listas.fi.uba.ar/mailman/listinfo/programacion
>>
>>
>>
>> ------------------------------
>> Qué preferís: ¿El día o la noche? ¿el verde o el rojo? ¡Descubrí quién
>> sos realmente! <http://www.descubrewindowslive.com/>
>>
>> _______________________________________________
>> Lista de correo Programacion.
>> [email protected]
>> http://listas.fi.uba.ar/mailman/listinfo/programacion
>>
>>
>
_______________________________________________
Lista de correo Programacion.
[email protected]
http://listas.fi.uba.ar/mailman/listinfo/programacion

Responder a