HowTo build FOP alternatively

This page is meant for distribution builders who want to build FOP using the java libraries in the system instead of the java libraries in FOP's lib and lib/build directories.

Libraries

The jar files in FOP's lib directory are both build-time and run-time dependencies. The jar files in FOP's lib/build directory are build-time dependencies. Most of those are used in special tasks. Only the qdox library is used in building fop.jar.

With ant

FOP's build system is based on ant. Due to the complexity of FOP's build process, it is advisable to use ant and FOP's ant build script in some or other way.

Using the CLASSPATH variable

Most efforts to build FOP using libraries in the system set the CLASSPATH variable for the invocation of ant. Example:

CLASSPATH=$JAVA_SHARE/avalon-framework.jar:$JAVA_SHARE/batik-all.jar:...
export CLASSPATH
ant package

This works generally, but the qdox library is an exception. When the qdox library is inserted in the class path in this way, it causes a NullPointerException, and the build fails. When this NPE is avoided by patching the relevant piece of code, the resulting jar file will lack many files called event-model.xml. The workaround is to copy the system's qdox library into FOP's lib/build directory.

Patching the build script

Alternatively, FOP can be built on top of libraries in the system by using a patched build script. FOP's build script defines its class paths in three path variables at the start of the build script, viz. libs-build-classpath, libs-tools-build-classpath, libs-run-classpath. These paths can be patched to refer to the required libraries in the system. The following is a working example on a Debian system:

 <property name="java-share" value="/usr/share/java"/>
 <path id="libs-build-classpath">
   <pathelement location="${java-share}/avalon-framework.jar"/>
   <pathelement location="${java-share}/batik-all.jar"/>
   <pathelement location="${java-share}/commons-io.jar"/>
   <pathelement location="${java-share}/commons-logging.jar"/>
   <pathelement location="${java-share}/serializer.jar"/>
   <pathelement location="${java-share}/servlet-api.jar"/>
   <pathelement location="${java-share}/xalan2.jar"/>
   <pathelement location="${java-share}/xercesImpl.jar"/>
   <pathelement location="${java-share}/xml-apis.jar"/>
   <pathelement location="${java-share}/xml-apis-ext.jar"/>
   <pathelement location="${java-share}/xmlgraphics-commons.jar"/>
 </path>
 <property name="lib-tools" value="${basedir}/lib/build"/>
 <path id="libs-tools-build-classpath">
   <path refid="libs-build-classpath"/>
   <!-- <pathelement location="${lib-tools}/asm-3.1.jar.jar"/> -->
   <!-- <pathelement location="${lib-tools}/asm-commons-3.1.jar"/> -->
   <!-- <pathelement location="${lib-tools}/backport-util-concurrent-3.1.jar"/> -->
   <!-- <pathelement location="${lib-tools}/jaxen-1.1.1.jar"/> -->
   <!-- <pathelement location="${lib-tools}/pmd-4.2.5.jar"/> -->
   <pathelement location="${java-share}/qdox.jar"/>
   <!-- <pathelement location="${lib-tools}/retroweaver-2.0.6-patched.jar"/> -->
   <!-- <pathelement location="${lib-tools}/retroweaver-rt-2.0.6-patched.jar"/> -->
   <!-- <pathelement location="${lib-tools}/xmlunit.jar"/> -->
 </path>
 <path id="libs-run-classpath">
   <path refid="libs-build-classpath"/>
   <pathelement location="${java-share}/fop.jar"/>
 </path>

Here many libraries in the lib/build directory were commented out, since they are not needed for building the package.

Without ant

Without ant you are entirely on your own. You should carefully analyse the build process as described in the ant build script, and reproduce that in your own build system.

But why would you?

HowTo test the newly built fop.jar file

FOP's layoutengine junit tests can be used to test the newly built fop.jar file. The following bash script gives an example:

FOP_SOURCE=/source/xml-fop-stable
JAVA_SHARE=/usr/share/java
FOP_JAR=$JAVA_SHARE/fop.jar
JAVA_CP="$FOP_SOURCE/build/test-classes:$FOP_JAR:$JAVA_SHARE/junit.jar:$JAVA_SHARE/xmlunit.jar:$JAVA_SHARE/avalon-framework.jar:$JAVA_SHARE/batik-all.jar:$JAVA_SHARE/commons-io.jar:$JAVA_SHARE/commons-logging.jar:$JAVA_SHARE/serializer.jar:$JAVA_SHARE/servlet-api.jar:$JAVA_SHARE/xalan2.jar:$JAVA_SHARE/xercesImpl.jar:$JAVA_SHARE/xml-apis.jar:$JAVA_SHARE/xml-apis-ext.jar:$JAVA_SHARE/xmlgraphics-commons.jar" TESTRUNNER=junit.textui.TestRunner

FOP_TEST_SET=standard
FOP_DISABLED=$FOP_SOURCE/test/layoutengine/disabled-testcases.xml
TESTCLASS=org.apache.fop.layoutengine.LayoutEngineTestSuite

cd $FOP_SOURCE
ant junit-compile
echo java -Dfop.layoutengine.testset=$FOP_TEST_SET -Dfop.layoutengine.disabled=$FOP_DISABLED -classpath $JAVA_CP $TESTRUNNER $TESTCLASS
java -Dfop.layoutengine.testset=$FOP_TEST_SET -Dfop.layoutengine.disabled=$FOP_DISABLED -classpath $JAVA_CP $TESTRUNNER $TESTCLASS
echo Tested $FOP_JAR, test suite $TESTCLASS

These tests compile and use the test classes in FOP's source directory, and use the newly built fop.jar file in the FOP_JAR variable and the libraries in the system. Note that these tests only test FOP's layout engine. They do not test FOP's backends, which write the laid-out pages to PDF, PostScript, etc.

HowTo/BuildFOPAlternatively (last edited 2011-08-30 07:45:48 by SimonPepping)