java 使用 JAXB 编组 LocalDate

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/36156741/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 01:00:48  来源:igfitidea点击:

Marshalling LocalDate using JAXB

javaxmljaxb

提问by pwaring

I'm building a series of linked classes whose instances I want to be able to marshall to XML so I can save them to a file and read them in again later.

我正在构建一系列链接类,我希望能够将它们的实例编组为 XML,以便我可以将它们保存到文件中,并在以后再次读取它们。

At present I'm using the following code as a test case:

目前我使用以下代码作为测试用例:

import javax.xml.bind.annotation.*;

import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;

import java.time.LocalDate;

public class LocalDateExample
{
  @XmlRootElement
  private static class WrapperTest {
    public LocalDate startDate;
  }

  public static void main(String[] args) throws JAXBException
  {
    WrapperTest wt = new WrapperTest();
    LocalDate ld = LocalDate.of(2016, 3, 1);
    wt.startDate = ld;
    marshall(wt);
  }

  public static void marshall(Object jaxbObject) throws JAXBException
  {
    JAXBContext context = JAXBContext.newInstance(jaxbObject.getClass());
    Marshaller marshaller = context.createMarshaller();
    marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, Boolean.TRUE);
    marshaller.marshal(jaxbObject, System.out);
  }
}

The XML output is:

XML 输出是:

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

Is there a reason why the startDateelement is empty? I would like it to contain the string representation of the date (i.e. toString()). Do I need to write some code of my own in order to do this?

startDate元素为空是否有原因?我希望它包含日期的字符串表示(即toString())。我是否需要编写一些自己的代码才能做到这一点?

The output of java -versionis:

的输出java -version是:

openjdk version "1.8.0_66-internal"
OpenJDK Runtime Environment (build 1.8.0_66-internal-b17)
OpenJDK 64-Bit Server VM (build 25.66-b17, mixed mode)

回答by nyname00

You will have to create an XmlAdapterlike this:

你将不得不创建一个XmlAdapter这样的:

public class LocalDateAdapter extends XmlAdapter<String, LocalDate> {
    public LocalDate unmarshal(String v) throws Exception {
        return LocalDate.parse(v);
    }

    public String marshal(LocalDate v) throws Exception {
        return v.toString();
    }
}

And annotate your field using

并使用注释您的字段

 @XmlJavaTypeAdapter(value = LocalDateAdapter.class)

See also javax.xml.bind.annotation.adapters.XmlJavaTypeAdaptersif you want to define your adapters on a package level.

另请参阅javax.xml.bind.annotation.adapters.XmlJavaTypeAdapters是否要在包级别定义适配器。

回答by R. Gulbrandsen

http://blog.bdoughan.com/2011/05/jaxb-and-joda-time-dates-and-times.htmldescribes the hole setup.

http://blog.bdoughan.com/2011/05/jaxb-and-joda-time-dates-and-times.html描述了孔设置。

Joda-Time provides an alternative to the Date and Calendar classes currently provided in Java SE. Since they are provided in a separate library JAXB does not provide a default mapping for these classes.

Joda-Time 提供了 Java SE 中当前提供的 Date 和 Calendar 类的替代方案。由于它们是在单独的库中提供的,因此 JAXB 不为这些类提供默认映射。

To register the adapter for all files in a package. you can add package-info.java in the package you want to register it.

为包中的所有文件注册适配器。您可以在要注册的包中添加 package-info.java 。

@XmlJavaTypeAdapters({
    @XmlJavaTypeAdapter(type=LocalDate.class, 
        value=LocalDateAdapter.class),
})
package PACKAGE_NAME;

import java.time.LocalDate;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapters;

The adapter looks like:

适配器看起来像:

import javax.xml.bind.annotation.adapters.XmlAdapter;
import java.time.LocalDate;

public class LocalDateAdapter extends XmlAdapter<String, LocalDate>{

    public LocalDate unmarshal(String v) throws Exception {
        return LocalDate.parse(v);
    }

    public String marshal(LocalDate v) throws Exception {
        return v.toString();
    }

}