FasterXML / FasterXML/jackson-modules-base

Registering JaxbAnnotationModule causes custom PropertyNamingStrategy to be ignored

Đang mở
#137 4 bình luận 0 reaction 0 người được giao Xem trên GitHub
jaxb-annotations
Ngôn ngữ chính
Java
Star
180
Fork
80
Merge trung bình
3 giờ 26 phút
Pull request đã merge (30 ngày)
1

Mô tả

I am trying to use the JaxbAnnotationModule when serialising a jaxb object to string. I am trying to achieve two things:

1. enums should be serialised with the jaxb enum value, rather than the java enum name
2. xml attributes names should be prefixed with the '@' symbol

I had hoped to use JaxbAnnotationModule to achieve 1. and a custom PropertyNamingStrategy to achieve 2. They work separately, but when I try to use both together, the custom PropertyNamingStrategy seems to never be invoked.

I don't know if my approach is wrong, or if this is a bug. Any help would be appreciated. Below is a pom.xml and junit 5 test that should reproduce the issue.

```xml

4.0.0
com.example
jaxb-jackson
0.0.1-SNAPSHOT




maven-surefire-plugin
2.22.2






com.fasterxml.jackson.module
jackson-module-jaxb-annotations
2.12.3


org.junit.jupiter
junit-jupiter-api
5.7.2
test


org.junit.jupiter
junit-jupiter-engine
5.7.2
test

```

```java
package com.example.jaxbjackson;

import static org.junit.jupiter.api.Assertions.assertEquals;
import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlAttribute;
import javax.xml.bind.annotation.XmlEnum;
import javax.xml.bind.annotation.XmlEnumValue;
import javax.xml.bind.annotation.XmlRootElement;
import javax.xml.bind.annotation.XmlType;
import org.junit.jupiter.api.Test;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.PropertyNamingStrategy;
import com.fasterxml.jackson.databind.cfg.MapperConfig;
import com.fasterxml.jackson.databind.introspect.AnnotatedField;
import com.fasterxml.jackson.databind.introspect.AnnotatedMember;
import com.fasterxml.jackson.databind.introspect.AnnotatedMethod;
import com.fasterxml.jackson.module.jaxb.JaxbAnnotationModule;

public class JaxbToJsonConverterTest {

@Test
public void usesCustomPropertyNamingStrategy() throws Exception {
AnXmlElement xmlelement = new AnXmlElement();
xmlelement.setAnXmlAttribute(AnXmlAttributesEnumValue.VALUE_ONE);

ObjectMapper mapper = new ObjectMapper();
mapper.setPropertyNamingStrategy(new AtSymbolPropertyNamingStrategy());
String json = mapper.writeValueAsString(xmlelement);

String[] split = json.split(":");

assertEquals("{\"@AnXmlAttribute\"", split[0]);
}

@Test
public void usesJaxBAnnotationToDeriveEnumValue() throws Exception {
AnXmlElement xmlelement = new AnXmlElement();
xmlelement.setAnXmlAttribute(AnXmlAttributesEnumValue.VALUE_ONE);

ObjectMapper mapper = new ObjectMapper();
mapper.registerModule(new JaxbAnnotationModule());
String json = mapper.writeValueAsString(xmlelement);

String[] split = json.split(":");

assertEquals("\"Value One\"}", split[1]);
}

@Test
public void usesJaxBAnnotationAndCustomPropertyNamingStrategyTogether() throws Exception {
AnXmlElement xmlelement = new AnXmlElement();
xmlelement.setAnXmlAttribute(AnXmlAttributesEnumValue.VALUE_ONE);

ObjectMapper mapper = new ObjectMapper();
mapper.registerModule(new JaxbAnnotationModule());
mapper.setPropertyNamingStrategy(new AtSymbolPropertyNamingStrategy());
String json = mapper.writeValueAsString(xmlelement);

String[] split = json.split(":");

// below assertion fails because AtSymbolPropertyNamingStrategy is ignored
assertEquals("{\"@AnXmlAttribute\"", split[0]);
assertEquals("\"Value One\"}", split[1]);
}

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "")
@XmlRootElement(name = "AnXmlElement")
static class AnXmlElement {

@XmlAttribute(name = "AnXmlAttribute")
protected AnXmlAttributesEnumValue anXmlAttribute;


public AnXmlAttributesEnumValue getAnXmlAttribute() {
return anXmlAttribute;
}

public void setAnXmlAttribute(AnXmlAttributesEnumValue value) {
this.anXmlAttribute = value;
}
}


@XmlType(name = "anXmlAttributesEnumValues")
@XmlEnum
static enum AnXmlAttributesEnumValue {

@XmlEnumValue("Value One")
VALUE_ONE("Value One");

private final String value;

AnXmlAttributesEnumValue(String v) {
value = v;
}

public String value() {
return value;
}

public static AnXmlAttributesEnumValue fromValue(String v) {
for (AnXmlAttributesEnumValue c: AnXmlAttributesEnumValue.values()) {
if (c.value.equals(v)) {
return c;
}
}
throw new IllegalArgumentException(v);
}
}

@SuppressWarnings("serial")
static class AtSymbolPropertyNamingStrategy extends PropertyNamingStrategy {

private String fieldName(AnnotatedMember member, String defaultName) {
XmlAttribute xmlAttributeAnnotation = member.getAllAnnotations().get(XmlAttribute.class);

if (xmlAttributeAnnotation != null) {
return "@" + xmlAttributeAnnotation.name();
}

return defaultName;
}

@Override
public String nameForGetterMethod(MapperConfig config, AnnotatedMethod method, String defaultName) {
return fieldName(method, defaultName);
}

@Override
public String nameForField(MapperConfig config, AnnotatedField field, String defaultName) {
return fieldName(field, defaultName);
}

@Override
public String nameForSetterMethod(MapperConfig config, AnnotatedMethod method, String defaultName) {
return fieldName(method, defaultName);
}
}
}

```

Hướng dẫn đóng góp

Chưa lập chỉ mục được hướng dẫn đóng góp cho kho mã nguồn này

Đánh giá

Issue này chưa được đánh giá.

Nhận issue mới trong hộp thư của bạn

Bản tóm tắt ngắn những issue GitHub phù hợp với người mới.