编组XMLGregorianCalendar时(奇怪)JaxB-Behavior

时间:2014-09-10 15:15:23

标签: java jaxb

主要班级:

public class CheckJaxBBehavior
{

    private String xml = "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?><Date day=\"---10+02:00\" month=\"--09--+02:00\" year=\"2014+02:00\"/>";

    public DateType unmarshal() throws Exception
    {

        ByteArrayInputStream input = new ByteArrayInputStream(xml.getBytes());

        JAXBContext jaxbContext = JAXBContext.newInstance(DateType.class);

        Unmarshaller jaxbUnmarshaller = jaxbContext.createUnmarshaller();
        DateType date = (DateType) jaxbUnmarshaller.unmarshal(input);

        return date;

    }

    private static XMLGregorianCalendar createXMLGregorianDate(Date date) throws Exception
    {
        GregorianCalendar gregorianCalendar = new GregorianCalendar();
        gregorianCalendar.setTime(date);

        XMLGregorianCalendar xmlGregorianCalendar = DatatypeFactory.newInstance().newXMLGregorianCalendar(gregorianCalendar);

        return xmlGregorianCalendar;
    }

    private void marshalAndPrint(DateType dateType) throws Exception
    {
        JAXBContext jaxbContext = JAXBContext.newInstance(DateType.class);
        Marshaller jaxbMarshaller = jaxbContext.createMarshaller();

        jaxbMarshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);

        StringWriter stringWriter = new StringWriter();

        jaxbMarshaller.marshal(dateType, stringWriter);

        System.out.println(stringWriter);
    }

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

        CheckJaxBBehavior checkIt = new CheckJaxBBehavior();

        DateType dateType = checkIt.unmarshal();

        System.out.println("Day: " + dateType.getDay());
        System.out.println("Month: " + dateType.getMonth());
        System.out.println("Year: " + dateType.getYear());

        XMLGregorianCalendar xmlGregorianCalendar = createXMLGregorianDate(new Date());

        System.out.println(xmlGregorianCalendar.toXMLFormat());

        DateType dateTypeToMarshal = new DateType();
        dateTypeToMarshal.setDay(xmlGregorianCalendar);
        dateTypeToMarshal.setMonth(xmlGregorianCalendar);
        dateTypeToMarshal.setYear(xmlGregorianCalendar);

        checkIt.marshalAndPrint(dateTypeToMarshal);

    }

}

数据类:

@XmlRootElement(name="Date")
@XmlAccessorType(XmlAccessType.FIELD)
public class DateType
{

    @XmlAttribute(name = "day")
    @XmlSchemaType(name = "gDay")
    protected XMLGregorianCalendar day;
    @XmlAttribute(name = "month")
    @XmlSchemaType(name = "gMonth")
//  @XmlJavaTypeAdapter(value=GMonthAdapter.class)
    protected XMLGregorianCalendar month;
    @XmlAttribute(name = "year", required = true)
    @XmlSchemaType(name = "gYear")
    protected XMLGregorianCalendar year;

// getters and setters
}

输出:

Day: ---10+02:00
Month: null
Year: 2014+02:00
2014-09-10T17:05:01.768+02:00
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<Date day="---10+02:00" month="--09--+02:00" year="2014+02:00"/>

我的问题: 我正在使用jkd 1.7.67,这有点奇怪!输入字符串与输出字符串完全相同,但JaxB无法解组月份。我认为输出不正确,所以--09 + 2:00必须是正确的值。这是一个未知的错误还是我的代码有问题?我写了一个适配器来解决这个问题,但可能还有其他解决方案?

1 个答案:

答案 0 :(得分:0)

xs:gMonth类型的词汇表示是--MM,后面有一个可选的时区。

如果您使用

"... month=\"--09+02:00\" ... "

在输入String xml中,month won * t再为null:

Day: ---10+02:00
Month: --09+02:00
Year: 2014+02:00

但是编组在JAXB中出现错误,因为@month的值不正确。