diff --git a/CMakeLists.txt b/CMakeLists.txt index 3d5d3909ad..71b5f13a3e 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -203,6 +203,9 @@ option(USE_XPRESS "Use the XPRESS solver" OFF) message(STATUS "XPRESS support: ${USE_XPRESS}") if(BUILD_JAVA) + option(BUILD_FAT_JAR "Create single .jar with all dependencies (including native binaries)" OFF) + message(STATUS "Java build single fat .jar: ${BUILD_FAT_JAR}") + option(SKIP_GPG "Disable GPG sign" ON) message(STATUS "Java disable gpg:sign: ${SKIP_GPG}") diff --git a/cmake/README.md b/cmake/README.md index ab3d273bd1..3c050be034 100644 --- a/cmake/README.md +++ b/cmake/README.md @@ -159,6 +159,7 @@ cmake -S. -Bbuild -LH | | | | | `SKIP_GPG` | OFF | Disable GPG sign
Only available if `BUILD_JAVA=ON` | | `UNIVERSAL_JAVA_PACKAGE` | OFF | Build a multi platform package (i.e. `ortools-java` will depends on all native packages)
Only available if `BUILD_JAVA=ON` | +| `BUILD_FAT_JAR` | OFF | Build a `ortools-java` .jar that includes all of its own Maven dependencies, including the native package
Only available if `BUILD_JAVA=ON` | | | | | | `FETCH_PYTHON_DEPS` | BUILD_DEPS | Fetch python modules needed to build ortools package
Only available if `BUILD_PYTHON=ON` | | | | | diff --git a/cmake/java.cmake b/cmake/java.cmake index b67b185e7d..f739a16737 100644 --- a/cmake/java.cmake +++ b/cmake/java.cmake @@ -140,7 +140,7 @@ add_custom_target(java_native_package $<$>:$> ${JAVA_RESOURCES_PATH}/${JAVA_NATIVE_PROJECT}/ COMMAND ${MAVEN_EXECUTABLE} compile -B - COMMAND ${MAVEN_EXECUTABLE} package -B + COMMAND ${MAVEN_EXECUTABLE} package -B $<$:-Dfatjar=true> COMMAND ${MAVEN_EXECUTABLE} install -B $<$:-Dgpg.skip=true> BYPRODUCTS ${JAVA_NATIVE_PROJECT_PATH}/target @@ -190,7 +190,7 @@ add_custom_target(java_package ALL ${JAVA_PROJECT_PATH}/pom.xml ${JAVA_SRCS} COMMAND ${MAVEN_EXECUTABLE} compile -B - COMMAND ${MAVEN_EXECUTABLE} package -B + COMMAND ${MAVEN_EXECUTABLE} package -B $<$:-Dfatjar=true> COMMAND ${MAVEN_EXECUTABLE} install -B $<$:-Dgpg.skip=true> BYPRODUCTS ${JAVA_PROJECT_PATH}/target diff --git a/ortools/java/README.md b/ortools/java/README.md index 275f6a5c1a..9854004502 100644 --- a/ortools/java/README.md +++ b/ortools/java/README.md @@ -89,6 +89,8 @@ to study their layout. #### Building local Package +##### Standard Maven Package + So now, let's create the local `com.google.ortools:ortools-java.jar` maven package which will depend on our previous native package. @@ -118,10 +120,69 @@ mvn package mvn install ``` -If everything good the package (located in -`/java/ortools-java/target/`) should have this layout: +If Maven executes these commands successfully, the package (located in +`/temp_java/ortools-java/target/`) should have this layout: ``` -{...}/target/ortools-java-8.0.jar: +{...}/target/ortools-java-{build version}.jar: +\- com/ + \- google/ + \- ortools/ + \- Loader$PathConsumer.class + \- Loader$1.class + \- Loader.class + \- constraintsolver/ + \- RoutingModel.class + \- RoutingIndexManager.class + \- ... + \- ... +... +``` + +##### Dependency-inclusive Maven Package (fat .jar) + +We can also create a Maven package that includes all of its own dependencies, also known as a 'fat .jar'. This is useful +for situations in which it is more convenient, or even necessary, to use a single .jar as a dependency for a Java +OR-Tools project. + +One example is when OR-Tools is compiled with third-party solver support (such as CPLEX or XPress), and one needs to +build and execute in an environment that does not have access to one's local Maven repository (for example, a +remotely-built Docker container). + +Building a fat .jar with all dependencies included (including the native package) allows one to have a single +dependency, namely `com.google.ortools:ortools-java.jar`, which can be marked as `provided` in one's +project `pom.xml`: +```xml + + com.google.ortools + ortools-java + {insert build version here} + provided + +``` +One would then make this fat .jar available in the execution environment's Java classpath, for example: +```bash +java -cp "/path/to/dependency.jar" -jar "/path/to/your/executable/.jar" +``` +There are several ways to make the fat .jar dependency available to your Java program - please consult +[JDK documentation](https://devdocs.io/openjdk/) (this links to OpenJDK 15 documentation), as well as documentation for +any packaging and/or execution frameworks/tools you may be using. + +To package a fat .jar with Maven, run +```bash +mvn package -Dfatjar=true +``` +To then (optionally) install it to your local Maven repository, run +```bash +mvn install +``` +Note that this will replace any previously downloaded or built 'non-fat-.jar' ortools-java packages in your local +Maven repository + +[comment]: <> (FIXME show depedencies within .jar structure) +If Maven executes these commands successfully, the package (located in +`/temp_java/ortools-java/target/`) should have this layout: +``` +{...}/target/ortools-java-{build version}.jar: \- com/ \- google/ \- ortools/ @@ -169,6 +230,7 @@ Few links on the subject... * [Maven Javadoc Plugin](https://maven.apache.org/plugins/maven-javadoc-plugin/) * [Maven Source Plugin](https://maven.apache.org/plugins/maven-source-plugin/) * [Maven GPG Plugin](https://maven.apache.org/plugins/maven-gpg-plugin/) +* [Maven Assembly Plugin](https://maven.apache.org/plugins/maven-assembly-plugin/) * [Java Native Access Project](https://github.com/java-native-access/jna) ## Misc diff --git a/ortools/java/pom-full.xml.in b/ortools/java/pom-full.xml.in index aab043d948..c983489763 100644 --- a/ortools/java/pom-full.xml.in +++ b/ortools/java/pom-full.xml.in @@ -154,4 +154,39 @@ + + + + build-fat-jar + + + fatjar + true + + + + + + maven-assembly-plugin + + + jar-with-dependencies + + false + + + + make-assembly + package + + single + + + + + + + + + diff --git a/ortools/java/pom-local.xml.in b/ortools/java/pom-local.xml.in index e591035fd2..70a9758380 100644 --- a/ortools/java/pom-local.xml.in +++ b/ortools/java/pom-local.xml.in @@ -140,4 +140,39 @@ + + + + build-fat-jar + + + fatjar + true + + + + + + maven-assembly-plugin + + + jar-with-dependencies + + false + + + + make-assembly + package + + single + + + + + + + + + diff --git a/ortools/java/pom.xml.in b/ortools/java/pom.xml.in index dc1690c4ef..9a38e75f2e 100644 --- a/ortools/java/pom.xml.in +++ b/ortools/java/pom.xml.in @@ -129,4 +129,39 @@ + + + + build-fat-jar + + + fatjar + true + + + + + + maven-assembly-plugin + + + jar-with-dependencies + + false + + + + make-assembly + package + + single + + + + + + + + +