3

オプションの属性が設定されている場合、別の属性が突然必須になるようにします。また、これは、前の属性が設定されている場合にのみ、ラダーのオプション属性を設定できることを意味します。

つまり、

お名前必須

status はオプションですが、設定する場合は国も指定する必要があります。

国は、ステータスが指定されている場合にのみ設定されます。

<field name="myField" status="citizen" country="England"/>

有効な xml タグは、status と country が null (したがって非整列化されていない) の場合もあります。

<field name="myField" />

オプションのフィールドを独自のxmlタグに入れると、おそらく簡単になりますか? 多分このようなもの:

<field name="myField">
     <option status="citizen" country="England"/>
</field>

最初の方法は可能でしょうか?

4

1 に答える 1

2

イベントを使用beforeMarshalして、次のことを行うことができます。

分野

beforeMarshalドメイン クラスにメソッドを配置したくない場合は、を実装しMarshaller.Listenerて設定することができます ( http://docs.oracle.com/javase/6/docs/api/javax/xml/bind/MarshallerMarshallerを参照)。 .Listener.html )。

package forum13918891;

import javax.xml.bind.Marshaller;
import javax.xml.bind.annotation.*;

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

    @XmlAttribute
    String name;

    @XmlAttribute
    String status;

    @XmlAttribute
    String country;

    private void beforeMarshal(Marshaller marshaller) {
        if(country != null && status == null) {
            throw new RuntimeException("country was set but status was not");
        }
    }

}

デモ

以下は、すべてが機能することを証明するデモ コードです。

package forum13918891;

import javax.xml.bind.*;

public class Demo {

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

        Field field = new Field();
        field.name = "myField";
        marshaller.marshal(field, System.out);

        field.status = "citizen";
        field.country = "England";
        marshaller.marshal(field, System.out);

        field.status = null;
        marshaller.marshal(field, System.out);
    }

}

出力

以下は、デモ コードを実行した結果の出力です。

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<field name="myField"/>
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<field name="myField" status="citizen" country="England"/>
Exception in thread "main" java.lang.IllegalStateException: java.lang.reflect.InvocationTargetException
    at com.sun.xml.bind.v2.runtime.XMLSerializer.fireMarshalEvent(XMLSerializer.java:758)
    at com.sun.xml.bind.v2.runtime.XMLSerializer.fireBeforeMarshalEvents(XMLSerializer.java:743)
    at com.sun.xml.bind.v2.runtime.XMLSerializer.childAsRoot(XMLSerializer.java:491)
    at com.sun.xml.bind.v2.runtime.MarshallerImpl.write(MarshallerImpl.java:315)
    at com.sun.xml.bind.v2.runtime.MarshallerImpl.marshal(MarshallerImpl.java:244)
    at javax.xml.bind.helpers.AbstractMarshallerImpl.marshal(AbstractMarshallerImpl.java:75)
    at forum13918891.Demo.main(Demo.java:21)
Caused by: java.lang.reflect.InvocationTargetException
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at com.sun.xml.bind.v2.runtime.XMLSerializer.fireMarshalEvent(XMLSerializer.java:755)
    ... 6 more
Caused by: java.lang.RuntimeException: country was set but status was not
    at forum13918891.Field.beforeMarshal(Field.java:21)
    ... 11 more
于 2012-12-21T19:55:24.890 に答える