4

我正在使用 JAXB 来编组和解组 Java 类。

这是我正在寻找的 xml:

<tag name="example" attribute1="enumValue"/>

如果 attribute1 设置为默认值,我根本不希望打印该属性,所以它看起来像这样:

<tag name="example"/>

有没有办法做到这一点?

现在我有一个 getter/setter 对,如下所示:

@XmlAttribute(name="attribute1")
public EnumExample getEnumExample() {
    return this.enumExample;
}

public void setEnumExample(final EnumExample enumExample) {
    this.enumExample = enumExample;
}
4

3 回答 3

5

您可以将 anXmlAdapter用于此用例:

XmlAdapter (Attribute1Adapter)

您可以利用 JAXB 不会编组 null 属性值这一事实,并使用 anXmlAdapter来调整要编组为 XML 的值。

import javax.xml.bind.annotation.adapters.XmlAdapter;
import forum16972549.Tag.Foo;

public class Attribute1Adapter extends XmlAdapter<Tag.Foo, Tag.Foo>{

    @Override
    public Foo unmarshal(Foo v) throws Exception {
        return v;
    }

    @Override
    public Foo marshal(Foo v) throws Exception {
        if(v == Foo.A) {
            return null;
        }
        return v;
    }

}

领域模型(标签)

@XmlJavaTypeAdapter注解用于XmlAdapter关联.

import javax.xml.bind.annotation.*;
import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;

@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class Tag {

    enum Foo {A, B};

    @XmlAttribute
    @XmlJavaTypeAdapter(Attribute1Adapter.class)
    private Foo attribute1;

    public Foo getAttribute1() {
        return attribute1;
    }

    public void setAttribute1(Foo attribute1) {
        this.attribute1 = attribute1;
    }

}

演示

下面是一些演示代码,您可以使用它来证明一切正常。

import javax.xml.bind.*;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(Tag.class);
        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);

        Tag tag = new Tag();
        tag.setAttribute1(Tag.Foo.A);
        System.out.println(tag.getAttribute1());
        marshaller.marshal(tag, System.out);

        tag.setAttribute1(Tag.Foo.B);
        System.out.println(tag.getAttribute1());
        marshaller.marshal(tag, System.out);
    }

}

输出

下面是运行演示代码的输出。

A
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<tag/>
B
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<tag attribute1="B"/>
于 2013-06-07T15:59:04.830 回答
2

标签

您可以利用 JAXB 不会编组空属性值这一事实,并向您的属性添加一些逻辑,然后使用 JAXB 映射到该字段。

import javax.xml.bind.annotation.*;

@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
public class Tag {

    private static Foo ATTRIBUTE1_DEFAULT = Foo.A;

    enum Foo {A, B};

    @XmlAttribute
    private Foo attribute1;

    public Foo getAttribute1() {
        if(null == attribute1) {
            return ATTRIBUTE1_DEFAULT;
        }
        return attribute1;
    }

    public void setAttribute1(Foo attribute1) {
        if(ATTRIBUTE1_DEFAULT == attribute1) {
            this.attribute1 = null;
        } else {
            this.attribute1 = attribute1;
        }
    }

}

演示

import javax.xml.bind.*;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(Tag.class);
        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);

        Tag tag = new Tag();
        tag.setAttribute1(Tag.Foo.A);
        System.out.println(tag.getAttribute1());
        marshaller.marshal(tag, System.out);

        tag.setAttribute1(Tag.Foo.B);
        System.out.println(tag.getAttribute1());
        marshaller.marshal(tag, System.out);
    }

}

输出

A
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<tag/>
B
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<tag attribute1="B"/>
于 2013-06-07T13:25:44.660 回答
1

AFAIK,这不可能直接使用 JAXB 注释。但是像这样使用required=true ,

@XmlAttribute(required=true name="attribute1") 
private String enumExample;

我们可以做一个解决方法。在对该属性调用 setter 之前,我们可以检查将要设置的值是否为默认值。如果是,我们可以将 null 传递给该 setter,并且该属性在编组后将不可见。

于 2013-06-07T12:20:51.813 回答