我是XSD设计和JAXB的新手。我设法如下创建我的XSD:

<xsd:element name="policy" >
<xsd:complexType>
    <xsd:sequence>
        <xsd:element name="actor-def" type="tns:actor-def"/>
        <xsd:element name="actor-system-def" type="tns:actor-system-def"/>
        </xsd:sequence>
</xsd:complexType>
</xsd:element>

<xsd:complexType name="actor-def">
    <xsd:sequence>
        <xsd:element name="actor-system" type="tns:actor-system-type"/>
    </xsd:sequence>
    <xsd:attribute name="name" type="xsd:ID" use="required" />
</xsd:complexType>
<xsd:complexType name="actor-system-type">
    <xsd:attribute name="name" type="xsd:IDREF" use="required" />
</xsd:complexType>

<xsd:complexType name="actor-system-def">
    <xsd:attribute name="name" type="xsd:ID" use="required" />
    <xsd:attribute name="url" type="xsd:anyURI" use="required" />
</xsd:complexType>


基本上,我有一个“策略”的根元素,该元素允许定义几个“ actor-def”和“ actor-system-def”。每个“ actor-def”将属于一个通过使用ID和IDREF实现的“ actor-system-def”。

为了与此一起使用JAXB,我使用Eclipse的Schema的JAXB类自动创建了所有必需的类。它会基于XSD文件自动创建以下类:

Policy.java

ActorDef.java

ActorSystemDef.java

ActorSystemType.java

除了ActorDef.java文件以及其中的actorSystem变量的类型(使用XSD文件中的IDREF定义)之外,其他所有内容看起来都很好。基本上,ActorDef.java文件具有以下内容:

@XmlElement(name = "actor-system", required = true)
protected ActorSystemType actorSystem;
public ActorSystemType getActorSystem() {
    return actorSystem;
}


问题在于,由于从ActorDef.getActorSystem()返回的类型是ActorSystemType类型,因此它是对错误对象的引用。我想要的是对相关ActorSystemDef的引用,以便我可以对此调用getName()方法以获取ActorSystemDef的名称(如下所示)

JAXBContext myJAXBContext = JAXBContext.newInstance("spec_jaxb");
Unmarshaller myUnmarshaller = myJAXBContext.createUnmarshaller();
Policy myPolicy = (Policy) myUnmarshaller.unmarshal(new  File("src/main/java/spec/private_policy.xml"));

List<ActorDef> actorList = myPolicy.getActorDef();
for (ActorDef actor : actorList) {
    System.out.println(actor.getActorSystem().getName());
}


我可以通过手动修改JAXB工具自动创建的类来使代码正常工作。我将ActorDef.java中actorSystem变量的类型更改为ActorSystemDef,如下所示:

protected ActorSystemDef actorSystem;
public ActorSystemDef getActorSystem() {
    return actorSystem;
}


这样就解决了问题,并且代码可以正常工作,但是我想学习如何更正XSD文件,以便JAXB类创建工具可以自动解决上述问题。我认为我在XSD定义中犯了一个错误,导致了这一点。我经常修改XSD文件,不能每次都手动进行所有这些更改。

最佳答案

我尝试了您的模式,并得到了ActorDef类的,与您相同:

@XmlElement(name = "actor-system", required = true)
protected ActorSystemType actorSystem;

public ActorSystemType getActorSystem() { return actorSystem; }
public void setActorSystem(ActorSystemType value) { this.actorSystem = value; }


但是后来我删除了架构的这一部分(似乎您没有在使用它-为什么在那儿?):

<xsd:complexType name="actor-system-type">
    <xsd:attribute name="name" type="xsd:IDREF" use="required" />
</xsd:complexType>


然后将actor-system元素的type更改为:

<xsd:element name="actor-system" type="tns:actor-system-type"/>


至:

<xsd:element name="actor-system" type="tns:actor-system-def"/>


因此,结束模式变为:

<xsd:element name="policy">
<xsd:complexType>
    <xsd:sequence>
        <xsd:element name="actor-def" type="tns:actor-def"/>
        <xsd:element name="actor-system-def" type="tns:actor-system-def"/>
    </xsd:sequence>
</xsd:complexType>
</xsd:element>

<xsd:complexType name="actor-def">
    <xsd:sequence>
        <xsd:element name="actor-system" type="tns:actor-system-def"/>
    </xsd:sequence>
    <xsd:attribute name="name" type="xsd:ID" use="required" />
</xsd:complexType>

<xsd:complexType name="actor-system-def">
    <xsd:attribute name="name" type="xsd:ID" use="required" />
    <xsd:attribute name="url" type="xsd:anyURI" use="required" />
</xsd:complexType>


然后,使用该代码生成类,并为ActorDef获得以下代码:

@XmlElement(name = "actor-system", required = true)
protected ActorSystemDef actorSystem;

public ActorSystemDef getActorSystem() { return actorSystem; }
public void setActorSystem(ActorSystemDef value) { this.actorSystem = value; }


在我看来,这就是您最初的期望,对吧?

同样,应该不再生成ActorSystemType.java

10-05 22:59
查看更多