0

did anyone tried to find a good solution to automatically convert all empty strings to null object on deserialization using JsonB (Yasson)?

I encountered this problem on migration from Jackson to Jsonb where empty string value in request produces deserialization exception since it cannot be parsed to object.

HTTP request payload:

{
   fieldNameUid: '', // Java property is UUID type
}

Jackson had the following configuration:

public void customize(ObjectMapper mapper) {
        mapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);
        mapper.enable(DeserializationFeature.READ_UNKNOWN_ENUM_VALUES_AS_NULL);

        SimpleModule module = new SimpleModule();
        module.addDeserializer(
                String.class,
                new StdDeserializer<>(String.class) {

                    @Override
                    public String deserialize(JsonParser parser, DeserializationContext context)
                            throws IOException {
                        String result = StringDeserializer.instance.deserialize(parser, context);
                        if (result == null || result.isBlank()) {
                            return null;
                        }
                        return result;
                    }
                });
        module.addDeserializer(byte[].class,
                new StdDeserializer<>(byte[].class) {

                    @Override
                    public byte[] deserialize(JsonParser parser, DeserializationContext context)
                            throws IOException {
                        String result = StringDeserializer.instance.deserialize(parser, context);
                        if (result == null || result.isBlank()) {
                            return null;
                        }
                        return result.getBytes(StandardCharsets.UTF_8);
                    }
                });

        mapper.registerModule(module);
    }

and current Jsonb config:

public class JsonbObjectMapper implements JsonbConfigCustomizer {

    @Override
    public void customize(JsonbConfig jsonbConfig) {

        jsonbConfig
                .withDeserializers(new StringDeserializer(), new ByteArrayDeserializer(), new EnumDeserializer())
                .withSerializers(new EnumSerializer());

    }

    public static class StringDeserializer implements JsonbDeserializer<String> {

        @Override
        public String deserialize(javax.json.stream.JsonParser jsonParser, javax.json.bind.serializer.DeserializationContext deserializationContext, Type type) {
            final String str = jsonParser.getString();
            return str == null || str.isBlank() ? null : str;
        }
    }

    public static class ByteArrayDeserializer implements JsonbDeserializer<byte[]> {

        @Override
        public byte[] deserialize(javax.json.stream.JsonParser jsonParser, javax.json.bind.serializer.DeserializationContext deserializationContext, Type type) {
            final String str = jsonParser.getString();
            return str == null || str.isBlank() ? null : str.getBytes(StandardCharsets.UTF_8);
        }
    }

    public static class EnumDeserializer implements JsonbDeserializer<Enum> {

        @Override
        public Enum deserialize(javax.json.stream.JsonParser jsonParser, javax.json.bind.serializer.DeserializationContext deserializationContext, Type type) {

            final String str = jsonParser.getString();
            if (str == null || str.isBlank()) {
                return null;
            }
            for (final Enum en : ((Class<Enum>) type).getEnumConstants()) {
                if (en.toString().equals(str)) {
                    return en;
                }
            }

            return null;
        }
    }

    public static class EnumSerializer implements JsonbSerializer<Enum> {

        @Override
        public void serialize(Enum anEnum, JsonGenerator jsonGenerator, SerializationContext serializationContext) {
            jsonGenerator.write(anEnum == null ? null : anEnum.toString());
        }
    }
}

1 Answer 1

0

Since there is no alternative property for JsonB, I ended up writing custom deserialiser for UUID type.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.