Сериализация UUID как канонической шестнадцатеричной строки в JSON с использованием JSON-B

UUID

Универсально уникальный идентификатор (UUID) является 128-битным значением. Представлено в Java java.util.UUID учебный класс.

Шестнадцатеричная строка

Для отображения и для сериализации он канонически форматируется как шестнадцатеричная строка из 36 символов, расположенных в пяти группах, разделенных дефисом. Например:
fd95cb46-8ec3-11e8-9eb6-529269fb1459

При сериализации с использованием стандартных API Java и XML и JSON я ожидаю эту шестнадцатеричную строку. Работал для XML, но не для JSON. Я не использую никаких аннотаций для XML или JSON. Мой простой POJO ничего не знает ни о XML, ни о JSON.

XML = успех

Когда я создаю XML, используя стандартную структуру XML-привязки JSR 222: JavaTM Architecture for XML Binding (JAXB) 2.0, успех. Я получаю шестнадцатеричную строку, как и ожидалось. Смотрите последний элемент этого фрагмента:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<panel>
    <connected>3.4kVA</connected>
    <fedFrom>PANEL 'EHE1' &amp; ATS-EM</fedFrom>
    <grounding>ground bus</grounding>
    <id>89d14b92-35ae-4c0c-b61d-ea8dbdeb324b</id>

JSON = ошибка

Когда я запускаю то же самое panel объект через стандартную структуру JSON-привязки JSR 367: API JavaTM для привязки JSON (JSON-B), сбой. Вместо ожидаемой шестнадцатеричной строки я получаю числа.

{"connected":"3.4kVA","fedFrom":"PANEL 'EHE1' & ATS-EM","grounding":"ground bus","id":{"leastSignificantBits":-5323841289984462261,"mostSignificantBits":-8515942329042973684},

Если вы прокрутите, вы увидите UUID с именем id представляется в виде пары чисел, а не в виде шестнадцатеричной строки:

"Идентификатор":{"leastSignificantBits":-5323841289984462261 "mostSignificantBits":-8515942329042973684}

Есть ли способ заставить привязку JSON вести себя так же, как привязка XML? Я хочу шестнадцатеричную строку, а не пару 64-битных чисел.

И, конечно, это маршалированное значение должно работать, когда не маршалируется, повторно гидратируется в объект Java.

0 ответов

В спецификации JSON-B не упоминается тип UUID, поэтому реализация зависит от того, предоставляет ли он (де) сериализатор из коробки. Однако если вы используете Eclipse Yasson (ссылка JSON-B), он по умолчанию предоставляет UUID (de) сериализатор. Я не уверен, что другие JSON-B (такие как Apache Johnzon) предоставляют по умолчанию.

Если вы используете Yasson, я бы порекомендовал открыть ошибку на их репозитории GitHub, потому что это должно работать.


Пользовательский способ

Если вы используете реализацию JSON-B, которая по умолчанию не предоставляет адаптеры UUID, вы можете создать и зарегистрировать свой собственный адаптер типа:

public static class MyUUIDAdapter implements JsonbAdapter<UUID, String> {

    @Override
    public String adaptToJson(UUID obj) throws Exception {
        return obj.toString();
    }

    @Override
    public UUID adaptFromJson(String obj) throws Exception {
        return UUID.fromString(obj);
    }

}

Самый простой способ зарегистрировать адаптер - это создать Jsonb пример:

Jsonb jsonb = JsonbBuilder.create(new JsonbConfig().withAdapters(new MyUUIDAdapter()));

Однако, если вы не контролируете создание вашего Jsonb Например (например, JAX-RS делает это под прикрытием), вы можете аннотировать поле / метод для использования адаптера:

public class Panel {
    @JsonbTypeAdapter(MyUUIDAdapter.class)
    public UUID id;
}
Другие вопросы по тегам