2010-03-09 44 views
18

Estoy usando jaxb para generar clases java a partir de un esquema xml. El esquema importa XMLSchema.xsd y su contenido se utiliza como un elemento en el documento.Generación de clases Java a partir de XMLSchema.xsd usando JAXB

Si elimino la importación y la referencia a "xsd: schema" respectivamente, entonces el compilador vinculante genera correctamente las clases. Si no lo hago, produciría los siguientes errores, ¡que son lo mismo si intentara generar clases de Java solo desde XMLSchema.xsd!

> C:\Users\me>"%JAXB%/xjc" -extension -d tmp/uisocketdesc -p uis.jaxb uisocketdesc.xsd -b xml_binding_test.xml -b xml_binding_test_2.xml 
-b xml_binding_test_3.xml 
parsing a schema... 
compiling a schema... 

> [ERROR] A class/interface with the same name "uis.jaxb.ComplexType" is already in use. Use a class customization to resolve this conflict. 
line 612 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "ComplexType" is generated from here. 
line 440 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] A class/interface with the same name "uis.jaxb.Attribute" is already in use. Use a class customization to resolve this conflict. 
line 364 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "Attribute" is generated from here. 
line 1020 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] A class/interface with the same name "uis.jaxb.SimpleType" is already in use. Use a class customization to resolve this conflict. 
line 2278 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "SimpleType" is generated from here. 
line 2222 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] A class/interface with the same name "uis.jaxb.Group" is already in use. Use a class customization to resolve this conflict. 
line 930 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "Group" is generated from here. 
line 727 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] A class/interface with the same name "uis.jaxb.AttributeGroup" is already in use. Use a class customization to resolve this conflict. 
line 1062 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "AttributeGroup" is generated from here. 
line 1026 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] A class/interface with the same name "uis.jaxb.Element" is already in use. Use a class customization to resolve this conflict. 
line 721 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Relevant to above error) another "Element" is generated from here. 
line 647 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 1020 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 364 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 2278 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 2222 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 930 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 727 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 440 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 612 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 1026 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 1062 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] Two declarations cause a collision in the ObjectFactory class. 
line 647 of "http://www.w3.org/2001/XMLSchema.xsd" 

> [ERROR] (Related to above error) This is the other declaration. 
line 721 of "http://www.w3.org/2001/XMLSchema.xsd" 

Failed to produce code. 

Respuesta

4

Parece que su esquema está roto. XJC es extremadamente exigente con estas cosas, y puede fallar en cosas que otras herramientas dejan pasar.

En lugar de seguir los errores de XJC, me resulta más fácil ejecutar el esquema primero a través del AlphaWorks Schema Quality Checker. Esto proporciona un resultado agradable y legible para el ser humano (bueno, el desarrollador puede leer, de todos modos) de lo que está mal. Si supera ese problema, tendrás muchas más posibilidades de que también lo haga XJC.

+1

Gracias por la sugerencia de SQC aunque no reconoce los problemas mencionados anteriormente. – david

+0

El enlace parece estar roto. ¿Puedes por favor suministrar uno nuevo? –

+0

He usado https://www.wsdl-analyzer.com –

-1

Puede usar xjc que viene con JDK1.6. También puede probar XML to Java, consulte this article.

+0

El OP ya está usando xjc –

9

Puede lograr que JAXB genere código para XML Schema xsd mediante (al menos) dos métodos. El problema que está experimentando se debe al hecho de que algunos tipos de esquema y elementos comparten los mismos nombres.


La primera opción evita conflictos de nombres mediante la aplicación de una o más transformaciones de nombres XML para los nombres de las clases generadas. Aquí está un ejemplo de un archivo de enlace externo que hacer esto:

<jxb:bindings version="2.1" 
       xmlns:jxb="http://java.sun.com/xml/ns/jaxb" 
       xmlns:xs="http://www.w3.org/2001/XMLSchema" 
       xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc" 
       jxb:extensionBindingPrefixes="xjc"> 
    <jxb:globalBindings> 
    <xjc:simple/> 
    </jxb:globalBindings> 
    <jxb:bindings schemaLocation="XMLSchema.xsd"> 
    <jxb:schemaBindings> 
     <jxb:nameXmlTransform> 
     <jxb:elementName suffix="Element"/> 
     </jxb:nameXmlTransform> 
    </jxb:schemaBindings> 
    </jxb:bindings> 
</jxb:bindings> 

Este enfoque funciona (se podría aplicar otras transformadas que funcionarían igual de bien, pero he visto esta técnica una y otra vez en la documentación) pero creo que produce resultados desagradables. Por ejemplo, hay una clase generada en este caso llamada ElementElement.


El segundo enfoque utiliza personalización de clase como lo sugiere la salida de xjc. De hecho, todas menos una de las clases de problemas tiene la propiedad abstract="true" establecida en el tipo de esquema correspondiente. Por lo tanto, tiene sentido para mí anteponer el nombre de clase con "Resumen", es decir, AbstractElement. La clase Attribute restante no es abstracta, pero la xs:element llamada attribute genera una clase de extensión con un cuerpo vacío. Por lo tanto, lo llamé BaseAttribute. Aquí está la definición de unión externa utilicé:

<jxb:bindings version="2.1" 
       xmlns:jxb="http://java.sun.com/xml/ns/jaxb" 
       xmlns:xs="http://www.w3.org/2001/XMLSchema" 
       xmlns:xjc="http://java.sun.com/xml/ns/jaxb/xjc" 
       jxb:extensionBindingPrefixes="xjc"> 
    <jxb:globalBindings> 
    <xjc:simple/> 
    </jxb:globalBindings> 
    <jxb:bindings schemaLocation="XMLSchema.xsd"> 
    <jxb:schemaBindings> 
     <jxb:package name="org.w3.xmlschema"/> 
    </jxb:schemaBindings> 
    <jxb:bindings node="//xs:complexType[@name='complexType']"> 
     <jxb:class name="AbstractComplexType"/> 
    </jxb:bindings> 
    <jxb:bindings node="//xs:complexType[@name='group']"> 
     <jxb:class name="AbstractGroup"/> 
    </jxb:bindings> 
    <jxb:bindings node="//xs:complexType[@name='attributeGroup']"> 
     <jxb:class name="AbstractAttributeGroup"/> 
    </jxb:bindings> 
    <jxb:bindings node="//xs:complexType[@name='simpleType']"> 
     <jxb:class name="AbstractSimpleType"/> 
    </jxb:bindings> 
    <jxb:bindings node="//xs:complexType[@name='element']"> 
     <jxb:class name="AbstractElement"/> 
    </jxb:bindings> 
    <jxb:bindings node="//xs:complexType[@name='attribute']"> 
     <jxb:class name="BaseAttribute"/> 
    </jxb:bindings> 
    </jxb:bindings> 
</jxb:bindings> 

Esto da nombres de clase generados más claras en mi opinión, y con éxito compila el esquema.


También recomendaría el uso de compilación separada para XMLSchema.xsd y mantenerlo en un archivo JAR para su uso posterior en caso de que este tema volvió a surgir durante la compilación de otro esquema. Las respuestas al this question describen cómo.

+0

frente a un problema similar. Pero tengo alrededor de 50 de estas variables, ¿alguna solución alternativa? – wib

14

Al luchar contra este tipo de cosas también, para mí es cuestión de mayúsculas y minúsculas y el mismo nombre para el elemento y la emisión de atributos (a través de la herencia a veces).Para el segundo problema que estoy usando archivo de enlace externo que contiene algo como esto:

<jaxb:bindings node="//xs:complexType[@name='AbstractGriddedSurfaceType']//xs:attribute[@name='rows']"> 
    <jaxb:property name="rowCount"/> 
</jaxb:bindings> 

Por cuestiones mayúsculas y minúsculas puede utilizar el argumento xjc -XautoNameResolution, versión experta es <args><arg>-B-XautoNameResolution</arg></args>, pero esto no funciona para los elementos de contenedor, por lo que para estos debe escribir personalizaciones de jaxb como se mencionó anteriormente, ... y si tiene mala suerte como yo :) puede que necesite usar una copia local de un archivo xsd y corregir duplicaciones manualmente.

Editar encontrado otra solución para el problema de mayúsculas y minúsculas, donde el cambio de nombre del nombre del elemento no es suficiente:

<jaxb:bindings node=".//xs:element[@name='imageDatum'][@type='gml:ImageDatumPropertyType']"> 
    <jaxb:property name="imageDatumInst"/> 
    <jaxb:factoryMethod name="imageDatumInst" /> 
</jaxb:bindings> 

Buena suerte, espero que esto ayude.

+7

-XautoNameResolution me lo resolvió :-D –

2

Tuve el mismo problema al generar objetos desde .wsdl usando cxf. La resolución para mí es usar -autoNameResolution como sugiere un mensaje de error. configuración de Maven:

  <wsdlOption> 
          <wsdl>${basedir}/test.wsdl</wsdl> 
          <extraargs> 
           <extraarg>-b</extraarg>  
          <extraarg>http://www.w3.org/2001/XMLSchema.xsd</extraarg> 
           <extraarg>-autoNameResolution</extraarg> 
          </extraargs> 
          <packagenames> 
           <packagename>test.wsdl</packagename> 
          </packagenames> 
         </wsdlOption> 
0

me trató siguiente y funcionó para mí:

<jxb:bindings schemaLocation="ClaimActivity-ACORD.xsd"> 
    <jxb:schemaBindings> 
     <jxb:package name="x.x.x.x" /> 
    </jxb:schemaBindings> 
    <jxb:bindings node="//xsd:complexType[@name='ConstructionType']"> 
     <jxb:class name="AbstractConstructionType" /> 
    </jxb:bindings> 
    <jxb:bindings node="//xsd:complexType[@name='ItemDefinitionType']"> 
     <jxb:class name="AbstractItemDefinitionType" /> 
    </jxb:bindings> 
    <jxb:bindings node="//xsd:complexType[@name='LocationType']"> 
     <jxb:class name="AbstractLocationType" /> 
    </jxb:bindings> 
    <jxb:bindings node="//xsd:complexType[@name='TaxFeeType']"> 
     <jxb:class name="AbstractTaxFeeType" /> 
    </jxb:bindings> 
    <jxb:bindings node="//xsd:complexType[@name='DeductibleType']"> 
     <jxb:class name="AbstractDeductibleType" /> 
    </jxb:bindings> 
    <jxb:bindings node="//xsd:complexType[@name='RegistrationType']"> 
     <jxb:class name="AbstractRegistrationType" /> 
    </jxb:bindings> 
</jxb:bindings> 

1

Otra opción sería la de eliminar la opción -p por lo que las clases se generan en diferentes paquetes

Cuestiones relacionadas