Offline Resolution of XSDs Using Maven JAXB
Learn more about this offline resolution for using the JAXB Maven Plugin.
Join the DZone community and get the full member experience.
Join For FreeSometimes, we encounter scenarios where an application is placed on a server that is restricted to downloading an XSD from the target namespace.
This article demonstrates how to resolve the XSD and manipulate a JAR file to create Java beans using a Maven plugin.
Here, as an example, we will be using the XML Encryption library. Additionally, some of the encrypted contents on the child library will be fetched from its parent library.
Implementation
Here is the simple project structure of the parent library, which will be used in other projects as well. The XML Encryption core library is being resolved in this project. We have downloaded the XSD from the official site of the W3 Organization. Some of the important files are described below:
imported-bindings.xsd:
These are used to globally expose the logical prefix of the whole XSD. In all projects using this library, we will be using this prefix for denoting this XSD.
xenc-schema.xsd
This main file is downloaded from the W3 organization and will be used offline for resolving the schema.
catalog.cat
This file is present in the main root path of the project folder and will be used for REWRITE /PUBLIC rule. We will be using the file in this folder to denote public rules. The public rule will be exposed while building this Maven repository. This rule is to denote the Maven compiler while searching the Internet; for the website location, be sure to look inside the project itself.
All of the above files are important to keep in the project, as they form the preliminary layer of the project. Next, we will look at the main section in the pom where we will using jaxb-maven plugin to integrate all the above files together using some special sections in the plugin.
<plugin>
<groupId>org.jvnet.jaxb2.maven2</groupId>
<artifactId>maven-jaxb2-plugin</artifactId>
<version>0.8.3</version>
<executions>
<execution>
<goals>
<goal>generate</goal>
</goals>
<configuration>
<catalog>catalog.cat</catalog>
<generateDirectory>${project.basedir}/target/generated</generateDirectory>
<extension>true</extension>
</configuration>
</execution>
</executions>
<configuration>
<schemaIncludes>
<include>*.xsd</include>
</schemaIncludes>
<bindingDirectory>src/main/resources</bindingDirectory>
<bindingIncludes>
<include>imported-bindings.xjb</include>
</bindingIncludes>
<args>
<arg>-XtoString</arg>
<arg>-Xnamespace-prefix</arg>
</args>
<plugins>
<plugin>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-basics</artifactId>
<version>0.6.4</version>
</plugin>
</plugins>
</configuration>
<dependencies>
<dependency>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-namespace-prefix</artifactId>
<version>1.1</version>
</dependency>
</dependencies>
</plugin>
In the above code, we have added the path to the catalog file, schema binding file, and directories. After adding the proper commands inside the plugin, we will build the project using simple Maven install commands. Once the project is successful, all of the newly created Java classes will be present under a target/generated folder (Maven built this to be done using offline mode).
Now for the interesting part. We will be using this Maven-built library for all other projects. The following changes would be needed to incorporate the build in other projects.
In the actual XSD, using this library, there will be a section mentioned in the following snippet:
Here, the above URL can be used to download the root XSD from the Internet, resolving the same and building the jar. We will keep the same and make the following modification in the catalog file of this project folder.
Here, we will be using the REWRITE_SYSTEM rule to direct the path of the URL to the previously built library, and the same will be picked up while Maven builds the individual project.
In the pom.xml, we will add the dependencies of the root folder and plugin in the following format:
<plugin>
<groupId>org.jvnet.jaxb2.maven2</groupId>
<artifactId>maven-jaxb2-plugin</artifactId>
<version>0.13.0</version>
<executions>
<execution>
<goals>
<goal>generate</goal>
</goals>
<configuration>
<catalog>src/main/resources/cvc-solution-catalog.cat</catalog> <generateDirectory>${project.basedir}/target/generated</generateDirectory>
<extension>true</extension>
</configuration>
</execution>
</executions>
<configuration>
<episodes>
<episode>
<groupId>org.w3._2001._04.xmlenc</groupId>
<artifactId>xmlenc</artifactId>
</episode>
</episodes>
<args>
<arg>-Xequals</arg>
<arg>-XtoString</arg>
<arg>-Xwildcard</arg>
<arg>-Xnamespace-prefix</arg>
</args>
<plugins>
<plugin>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-basics</artifactId>
<version>0.6.4</version>
</plugin>
</plugins>
<strict>false</strict>
<schemaDirectory>src/main/resources</schemaDirectory>
<schemaIncludes>
<include>**/*.xsd</include>
</schemaIncludes>
<bindingDirectory>./</bindingDirectory>
<bindingIncludes>
<include>imported-bindings.xjb</include>
</bindingIncludes>
</configuration>
<dependencies>
<dependency>
<groupId>org.jvnet.jaxb2_commons</groupId>
<artifactId>jaxb2-namespace-prefix</artifactId>
<version>1.1</version>
</dependency>
</dependencies>
</plugin>
We are using the episode inside the plugin to avoid adding the already generated classes of the root folder inside the current directory.
Finally, we are done! With this structural hierarchy, we can keep all of the parent XSD built offline and use them as per our requirements in the project via the above orchestrations.
Conclusion
This is an example of using JAXB plugins in a structured way to resolve Internet-downloadable dependencies offline. There are obviously some pros and cons of using this approach. But for the use case in which the system sits inside a much-restricted ecosystem, this approach would be a feasible solution to fetch the dependencies without touching network configurations.
References
XML Catalog on Wikipedia
Published at DZone with permission of Aritra Nag. See the original article here.
Opinions expressed by DZone contributors are their own.
Comments