Defining package names for common XSD's with xjc and bindings

Xavi López picture Xavi López · May 24, 2012 · Viewed 16.3k times · Source

I'm trying to generate Java classes from several specific XSD's with xjc. Those schemas have some definitions in common, so they import a number of common XSD's. In particular, they can include from zero to all of the common XSD's.

I'd like to generate all classes from an specific XSD to a specific package, but keeping the generated classes for the common schemas in a common package, so they don't get repeated for each specific schema in the source tree.

I've learnt that custom bindings can be used to specify packages on a per-schema basis, with for instance:

<jxb:bindings schemaLocation="common1.xsd" node="/xsd:schema">
    <jxb:schemaBindings>
        <jxb:package name="mypackage.commonclasses"/>
    </jxb:schemaBindings>
</jxb:bindings>

I've got the following structure:

schemas
| - common
| | - common1.xsd --> XSD with common types #1
| | - ...
| | - commonN.xsd --> XSD with common types #N
| | - commonBindings.xjb --> Defines package "mypackage.commons" for common*.xsd
| - specific1
| | - specific1.xsd --> Includes ../common/common{1-N}.xsd
| | - specific1.xjb --> Defines package "mypackage.specific1" for specific1.xsd
| - specificN
| | - specificN.xsd --> Includes only ../common/common1.xsd
| | - specificN.xjb --> Defines package "mypackage.specificN" for specificN.xsd

It all works fine with:

xjc -b schemas/specific1
    -b schemas/common 
    schemas/specific1/specific1.xsd

It generates the classes for specific1.xsd in mypackage.specific1 and the common classes in mypackage.commons. But when I try to generate the classes for specificN, xjc throws the following error:

[ERROR] "file:/drive/dir/schemas/common/common1.xsd" is not a part of
 this compilation. Is this a mistake for "/drive/dir/schemas/common/commonBindings.xjb"?
  line 2 of file:/drive/dir/schemas/common/commonBindings.xjb

I get this error repeated for every common XSD not imported in any specific xsd.

Is there any way I can make xjc ignore the bindings in commonBindings.xjb that aren't used in the XSD I'm generating the classes for?

Or, am I aiming in the wrong direction by using this approach, and should be, for instance, using annotations in the specific xsd? I'd like to avoid modifying the schemas if possible.

Answer

Petru Gardea picture Petru Gardea · May 24, 2012

I think that what you need is to use the JAXB episode. See this SO post, take a look at the answer @BlaiseDoughan provided.

In your case, run xjc first, using your custom binding file for package name customization, against all the XSDs that are common, to generate an episode file and your common Java classes.

Then use xjc again, with the other XSDs you want, by referencing the episode file from the first run.