Repository navigation
Trim the bundled JRE: drop java.desktop, jdk.jfr, java.compiler and strip native libraries (-13 MB per wheel) - #452
Merged
Merged
Conversation
…trip native libraries jdeps names java.desktop, jdk.jfr and java.compiler because of optional users (JTS awt, Jackson and snakeyaml java.beans, an unused JFR reporter, agrona's code generator), so the jlink runtime carried about 13 MB that no code path of the wheel reaches. scripts/jre_module_exclusions.txt now lists the modules to keep out. Dockerfile.build and build-native.sh remove them from the jdeps answer before jlink and fail the build when one is still in `java --list-modules` afterwards. The Linux build also strips the runtime's .so files. tests/test_jar_closure.py reads the class files of the shipped jars against the packages of the running runtime and fails when a class names a package of a removed module unless the reference is listed with a reason; it also checks that the runtime lacks the modules and runs Jackson and the YAML mapper on it. Linux x86_64 wheel: 80.8 MB to 67.7 MB. Closes #447. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #447.
The wheel's bundled jlink runtime no longer carries
java.desktop(withjava.datatransferandjava.prefs, which only it requires),jdk.jfrandjava.compiler, and on Linux its.sofiles are stripped. The Linux x86_64 wheel built from the same 71 jars goes from 80,848,056 bytes (80.8 MB) to 67,688,031 bytes (67.7 MB, 64.6 MiB), and the runtime goes from 20 modules to 15. The module list is still detected by jdeps.scripts/jre_module_exclusions.txtlists what to keep out,Dockerfile.build(Linux) andbuild-native.sh(macOS, Windows) remove those names from the jdeps answer before jlink, and both fail the build whenjava --list-modulesof the finished runtime still shows one of them. Detection that finds no modules now stops the build, because thejava.sefallback would bring the three modules back.Size after each step, Linux x86_64 runtime (deflated, as in the wheel): baseline 40.9 MB, with
strip --strip-unneededon the.sofiles only 39.2 MB, with the three modules removed only 29.3 MB, both 27.8 MB. jlink already ran with--strip-debug,--no-header-files,--no-man-pagesand--compress zip-9;libjvm.sostill carried its symbol table, which the strip removes (a JVM crash report names fewer native frames). The strip runs on Linux only: macOS and Windows keep their libraries as jlink writes them, and the Windows build already prunes its own artifacts.jdeps findings over the 62 shipped jars the build analyses, then checked on the constant pools of every shipped class (multi-release entries included):
java.desktopis named byorg.locationtech.jts.awt.*andTestBuilderProxy(JTS),java.beansin jackson-databindJava7SupportImpl, snakeyamlMethodProperty, commons-lang3AbstractCircuitBreaker, micrometerLog4j2Metricsand jakarta.xml.bind-apiJAXB,java.awt.geomin commons-math3twod.Line, andjava.awt.datatransferin jakarta.activation-apiDataHandler.jdk.jfris named only by the engine'sJVMGCHistogramReporter, andjava.compileronly byorg.agrona.generation.*. For every one of them no class outside the named one refers to it (nothing instantiatesYaml, nothing calls the JFR reporter or agrona's generator, swagger-core refers only to the JAXB annotations), so each is optional and unreachable from the bindings, the server, Studio and the SQL and Cypher engines. Jackson loadsJava7SupportImplby name (no class refers to it) and the runtime prints no warning for it. Nothing in the engine, server or bindings sources importsjava.awt,javax.swing,javax.toolsorjavax.lang.model.tests/test_jar_closure.pynow starts the bundled runtime, reads the class files of the shipped jars, and fails when a class names a package of a removed module unless the jar and package are onALLOWED_REMOVED_MODULE_USEwith a reason (ten entries, each one of the findings above). It also checks that the running runtime lacks the removed modules, that the scan sees the known references, that no allow-list entry is dead, and that Jackson and its YAML mapper run withoutjava.beans. On the untrimmed baseline wheel onlytest_bundled_runtime_lacks_the_excluded_modulesfails, as it should.Gate, linux/amd64 wheel built with
build.sh linux/amd64 3.12on the local jars: the build's Docker smoke test passed, the full bindings suite (uv run pytest, 1,266 tests) gave 1,262 passed, 4 failed, 1 skipped (polars not installed), and the same four fail on the untouched baseline wheel with the same jars: threetest_collection_equality_known_issues.pytests are XPASS(strict) for ArcadeData#10448 (the engine jars now fix it, so those xfail markers are stale), andtest_sigint_during_a_query_that_calls_python_is_a_keyboard_interruptfails in the full run at the same place on both wheels and passes alone (3 of 3 on this wheel). Of 12 standalone examples run on this wheel (01, 02, 17 to 21, 23 to 26, 28), 11 pass;21_graph_analytical_view_sql.pyfails withExpected restored GAV nodeCount = 135000on both wheels. The examples that need downloaded datasets or sentence-transformers were not run.build-native.shpassesbash -nandshfmtbut was not run: macOS and Windows runners build it in the release workflow.Docs: the module exclusion and the strip are in
build-architecture.md,contributing.md,testing.mdandarchitecture.md; the wheel and runtime sizes inREADME.md,bindings/python/README.md,index.md,installation.md,build-architecture.mdandci-setup.mdare the numbers measured on this wheel (2026-10-22); strict mkdocs builds.🤖 Generated with Claude Code