hibernate postgresql jpa jpa-2.0

hibernate - Cómo asignar “marca de tiempo con zona horaria” de postgresql en una entidad JPA 2



jpa-2.0 (2)

Agregar @Column(columnDefinition= "TIMESTAMP WITH TIME ZONE")

@Column(name = "run_from", columnDefinition= "TIMESTAMP WITH TIME ZONE") @NotNull @Temporal(TemporalType.TIMESTAMP) private Date runFrom;

Tengo una aplicación JPA 2 (con Hibernate 3.6 como implementación de JPA) que utiliza Postgresql (con el controlador JDBC 9.0-801.jdbc3).

Tengo problemas para asignar los campos de "marca de tiempo con zona horaria" en mis entidades JPA.

Aquí hay un ejemplo:

CREATE TABLE theme ( id serial NOT NULL, # Fields that are not material to the question have been edited out run_from timestamp with time zone NOT NULL, run_to timestamp with time zone NOT NULL, CONSTRAINT theme_pkey PRIMARY KEY (id ), CONSTRAINT theme_name_key UNIQUE (name ) )

He tratado de mapear de la siguiente manera:

@Entity @Table(schema = "content", name = "theme") public class Theme extends AbstractBaseEntity { private static final long serialVersionUID = 1L; @Column(name = "run_from") @NotNull @Temporal(TemporalType.TIMESTAMP) private Date runFrom; @Column(name = "run_to") @NotNull @Temporal(TemporalType.TIMESTAMP) private Date runTo; /* The rest of the entity has been edited out */

Sigo recibiendo una excepción con la siguiente causa raíz: Caused by: org.hibernate.HibernateException: Wrong column type in public.backend_themetopic for column created. Found: timestamptz, expected: date Caused by: org.hibernate.HibernateException: Wrong column type in public.backend_themetopic for column created. Found: timestamptz, expected: date

Lo que he intentado

  • reemplazar java.util.Calendar con java.util.Date - no hizo ninguna diferencia
  • utilizando java.sql.Timestamp - se quejó de que no puedo aplicar la anotación @Temporal a una Timestamp
  • el uso de org.joda.time.DateTime con una anotación @Type personalizada ( @Type(type="org.joda.time.contrib.hibernate.PersistentDateTimeTZ") ) tampoco funcionó

Restricciones

  • Esta aplicación interactúa con un "sistema heredado", por lo que cambiar los tipos de campos de fecha no es una buena opción

Mi pregunta es: ¿cómo debo asignar estas marcas de tiempo conscientes de la zona horaria en mis entidades JPA?


Eventualmente hice este "trabajo", de una manera un tanto hackada, desactivando la validación del esquema.

Anteriormente, tenía <property name="hibernate.hbm2ddl.auto" value="validate"/>"hibernate.hbm2ddl.auto" en mi persistence.xml. Cuando comenté esta propiedad, mi servidor de aplicaciones se inició y el modelo "funcionó".

La forma final de mi entidad fue:

@Entity @Table(schema = "content", name = "theme") public class Theme extends AbstractBaseEntity { private static final long serialVersionUID = 1L; @Column(name = "run_from", columnDefinition = "timestamp with time zone not null") @NotNull @Temporal(TemporalType.TIMESTAMP) private Date runFrom; @Column(name = "run_to", columnDefinition = "timestampt with time zone not null") @NotNull @Temporal(TemporalType.TIMESTAMP) private Date runTo; /* Getters, setters, .hashCode(), .equals() etc omitted */

Después de leer un poco sobre esto, tengo la impresión de que no hay una manera fácil de asignar la marca de tiempo Postgresql con columnas de zona horaria.

Algunas combinaciones de implementación de JPA + base de datos admiten esto de forma nativa (EclipseLink + Oracle es un ejemplo). Para hibernar, con las extensiones de jodatime, es posible almacenar marcas de tiempo conscientes de la zona horaria utilizando una marca de tiempo normal + un campo varchar para la zona horaria (no pude hacerlo ya que me vi obligado a cambiar el esquema de la base de datos). Los tipos de usuario de Jadira o los tipos de usuario completamente personalizados también se pueden usar para abordar este problema.

Debo señalar que mi caso de uso para esta entidad es "solo lectura", por lo que podría salirme con una "solución" aparentemente ingenua.