12

xjc を使用して XML スキーマから Java オブジェクトを生成しています。IDREF を使用して、ドキュメント内で同じ要素を複数回参照したいと考えています。また、IDREF によって参照されるオブジェクトを特定の型に制限したいと考えています。私はこれをスキーマ検証の目的で行いたいと考えていますが、Java コードでは、参照されたオブジェクトが Object 型ではなく特定の型として返されるようにもします。たとえば、スキーマで次のことを記述したいとします。

<teams>
  <team id="team1">
    <coach>coachz</coach>
    <player>homestar</player>
    <player>marzipan</player>
    <player>strongsad</player>
    <player>strongbad</player>
  </team>

  <team id="team2">
    <coach>bubs</coach>
    <player>homesar</player>
    <player>thecheat</player>
    <player>poopsmith</player>
    <player>bubs</player>
  </team>

  <team id="allstars">
    <coach>poopsmith</coach>
    <player>coachz</player>
    <player>bubs</player>
    <player>kingoftown</player>
    <player>strongbad</player>
  </team>
</teams>

<people>
 <person id="coachz">Coach Z</person>
 <person id="homesar">Homesar</person>
 <person id="homestar">Homestar</person>
 <person id="strongbad">Strong Bad</person>
 <person id="strongsad">Strong Sad</person>
 <person id="marzipan">Marzipan</person>
 <person id="bubs">Bubs</person>
 <person id="kingoftown">King of Town</person>
 <person id="poopsmith">The Poopsmith</person>
 <person id="thecheat">The Cheat</person>
</people>

player次のように定義できます。

<xs:element name="player" type="xs:IDREF" maxOccurs="unbounded"/>

しかし、Java コードでは、プレーヤーを取得しようとすると、型オブジェクトとして返され、人にキャストする必要があります。その時点で、誰かが Team オブジェクトを誤って参照した場合、検証時に発見された可能性のある対処すべきエラーがあります。私はこのようなものを指定したい:

<xs:element name="player" type="xs:IDREF"reftype="person"maxOccurs="unbounded" />

しかし、私が知る限り、ここで不自然な属性 'reftype' を使用して行ったように、型を指定する方法はありません。これは IDREF を使用して実行できますか? そうでない場合、別の方法はありますか?

4

2 に答える 2

13

要素baseTypeにバインディングを適用するだけです。player何かのようなもの:

<jaxb:bindings node="xsd:element[@name='player']">
    <jaxb:property>
        <jaxb:baseType name="....Person"/>
    </jaxb:property>
</jaxb:bindings>

スキーマの正しいバインディングの場所を把握する必要がある場合があります。

私のコードの例:

スキーマ:

<xsd:complexType name="HJIII-53-A">
    <xsd:sequence>
        <xsd:element name="b" type="xsd:IDREF"/>
        <xsd:element name="b1" type="test:HJIII-53-B"/>
        <xsd:element name="c" type="xsd:IDREFS"/>
        <xsd:element name="c1" type="test:HJIII-53-C" minOccurs="0" maxOccurs="unbounded"/>
    </xsd:sequence>
</xsd:complexType>

バインディング:

<jaxb:bindings schemaLocation="schema.xsd" node="/xsd:schema">
    <jaxb:globalBindings localScoping="toplevel">
        <jaxb:serializable/>
    </jaxb:globalBindings>
    <jaxb:bindings node="xsd:complexType[@name='HJIII-53-A']//xsd:element[@name='b']">
        <jaxb:property>
            <jaxb:baseType name="org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53B"/>
        </jaxb:property>
    </jaxb:bindings>
    <jaxb:bindings node="xsd:complexType[@name='HJIII-53-A']//xsd:element[@name='c']">
        <jaxb:property>
            <jaxb:baseType name="org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53C"/>
        </jaxb:property>
    </jaxb:bindings>
</jaxb:bindings>

生成されたコード:

@XmlElement(required = true, type = Object.class)
@XmlIDREF
@XmlSchemaType(name = "IDREF")
protected org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53B b;
@XmlElement(required = true)
protected org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53B b1;
@XmlList
@XmlElement(required = true, type = Object.class)
@XmlIDREF
protected List<org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53C> c;
protected List<org.jvnet.hyperjaxb3.ejb.tests.issuesjpa2.HJIII53C> c1;

参照: https://svn.java.net/svn/hj3~svn/trunk/ejb/tests/issues-jpa2/src/main/resources/

于 2013-04-29T22:28:57.873 に答える
11

lexicoreの答えは、私が必要とするものを与えてくれました(そして、私の答えよりも彼の答えに投票することをお勧めします)。ただし、別のバインディング ファイルの代わりにインライン アノテーションを使用しています。これは、私の Homestar の例を使用して、インライン注釈でどのように見えるかです:

<xs:element name="player" type="xs:IDREF" maxoccurs="unbounded">
  <xs:annotation>
    <xs:appinfo>
      <jaxb:property>
        <jaxb:baseType name="Person"/>
      </jaxb:property>
    </xs:appinfo>
  </xs:annotation>
</xs:element>
于 2013-04-29T23:20:51.690 に答える