Skip to content

chore(ci): run GraalVM native tests on GraalVM 25 and upgrade native-maven-plugin to 1.1.14 - #2684

Draft
phipag wants to merge 9 commits into
mainfrom
feat/graalvm-25
Draft

phipag wants to merge 9 commits into
mainfrom
feat/graalvm-25

Conversation

@phipag

@phipag phipag commented Oct 10, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Changes

This PR moves the GraalVM native tests from GraalVM 21.0.8 to GraalVM 25 and upgrades native-maven-plugin from 0.11.5 to 1.1.14. It supersedes the Dependabot PR aws-powertools/powertools-lambda-java#2661, which cannot pass on GraalVM 21.

  • native-maven-plugin 1.1.14: Upgrades the root pom.xml, the 5 sam-graalvm example poms and powertools-e2e-tests/handlers/pom.xml. Plugin 1.x requires the 1.0 reachability metadata repository, which uses the unified reachability-metadata.json format for GraalVM 25. GraalVM 21 rejects this format.
  • Removes the native-junit6-jdk21 profile: The initialize-at-buildtime list in junit-platform-native 1.1.14 contains MethodSegmentResolver and DiscoveryIssueReportingDiscoveryListener. The 0.11.5 list does not (graalvm/native-build-tools#794). GraalVM 21 is no longer the tested toolchain for the native tests.
  • CI on a pinned GraalVM 25 innovation release: The graalvm-build job uses graalvm/setup-graalvm v1.6.7 with java-version: "25" and version: "25.4.4.1.1". setup-graalvm matches this value against the version metadata of the Oracle GraalVM artifacts. Move back to the LTS release once oracle/graal#12723 is fixed there.
  • Examples: The sam-graalvm Dockerfiles use sam/build-java25 and GraalVM for JDK 25 LTS (download.oracle.com/graalvm/25/latest, currently 25.0.4). They only build native images of the examples and do not run the tracing-agent native tests. This PR also removes a stray curl argument from their download step.
  • Docs: GraalVM.md and docs/FAQs.md describe GraalVM 25, the CI GraalVM version, the example toolchain and the known issue below.
  • Skips JaCoCo in the native profile: Plugin 0.11.5 replaced the surefire argLine with the tracing agent. Plugin 1.x appends the agent to the existing argLine, so JaCoCo now instruments net.bytebuddy.utility.Invoker$Dispatcher before the tracing agent records it as a predefined class. The native image then rejects the uninstrumented class because its hash does not match.
  • Adds -H:+ClassForNameRespectsClassLoader to the native test build: Byte Buddy loads each Mockito mock class with Class.forName(name, false, loader) on its own class loader. GraalVM 25.0 fell back to ClassLoader#loadClass when the image contained predefined classes. GraalVM 25.1 and later ignore the class loader by default, so every Mockito mock failed with ClassNotFoundException. The option restores the delegation. GraalVM 25.1 added the equivalent --future-defaults=class-for-name-respects-class-loader, but GraalVM 25.0 rejects it.
  • ClassPreLoader continues after a LinkageError: With the class loader delegation, Class.forName initializes com.sun.management.internal.PlatformMBeanProviderImpl from the tracing classesloaded.txt. Its static initializer throws UnsatisfiedLinkError in a native image, which escaped the CRaC beforeCheckpoint hook. ClassPreLoader now logs the error at debug level and loads the next class. A new unit test covers this.

Why CI uses the innovation release and not 25.0 LTS: GraalVM 25.0.x bundles ASM 9.7.1, which reads class files up to major version 68. On JDK 25, Byte Buddy (used by Mockito) generates classes with major version 69. The tracing agent records these classes as predefined classes, and the native test image build fails in ClassPredefinitionFeature with Unsupported class file major version 69. On GraalVM 25.0.2, this breaks 12 of 17 native modules. The upstream issue is oracle/graal#12723. GraalVM 25 innovation releases parse class files with the Java Class-File API instead of ASM. This only affects the native tests that use Mockito. Users can build Powertools functions with GraalVM 25.0 LTS.

Verification: The graalvm-build job resolved Oracle GraalVM 25.4.4.1.1 and passed the native tests of all 16 modules with tests (664 tests, 0 failures). java-build passed on Java 17, 21 and 25. The verify dependency review fails because the license metadata of native-maven-plugin 1.1.14 resolves to LicenseRef-bad-non-standard. That is a license gate, not a code failure.

Issue number: closes #2416


By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.

Disclaimer: We value your time and bandwidth. As such, any pull requests created on non-triaged issues might not be successful.

Move the graalvm-build job from GraalVM 21.0.8 to the latest GraalVM 25
innovation release (setup-graalvm version "25i-latest").

GraalVM 25.0.x LTS bundles ASM 9.7.1, which reads class files up to
major version 68. On JDK 25, Byte Buddy generates Mockito classes with
major version 69, and ClassPredefinitionFeature fails with
"Unsupported class file major version 69" (oracle/graal#12723).
Innovation releases parse class files with the Java Class-File API.

Also move the sam-graalvm example build images to sam/build-java25 and
GraalVM 25, and document the known issue in GraalVM.md.

Refs #2416
Upgrade native-maven-plugin from 0.11.5 to 1.1.14 in the root pom, the
sam-graalvm examples and the e2e test handlers. Plugin 1.x uses the 1.0
reachability metadata repository in the unified reachability-metadata.json
format, which requires GraalVM 25.

Remove the temporary native-junit6-jdk21 profile. Plugin 1.1.0 and later
initialize the JUnit 6 discovery classes at build time
(graalvm/native-build-tools#794).

Supersedes the Dependabot bump to native-maven-plugin 1.1.14.
Refs #2416
@github-actions

github-actions Bot commented Oct 10, 2026 •

Copy link
Copy Markdown
Contributor

Dependency Review

The following issues were found:
  • ✅ 0 vulnerable package(s)
  • ❌ 7 package(s) with incompatible licenses
  • ✅ 0 package(s) with invalid SPDX license definitions
  • ✅ 0 package(s) with unknown licenses.
See the Details below.

Snapshot Warnings

⚠️: No snapshots were found for the head SHA f4d40dc.
Ensure that dependencies are being submitted on PR branches and consider enabling retry-on-snapshot-warnings. See the documentation for more information and troubleshooting advice.

License Issues

examples/powertools-examples-cloudformation/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

examples/powertools-examples-core-utilities/sam-graalvm/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

examples/powertools-examples-idempotency/sam-graalvm/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

examples/powertools-examples-parameters/sam-graalvm/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

examples/powertools-examples-serialization/sam-graalvm/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License

powertools-e2e-tests/handlers/pom.xml

PackageVersionLicenseIssue Type
org.graalvm.buildtools:native-maven-plugin1.1.14LicenseRef-bad-non-standardIncompatible License
Allowed Licenses: Apache-1.1, Apache-2.0, ISC, MIT, MIT-0, MIT-CMU, MIT-enna, MIT-feh, MIT-Festival, MIT-Modern-Variant, MIT-open-group, MIT-testregex, MIT-Wu, BSD-1-Clause, BSD-2-Clause, BSD-2-Clause-Views, BSD-3-Clause, BSD-3-Clause-Attribution, BSD-3-Clause-Clear, BSD-3-Clause-flex, BSD-3-Clause-HP, BSD-3-Clause-LBNL, BSD-3-Clause-Modification, BSD-3-Clause-No-Military-License, BSD-3-Clause-No-Nuclear-License, BSD-3-Clause-No-Nuclear-License-2014, BSD-3-Clause-No-Nuclear-Warranty, BSD-3-Clause-Open-MPI, UPL-1.0

OpenSSF Scorecard

PackageVersionScoreDetails
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0
maven/org.graalvm.buildtools:native-maven-plugin 1.1.14 🟢 6.7
Details
CheckScoreReason
Code-Review🟢 10all changesets reviewed
Maintained🟢 1030 commit(s) and 11 issue activity found in the last 90 days -- score normalized to 10
Packaging⚠️ -1packaging workflow not detected
Dangerous-Workflow🟢 10no dangerous workflow patterns detected
Token-Permissions🟢 10GitHub workflow tokens follow principle of least privilege
Binary-Artifacts🟢 5binaries present in source code
Pinned-Dependencies🟢 10all dependencies are pinned
CII-Best-Practices⚠️ 0no effort to earn an OpenSSF best practices badge detected
License🟢 9license file detected
Branch-Protection⚠️ -1internal error: error during branchesHandler.setup: internal error: some github tokens can't read classic branch protection rules: https://github.com/ossf/scorecard-action/blob/main/docs/authentication/fine-grained-auth-token.md
Signed-Releases⚠️ -1no releases found
Security-Policy⚠️ 0security policy file not detected
Fuzzing⚠️ 0project is not fuzzed
SAST⚠️ 0SAST tool is not run on all commits -- score normalized to 0

Scanned Files

  • examples/powertools-examples-cloudformation/pom.xml
  • examples/powertools-examples-core-utilities/sam-graalvm/pom.xml
  • examples/powertools-examples-idempotency/sam-graalvm/pom.xml
  • examples/powertools-examples-parameters/sam-graalvm/pom.xml
  • examples/powertools-examples-serialization/sam-graalvm/pom.xml
  • pom.xml
  • powertools-e2e-tests/handlers/pom.xml

native-maven-plugin 0.11.5 replaced the surefire argLine with the tracing
agent argument. 1.x appends it to the existing argLine
(graalvm/native-build-tools NativeExtension#appendAgentArgument), so the
JaCoCo agent from prepare-agent now runs in the same JVM as the tracing
agent.

JaCoCo instruments net.bytebuddy.utility.Invoker$Dispatcher, which Byte
Buddy defines at runtime, before the tracing agent records it as a
predefined class. At native runtime, Byte Buddy defines the uninstrumented
class, whose hash is not in predefined-classes-config.json, and Mockito
fails with "Could not initialize plugin: interface MockMaker". This broke
20 of 138 powertools-metrics native tests on GraalVM 25.4.

Skip JaCoCo in the native profile so the tracing agent records the same
bytes that Byte Buddy defines in the native image.
Mockito creates mocks with Byte Buddy's ByteArrayClassLoader, which loads
each generated class with Class.forName(name, false, this). Up to GraalVM
25.0, Class.forName fell back to ClassLoader#loadClass when the image
contained predefined classes. GraalVM 25.1 and later route Class.forName
through ClassRegistries, which ignores the class loader unless
ClassForNameRespectsClassLoader is enabled. Byte Buddy never defines the
predefined mock class, and all Mockito tests fail with
"Cannot load class ...$MockitoMock$..." caused by ClassNotFoundException.

Enable -H:+ClassForNameRespectsClassLoader for native test images. GraalVM
25.1 added the equivalent --future-defaults=class-for-name-respects-class-loader
(GR-71698), but GraalVM 25.0 rejects that value. The experimental option
is available in both.
ClassPreLoader only caught ClassNotFoundException. A LinkageError from
Class.forName, e.g. an ExceptionInInitializerError or an
UnsatisfiedLinkError, stopped the preloading and propagated out of the
CRaC beforeCheckpoint hooks.

With -H:+ClassForNameRespectsClassLoader on GraalVM 25.4, the tracing
native test TracingUtilsTest.testBeforeCheckpointDoesNotThrowException
fails this way. Class.forName now initializes
com.sun.management.internal.PlatformMBeanProviderImpl from the tracing
classesloaded.txt, and its static initializer cannot load the
management_ext native library in the native image.

Catch LinkageError, log it at debug level and continue with the next class.
The GraalVM download step ran "curl -4 -L curl <url>", so curl also tried
to fetch a host named "curl". Use the same command as the e2e test
Dockerfile.
Replace the floating "25i-latest" with the exact innovation release, so
the graalvm-build job is reproducible, as with the earlier 21.0.8 pin.
setup-graalvm v1.6.7 matches the version input against the GDS artifact
version metadata, which is "25.4.4.1.1" for this release.

Document the CI GraalVM version in GraalVM.md. Also state that the
sam-graalvm example Dockerfiles use the GraalVM for JDK 25 LTS release:
they only build native images of the examples and do not run the
tracing-agent native tests, so oracle/graal#12723 does not affect them.

Refs #2416
…tive profile

The comment said that NativeExtension overwrites the surefire argLine.
That was the 0.11.x behavior. 1.x appends the tracing agent to the
existing argLine (verified with help:effective-pom -Pnative -Dagent=true),
so the jdk16 add-opens flags are kept. Keep JDK_JAVA_OPTIONS as is and
explain why JaCoCo is skipped.
…guard

native-maven-plugin 1.x keeps the jdk16 add-opens flags in the surefire
argLine (NativeExtension.appendAgentArgument). JDK_JAVA_OPTIONS is no
longer required, but it stays as a safeguard. Comment-only change.
@sonarqubecloud

Copy link
Copy Markdown

This branch was successfully deployed

1 active deployment
E2E — f4d40dcc Deployed Oct 10, 2026 by phipag via E2E ValidationALBE2ET (Java 25) #455
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Maintenance: Modernize GraalVM native-image test infrastructure

1 participant