JAXB:为两个共享一个共同XSD的XSD生成类

时间:2011-06-08 22:22:33

标签: java xsd jaxb

我有2个服务XSD文件AService.xsd和BService.xsd,每个文件都有不同的targetNamespace。这两个都使用一个名为common.xsd的通用XSD。我使用JAXB Maven插件生成类。这是怎么回事,

<execution>
    <id>generate-package</id>
    <goals>
        <goal>generate</goal>
    </goals>
    <configuration>
        <extension>true</extension>
        <schemaIncludes>
            <include>schema/Aservice.xsd</include>
            <include>schema/Bservice.xsd</include>                             
        </schemaIncludes>
        <bindingIncludes>                                   
            <include>schema/*.xjb</include>
        </bindingIncludes>
        <generatePackage>com.schema</generatePackage>
        <generateDirectory>src/main/java</generateDirectory>
    </configuration>
</execution>

当我尝试运行时,我收到以下错误。 ValidationType在common.xsd

中定义
org.xml.sax.SAXParseException: A class/interface with the same name "com.schema.ValidationType" is already in use. Use a class customization to resolve this conflict.
..........
org.xml.sax.SAXParseException: (Relevant to above error) another "ValidationType" is generated from here.
......
com.sun.istack.SAXParseException2: Two declarations cause a collision in the ObjectFactory class.

如果我在2个不同的执行中运行2个服务xsds,生成2个不同的包,我在2个不同的包中得到相同的ValidationType类。

有关如何使JAXB识别共享模式的任何想法?

2 个答案:

答案 0 :(得分:6)

你正面临着一种所谓的“变色龙图式”,这被认为是一种不好的做法。不幸的是,由于JAXB的性质,没有好的解决方案。 JAXB注释将bean属性绑定到特定名称空间中的XML元素和属性(在模式编译时确定)。因此,一旦编译了模式,就没有官方的好方法来更改属性绑定到的元素和属性的名称空间。

然而,这正是您想要通过“变色龙”模式实现的目标。从“common.xsd”派生的类应该以某种方式神奇地映射到命名空间A(如果在A类中使用)和命名空间B(如果在B类中使用)。我可以想象这种魔力,但在现实生活中从未见过。

由于你基本上希望A / common和B / common是“相同的东西”,解决它的方法之一是在两次执行中生成A和B(两者都有共同的)并使公共类实现一个某些“常见”界面。然后你的软件可以在同一个方面处理A / common和B / common,而不管这些实际上是来自不同包的类。

<强>更新

从评论中我看到你没有变色龙模式,只是一个正常的导入。这很简单,只需分别编译common,A和B.有关maven-jaxb2-plugin的信息,请参阅Separate schema compilation

答案 1 :(得分:5)

I customized the packages as described here。因此common.xsd进入com.common.schema并由AService.xsdBService.xsd共享,它们本身位于不同的包中,因为它们位于不同的名称空间中。

从maven配置中移除generatePackage,看起来像这样,

<execution>
    <id>generate-package</id>
    <goals>
        <goal>generate</goal>
    </goals>
    <configuration>
        <extension>true</extension>
        <schemaIncludes>
            <include>schema/Aservice.xsd</include>
            <include>schema/Bservice.xsd</include>                            
        </schemaIncludes>
        <bindingIncludes>
            <include>schema/*.xjb</include>
        </bindingIncludes>                                
        <generateDirectory>src/main/java</generateDirectory>
    </configuration>
</execution>