Registering Converters in JPA 2.1 with EclipseLink

僤鯓⒐⒋嵵緔 提交于 2019-12-03 05:06:54

Give this a try and ensure you have included the correct packages.

Car entity

Stays the same

import javax.persistence.Convert;

@Entity
public class Car implements Serializable {

    [...]

    @Convert(converter = CarColorConverter.class)
    private CarColor    color;

    [...]
}

CarColor Converter

You only need the empty Annotation

import javax.persistence.AttributeConverter;
import javax.persistence.Converter;

@Converter
public class CarColorConverter implements AttributeConverter<CarColor, String> {
    [...]
}

persistence.xml

You can either

  • declare no class at all

or

  • declare every class that is involved.

As soon as you need to declare an entity manually (e.g. when it resists in a library) then you also need do declare all other entity/converter classes.

<?xml version="1.0" encoding="UTF-8"?>
<persistence 
    version="2.1"
    xmlns="http://xmlns.jcp.org/xml/ns/persistence" 
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_1.xsd">

    <persistence-unit name="xyz-restful-api" transaction-type="RESOURCE_LOCAL">

        <!-- Converters -->
        <class>com.xyz.model.converters.CarColorConverter</class>

        <!-- Entities / Model -->
        <class>com.xtz.model.Car</class>

        [...]
    </persistence-unit>
</persistence>
Petros Splinakis

My guess is that you have intermixed javax.persistence and org.eclipse.persistence.annotations packages.

Using javax.persistence package classes, you may use an empty Converter annotation on the converter class and a Convert annotation on the entity class specifying the converter class.

Frank Essenberger

Just wanted to make the small remark, that the empty @Converter annotation is supported from JPA 2.1 up via EclipseLink 1. You find the used JPA version under project(rightclick)->properties->facets.

Also note that as mentioned above, if you start to add a single class in the persistence.xml you have to add everything.

Wait till they release the patch for your application server.

https://bugs.eclipse.org/bugs/show_bug.cgi?id=443546

The release schedules pending are listed in http://www-01.ibm.com/support/docview.wss?uid=swg27004980

The workaround for now is to store it as a String and have a getter and setter that would do the transform for you like this

public final class StaticEnumToStringConverter {

    public static <E extends Enum<E>> String convertToDatabaseColumn(final E attribute) {

        if (attribute == null) {
            return null;
        }
        return attribute.toString();
    }

    public static <E extends Enum<E>> E convertToEntityAttribute(final String dbData, final Class<E> enumClass) {

        if (dbData == null) {
            return null;
        }
        for (final E c : EnumSet.allOf(enumClass)) {
            if (dbData.equals(c.toString())) {
                return c;
            }
        }
        throw new IllegalArgumentException(dbData);

    }

    private StaticEnumToStringConverter() {

    }
}

Then use in the JPA Entity as:

@NotNull
@Column(nullable = false)
private String genderAtBirth;

public Gender getGenderAtBirth() {
    return StaticEnumToStringConverter.convertToEntityAttribute(genderAtBirth, Gender.class);
}
public void setGenderAtBirth(final Gender genderAtBirth) {

    this.genderAtBirth = StaticEnumToStringConverter.convertToDatabaseColumn(genderAtBirth);
}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!