Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using Java records as JPA embeddables

I want to use Java records as embeddable objects with JPA. For example I want to wrap the ID in a record to make it typesafe:

@Entity
public class DemoEntity {

    @EmbeddedId
    private Id id = new Id(UUID.randomUUID());

    @Embeddable
    public static record Id(@Basic UUID value) implements Serializable {}
}

But If I try to persist it with Hibernate 5.4.32 I get the following error:

org.hibernate.InstantiationException: No default constructor for entity:  : com.example.demo.DemoEntity$Id
    at org.hibernate.tuple.PojoInstantiator.instantiate(PojoInstantiator.java:85) ~[hibernate-core-5.4.32.Final.jar:5.4.32.Final]
    at org.hibernate.tuple.component.AbstractComponentTuplizer.instantiate(AbstractComponentTuplizer.java:84) ~[hibernate-core-5.4.32.Final.jar:5.4.32.Final]
...

So it looks like Hibernate would treat the record Id like an entity, although it is an @Embeddable.

The same happens with non-id fields and @Embedded:

@Embedded
private Thing thing = new Thing("example");

@Embeddable
public static record Thing(@Basic String value) implements Serializable {}

Is there a way to use @Embeddable records with JPA/Hibernate?

like image 514
deamon Avatar asked Sep 07 '25 00:09

deamon


1 Answers

Update: Jakarta Persistence 3.2

Now supported.

According to this post, What is new in Jakarta Persistence 3.2 by F.Marchioni of 2024-11, Jakarta Persistence 3.2 (part of Jakarta EE 11) allows Java records to be used as embeddable entities.

His code example defining a record as Embeddable.

import jakarta.persistence.Embeddable;
@Embeddable
public record Employee(String name, String department, long salary) {}

And embedding that record in an Entity.

import jakarta.persistence.Entity;
import jakarta.persistence.Id;
@Entity
public class Company {
    @Id
    private Long id;
    private Employee employee;
    // Constructors, getters, and setters (if needed)
}
like image 136
Basil Bourque Avatar answered Sep 08 '25 22:09

Basil Bourque