Suppose, we have 2 RESTful webservices (JAX-RS). The first service acts as a consumer and calls the API of the second service. The second service (provider) is generated using the openapi-generator-maven-plugin
with jaxrs-spec option and an underlying .yml-file describing the API. Both the provider- and the consumer webservices are deployed successfully on the Weblogic application server and serve requests as expected...
... with one little exception. The serialization / deserialization of Enums is not working as expected. Eums are generated with the corresponding Jackson2 Annotations @JsonValue
and @Jsoncreator
:
public enum MyEnum {
FIRST_VALUE("first_value"),
SECOND_VALUE("second_value");
private static Map<String, MyEnum> ENUM_MAP = Stream
.of(MyEnum.values())
.collect(Collectors.toMap(s -> s.formatted, Function.identity()));
private final String value;
private MyEnum(String value) { this.value = value; }
@JsonValue
public String value() { return value; }
@JsonCreator
public static MyEnum fromString(String string) {
return Optional
.ofNullable(ENUM_MAP.get(string))
.orElseThrow(() -> new IllegalArgumentException(string));
}
}
The expectation would be (assuming the Jackson annotations would not be ignored by the ObjectMapper) that a Java object MyEnum.FIRST_VALUE
gets serialized as {"first_value"}
. However, the result (what the provider webservice receives and the consumer webservice sends) is {"FIRST_VALUE"}
. How come? Weblogic uses MOXy as default JSON provider. And MOXy ignores the above mentioned Jackson2 Annotations.
The question, therefore is: How can I make the webservice receive {"first_value"}
instead of {"FIRST_VALUE"}
and how am I supposed to adjust my JAX-RS Jersey Client (in the first webservice) in order to pass the value {"first_value"}
to my second webservice when called using
Client client = ClientBuilder().newClient();
client.target(MY_URI)
.request(MediaType.APPLICATION_JSON)
.post(Entity.entity(MyEnum.FIRST_VALUE, MediaType.APPLICATION_JSON));
I tried the following:
- Finding out that serialization / deserialization works correctly in a Java SE environment when we use Jackson as JSON provider (after adding the corresponding maven coordinates). Please click here, my example Enum looks the same (plus
@JsonValue
Annotation, minus@JsonProperty
). However, serialization works as expected in a Java SE Unit-Test - Finding out that MOXy needs JAXB-Annotations, so we could use the
openapi-generator-maven-plugin
to generate JAXB-Annotations. See here. Seems a little too complicated to achieve the goal. - Writing a custom XmlAdapter, see here. Why would we do that, when Jackson does the marshalling out of the box?
- Disable MOXy as default JSON provider, see here. Actually, this solves the problem on the producer side, but what about the consumer? The client still sends the "wrong" JSON, so that the service throws an Exception.