11

我有一个 XSD,我想从中支持 JSON 和 XML 数据格式的序列化/反序列化。

xjc我使用实用程序生成了我的模型类。

所以到目前为止,我已经使用 Jackson JSON 库处理了 JSON 数据。

我无法修改我的 Java 类,因此我配置ObjectMapperMix-In annotations其他功能,例如PropertyNamingStrategy(更改字段名称),SerializationFeature.WRAP_ROOT_VALUE以通过代码提供对我的序列化的配置。

现在我想对 XML 序列化过程做同样的事情。

我已经在线阅读了各种选项:

  1. JAXB
  2. Jackson 库 + Jackson-dataformat-xml.jar
  3. XStream

哪个最适合我的情况(不能用注释编辑我的 POJO,只允许代码配置)??

4

3 回答 3

7

我的投票是#2 Jackson 库 + Jackson-dataformat-xml.jar 看看 JSON 和 XML 的代码,这里和那里的位变化是一样的。

主类

  import com.fasterxml.jackson.annotation.JsonAutoDetect.Visibility;
  import com.fasterxml.jackson.annotation.PropertyAccessor;
  import com.fasterxml.jackson.core.JsonProcessingException;
  import com.fasterxml.jackson.databind.ObjectMapper;
  import com.fasterxml.jackson.databind.SerializationFeature;
  import com.fasterxml.jackson.dataformat.xml.XmlMapper;

 public class MainClass {

public static void main(String[] args) throws JsonProcessingException {

    // Serialization: java obj to json--> writeValueAsString
    // DeSerialization: json to java obj--> ReadValue

    XmlMapper mapper1 = new XmlMapper();
    ObjectMapper mapper2 = new ObjectMapper();

    mapper1.setVisibility(PropertyAccessor.FIELD, Visibility.ANY);
    mapper2.setVisibility(PropertyAccessor.FIELD, Visibility.ANY);

    mapper1.enable(SerializationFeature.INDENT_OUTPUT);
    mapper2.enable(SerializationFeature.INDENT_OUTPUT);

    MyPojo mypojo = new MyPojo();
    mypojo.setName("Dhani");
    mypojo.setId("18082013");
    mypojo.setAge(5);

    String jsonStringXML = mapper1.writeValueAsString(mypojo);
    String jsonStringJSON = mapper2.writeValueAsString(mypojo);
    // takes java class with def or customized constructors and creates JSON

    System.out.println("XML is " + "\n" + jsonStringXML + "\n");
    System.out.println("Json is " + "\n" + jsonStringJSON);
}   }

MyPojo.java

   import com.fasterxml.jackson.annotation.JsonIgnore;
   import com.fasterxml.jackson.annotation.JsonProperty;
   import com.fasterxml.jackson.annotation.JsonPropertyOrder;
   import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlRootElement;

  @JsonPropertyOrder({ "name", "age", "id", "note" })
  @JacksonXmlRootElement(namespace = "urn:stackify:jacksonxml", localName = "myPOJO")
   public class MyPojo {

@JsonProperty("_id")
private String id;

private String name;

private int age;

@JsonIgnore
private String note;

public String getNote() {
    return note;
}

public void setNote(String note) {
    this.note = note;
}

public String getId() {
    return id;
}

public void setId(String id) {
    this.id = id;
}

public String getName() {
    return name;
}

public void setName(String name) {
    this.name = name;
}

public int getAge() {
    return age;
}

public void setAge(int age) {
    this.age = age;
} }

结果

XML

        <myPOJO xmlns="urn:stackify:jacksonxml">
        <name xmlns="">Dhani</name>
         <age xmlns="">5</age>
         <_id xmlns="">18082013</_id>
         </myPOJO>

json

     {
      "name" : "Dhani",
       "age" : 5,
       "_id" : "18082013"
         }
于 2019-03-10T03:33:52.500 回答
5

我投票支持答案 #2:使用 Jackson-dataformat-xml。我们遇到了类似的情况,发现通过 Jackson 序列化为 XML 比预期的要容易。这是因为XmlMapper扩展ObjectMapper了,所以我们所有的配置更改(混合、使用JavaTimeModule等)都可以直接应用,XmlMapper并且它们可以正常工作。

您已经将 Jackson 配置为根据需要输出数据,因此完成了困难的部分。我建议利用您已经投入的努力并使用 Jackson-dataformat-xml。

于 2016-11-17T16:43:01.853 回答
0

我为我的 XML 序列化/反序列化选择了 JAXB,因为我已经有一个 XML 模式,并且想要以 JAXB 提供的方式作为原生 XML 库的 XML。即使 Jackson xml 满足您的需求,它也是一个不错的选择。

Jackson XML 模块的限制:

Jackson 中的 XML 模块绝不是为了完全替代 JAXB 而设计的。在 JAXB 和 Jackson 之间,某些结构的工作方式会略有不同,并且不能保证 Jackson 会生成与 JAXB 相同的 XML。

请注意,与 JSON 不同,最外层对象必须是 bean 类型——它不能是原始类型或包装类型、枚举或集合。这是 XML 工作方式的直接结果——在 XML 中无法表示这样的顶级值。

默认情况下,Jackson 将始终为集合使用包装器元素,这也与 JAXB 的工作方式不同。这是 Jackson 生成的 XML 与 JAXB 生成的 XML 不兼容的主要方式。当然,可以使用 JacksonXmlElementWrapper 注释为一个字段或全局 XmlMapper 上的 setDefaultUseWrapper 配置设置来配置行为。

Jackson 也不支持使用特定的 XML 模式。它是为首先编写 Java Bean 而设计的,而不是从预先存在的模式中生成 Java 代码。请注意,这可以通过使用 JAXB 注释支持并使用标准 xjc 工具生成 bean 在一定程度上解决。

同样,它也不支持一些更高级的 XML 工具——例如 XPath 或 XSLT。如果我们需要这种级别的支持,那么我们应该改用功能更全面的 XML 解决方案。

概括:

如果您正在寻找一种成熟、灵活的方式来支持和使用 JSON 和 XML 来处理相同的数据,那么 Jackson XML 模块是一个可以利用的绝佳库。它不仅是一种独立运行的可靠方式,而且还具有额外的好处,即能够为 XML 和 JSON 重用相同的配置。

通常,这必须使用具有完全独立配置的两个不同库来处理。

最后,除了灵活性和易用性之外,Jackson 团队历来都非常重视性能。鉴于数据的编组和解组是大多数 Web 应用程序的很大一部分,选择正确的库来处理所有这些工作至关重要。再加上 Retrace 等性能监控工具,您可以充分利用您的应用程序。

参考资料:https ://stackify.com/java-xml-jackson/

于 2021-11-24T05:00:30.170 回答