如果匹配的Java-Class使用绑定到 abstract 类的泛型类型,我遇到了一个关于使用JAXB解组XML文件的问题。
我已经就这种行为(java.net/jira)提交了一个错误报告,但是我错过了什么或有人有想法解决这个问题?所以这是我的问题:
在下面的示例中,我需要任何类型的Number的边界,但是JAXB尝试通过实例化为Number来解组它,这是抽象的。 省略边界或将其更改为可实例化的类型(如Object)可以解决问题,但会削弱泛型。
以下示例显示了这一点,请参阅附带的注释。删除取消激活类型边界的注释,此程序将失败。
import java.io.StringReader;
import java.io.StringWriter;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.Marshaller;
import javax.xml.bind.Unmarshaller;
import javax.xml.bind.annotation.XmlElement;
import javax.xml.bind.annotation.XmlRootElement;
public class JaxbTester {
/*
* AbstractContainer<T> -> works, but misses boundaries
* AbstractContainer<T extends Object> -> works, but boundaries are too large
* AbstractContainer<T extends Number> -> fails: "Exception in thread "main" javax.xml.bind.UnmarshalException: Unable to create an instance of java.lang.Number"
*/
static abstract class AbstractContainer<T /* extends Number */> {
@XmlElement
T someNumber;
}
@XmlRootElement
static class ContainerImpl<T extends Number> extends AbstractContainer<T> {
@SuppressWarnings("unused")
private ContainerImpl() {
// for JAXB
}
public ContainerImpl(final T someNumber) {
this.someNumber = someNumber;
}
}
/**
* @param args
*/
public static void main(final String[] args) throws Exception {
final AbstractContainer<Double> containerA = new ContainerImpl<>(42.5);
final JAXBContext context = JAXBContext.newInstance(ContainerImpl.class);
final Marshaller marshaller = context.createMarshaller();
marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
final StringWriter stringWriter = new StringWriter();
marshaller.marshal(containerA, stringWriter);
final String xmlString = stringWriter.toString();
System.out.println(xmlString);
final Unmarshaller unmarshaller = context.createUnmarshaller();
unmarshaller.setEventHandler(event -> {
System.err.println("!! " + event.getMessage() + " - " + event.getLocator() + "\n");
return true;
});
final Object unmarshal = unmarshaller.unmarshal(new StringReader(xmlString));
System.out.println("unmarshal: " + unmarshal.toString());
}
}
对此有何建议?谢谢!
答案 0 :(得分:0)
我遇到了一个可能的解决方案(让我们称之为解决方法&#39;解决方法&#39;)以解决我的问题:
将@XmlElement T someNumber;
更改为@XmlElement(type = Object.class) T someNumber;
。这为JAXB提供了可实例化的Object-Class的完全自由......实际上,返回的Value-Object的类型为Double
,因此内部转换似乎有效...除了必须注释每个字段 - 任何其他警告呢?