Columna autoincremental en PostgreSQL con Java JPA

JPA facilita las consulta y actualizaciones de registros en la Base de Datos desde Java. Es la base, más allá de otros frameworks muy utilizados como Hibernate o myBatis. Facilita muchas cosas como la concurrencia o la integridad de los datos y las claves utilizadas en las bases de datos relacionales.

Sin embargo, hay bases de datos que no generan automáticamente ids autoincrementales en sus tablas al insertar un nuevo registro. Es el caso de PostgreSQL, a diferencias de otras bases de datos como SQL Server o My SQL que sí que disponen de directivas que lo facilitan. Es el caso de IDENTITY en SQL Server. Para simular este comportamiento, se pueden utilizar secuencias.

Supongamos que estamos usando Postgres y tenemos una tabla, donde el campo clave es ID y es de tipo Serial. Este tipo de datos es un entero que se genera automáticamente con una secuencia definida.

Esto puede ocasionas en Java que, cuando se intenta insertar un registro sin el campo ID (que como es el campo clave tiene la especificación «NULL = FALSE»), genera un error porque no se ha especificado el valor para el campo ID.

Para hacerle entender a java que este ID esta vacío porque se genera automáticamente en la BD y no genere la excepción, hay que hacer lo siguiente:

Lo primero sería definir la tabla y la secuencia que se utilizará para el id de dicha tabla en la base de datos. Un ejemplo sencillo, podría ser este.

-- Secuencia: cupon_id_seq

CREATE SEQUENCE cupon_id_seq;

ALTER SEQUENCE cupon_id_seq OWNER TO postgres;


-- Tabla: cupon

CREATE TABLE cupon
(
id int NOT NULL DEFAULT nextval('cupon_id_seq'),
coupon character(10),
CONSTRAINT pk_cupon PRIMARY KEY (id)
)
WITH (
OIDS=FALSE
);
ALTER TABLE cupon
OWNER TO postgres;

A continuación, en Java, se debe agregar las anotaciones @GeneratedValue y @SequenceGenerator en la clase que define el modelo de la tabla en cuestión. El nombre de la secuencia es el que se crea en Postgres.

@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "cupon_id_seq")
@SequenceGenerator(name = "cupon_id_seq", sequenceName = "cupon_id_seq")
private Long id;

Deja un comentario