为了账号安全,请及时绑定邮箱和手机立即绑定

通用类的 JAXB 序列化失败

通用类的 JAXB 序列化失败

千万里不及你 2021-09-12 19:41:47
我正在尝试编写一个可以使用 Java 将设置序列化和反序列化到 XML 的类。我用 C# 成功编写了这段代码,它非常有用,所以我想在我的 Java 应用程序中使用类似的东西。我有以下基类,我想要序列化为 XML 的每个类都必须实现。package serializers;import java.lang.reflect.ParameterizedType;abstract class XmlSerializableObject<T> {    abstract T getDefault();    abstract String getSerializedFilePath();    String getGenericName() {        return ((Class<T>) ((ParameterizedType) getClass()            .getGenericSuperclass()).getActualTypeArguments()[0]).getTypeName();    }    ClassLoader getClassLoader() {        return ((Class<T>) ((ParameterizedType) getClass()            .getGenericSuperclass()).getActualTypeArguments()[0]).getClassLoader();    }}其中getGenericName和getClassLoader用于实例化JAXBContext. 然后我有一个基本的实现作为设置提供者public class SettingsProvider extends XmlSerializableObject<SettingsProvider> {    private Settings settings;    @Override    public SettingsProvider getDefault() {        return null;    }    @Override    public String getSerializedFilePath() {        return "C:\\Data\\__tmp.settings";    }    public Settings getSettings() {        return settings;    };    public void setSettings(Settings settings) {        this.settings = settings;    }}class Settings {    private String tmp;    public String getTmp() {        return tmp;    }    public void setTmp(String tmp) {        this.tmp = tmp;    }}现在我有以下序列化程序类package serializers;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import javax.xml.bind.JAXBContext;import javax.xml.bind.JAXBException;import javax.xml.bind.Marshaller;import javax.xml.bind.Unmarshaller;import java.io.File;问题是JAXBContext jaxbContext = JAXBContext.newInstance(name, classLoader);抛出的调用javax.xml.bind.JAXBException:无法实例化提供程序 com.sun.xml.internal.bind.v2.ContextFactory:javax.xml.bind.JAXBException:“serializers.SettingsProvider”不包含 ObjectFactory.class 或 jaxb.index -带有链接异常:[javax.xml.bind.JAXBException:“serializers.SettingsProvider”不包含 ObjectFactory.class 或 jaxb.index]我试过有和没有ClassLoader对象都无济于事。如何以这种方式序列化泛型类型?谢谢你的时间。
查看完整描述

3 回答

?
大话西游666

TA贡献1817条经验 获得超14个赞

看起来应该是这样JAXBContext.newInstance(SettingsProvider.class)

JAXBContext.newInstance(String ...)方法的版本需要一个包名,正如错误消息所说,它应该包含一个ObjectFactory类,或jaxb.index将其引导到类的列表。


查看完整回答
反对 回复 2021-09-12
?
茅侃侃

TA贡献1842条经验 获得超21个赞

您正在使用此newInstance方法:


参数:


contextPath -包含模式派生类和/或 java 到模式(JAXB 注释)映射类的java 包名称列表


classLoader - 该类加载器将用于定位实现类。


所以 df778899 是对的,你不应该使用这个签名作为getGenericName返回一个完全限定的类名而不是一个包。即使是包裹,您仍然会错过ObjectFactory.class或jaxb.index


但JAXBContext.newInstance(SettingsProvider.class)也不会奏效。你会得到一个缺少的MarshalException指示@XmlRootElement


SettingsProvider像这样注释:


@XmlRootElement(name = "root")

static class SettingsProvider extends XmlSerializableObject<SettingsProvider>

{


    private Settings settings;


    // [...]

最后你会得到:


<?xml version="1.0" encoding="UTF-8" standalone="yes"?>

<root>

    <settings>

        <tmp>testing</tmp>

    </settings>

</root>


查看完整回答
反对 回复 2021-09-12
  • 3 回答
  • 0 关注
  • 252 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信