Imagine I have a simple table such as the following, defined using a liquibase changeset
<databaseChangeLog
xmlns="http://www.liquibase.org/xml/ns/dbchangelog"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.liquibase.org/xml/ns/dbchangelog http://www.liquibase.org/xml/ns/dbchangelog/dbchangelog-latest.xsd">
<changeSet author="..." id="uuid-ossp-extension">
<sql>CREATE EXTENSION IF NOT EXISTS "uuid-ossp"</sql>
</changeSet>
<changeSet author="example" id="widgets-table">
<createTable tableName="widgets">
<column name="widget_id" type="uuid" defaultValueComputed="uuid_generate_v1mc()">
<constraints nullable="false" primaryKey="true" primaryKeyName="widget_pk"/>
</column>
<column name="name" type="varchar(10)">
<constraints nullable="false"/>
</column>
</createTable>
</changeSet>
</databaseChangeLog>
That is, I want to be explicit about letting postgres compute the UUID.
If I was using Spring JdbcTemplate, I could use something simple like:
@Repository
@RequiredArgsConstructor
public class WidgetRepository {
public static final String INSERT_QUERY = "INSERT INTO widgets(name) VALUES (:name)";
private final NamedParameterJdbcTemplate template;
public UUID saveAndReturn(Widget widget) {
var params = new MapSqlParameterSource(Map.of("name", widget.getName());
var generatedKeyHolder = new GeneratedKeyHolder();
var generateKeyColumns = new String[]{"widget_id"};
template.update(INSERT_QUERY, params, generatedKeyHolder, generateKeyColumns);
return generatedKeyHolder.getKeyAs(UUID.class);
}
...
}
With Hibernate 6.0 onwards, there is a new UuidGenerator annotation, that simplifies Hibernate taking responsibility for generating a UUID:
@Entity
@Table(name = "widgets")
public class Widget {
@Id
@UuidGenerator(style = TIME)
@Column(name = "widget_id")
private UUID id;
@Column
private String name;
...
}
However, this new UUIDGenerator mechanism doesn't seem to support delegating to postgres. https://vladmihalcea.com/uuid-identifier-jpa-hibernate/ suggested an alternative approach, but the UUIDGenerationStrategy it implements is now deprecated.
Does anyone know the preferred mechanism for Hibernate 6.0 onwards?
I tweeted about this here:
https://twitter.com/1ovthafew/status/1645795161379831811
The short answer is:
@Entity
public class Entity {
@Generated @Id
@ColumnDefault("gen_random_uuid()")
UUID uuid;
}
Note that Hibernate 6.2 is required.