Quarkus native problem with latest Spring

73 views
Skip to first unread message

Aurea Munoz Hernandez

unread,
Jun 3, 2024, 4:21:30 AMJun 3
to Quarkus Development mailing list

Hi Team,

I'm encountering an issue while building a Quarkus application native image. When I run from quarkus root path the `mvn clean install -Dquickly` everything goes well.

However, when trying to run tests in native, specifically the spring-data-jpa integration test, I'm getting an error. Running the following command:

mvn -f integration-tests -pl spring-data-jpa -Dnative clean install

Results in:

Caused by: com.oracle.graal.pointsto.constraints.UnsupportedFeatureException: Discovered unresolved method during parsing: org.springframework.data.util.MethodInvocationRecorder.forProxyOf(java.lang.Class). This error is reported at image build time because class org.springframework.data.domain.Sort$TypedSort is registered for linking at image build time by command line and command line.
Error encountered while parsing org.springframework.data.domain.Sort.sort(Sort.java:143)
Parsing context:
   at static root method.(Unknown Source)

Detailed message:

        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.constraints.UnsupportedFeatures.report(UnsupportedFeatures.java:126)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.NativeImageGenerator.runPointsToAnalysis(NativeImageGenerator.java:810)
        ... 6 more
Caused by: com.oracle.graal.pointsto.constraints.UnresolvedElementException: Discovered unresolved method during parsing: org.springframework.data.util.MethodInvocationRecorder.forProxyOf(java.lang.Class). This error is reported at image build time because class org.springframework.data.domain.Sort$TypedSort is registered for linking at image build time by command line and command line.
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.reportUnresolvedElement(SharedGraphBuilderPhase.java:548)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.reportUnresolvedElement(SharedGraphBuilderPhase.java:542)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.handleUnresolvedMethod(SharedGraphBuilderPhase.java:469)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.handleUnresolvedInvoke(SharedGraphBuilderPhase.java:366)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.genInvokeStatic(BytecodeParser.java:1698)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.genInvokeStatic(BytecodeParser.java:1677)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.processBytecode(BytecodeParser.java:5441)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.iterateBytecodesForBlock(BytecodeParser.java:3431)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.iterateBytecodesForBlock(SharedGraphBuilderPhase.java:741)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.handleBytecodeBlock(BytecodeParser.java:3391)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.processBlock(BytecodeParser.java:3233)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.build(BytecodeParser.java:1137)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase$SharedBytecodeParser.build(SharedGraphBuilderPhase.java:161)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.BytecodeParser.buildRootMethod(BytecodeParser.java:1029)
        at jdk.internal.vm.compiler/org.graalvm.compiler.java.GraphBuilderPhase$Instance.run(GraphBuilderPhase.java:101)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.phases.SharedGraphBuilderPhase.run(SharedGraphBuilderPhase.java:115)
        at jdk.internal.vm.compiler/org.graalvm.compiler.phases.Phase.run(Phase.java:49)
        at jdk.internal.vm.compiler/org.graalvm.compiler.phases.BasePhase.apply(BasePhase.java:434)
        at jdk.internal.vm.compiler/org.graalvm.compiler.phases.Phase.apply(Phase.java:42)
        at jdk.internal.vm.compiler/org.graalvm.compiler.phases.Phase.apply(Phase.java:38)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.AnalysisParsedGraph.parseBytecode(AnalysisParsedGraph.java:146)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.meta.AnalysisMethod.parseGraph(AnalysisMethod.java:895)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.meta.AnalysisMethod.ensureGraphParsedHelper(AnalysisMethod.java:860)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.meta.AnalysisMethod.ensureGraphParsed(AnalysisMethod.java:843)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.phases.InlineBeforeAnalysisGraphDecoder.lookupEncodedGraph(InlineBeforeAnalysisGraphDecoder.java:175)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.doInline(PEGraphDecoder.java:1211)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.tryInline(PEGraphDecoder.java:1194)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.trySimplifyInvoke(PEGraphDecoder.java:1049)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.handleInvokeWithCallTarget(PEGraphDecoder.java:1001)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.handleInvoke(PEGraphDecoder.java:987)
        at jdk.internal.vm.compiler/org.graalvm.compiler.nodes.GraphDecoder.processNextNode(GraphDecoder.java:921)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.phases.InlineBeforeAnalysisGraphDecoder.processNextNode(InlineBeforeAnalysisGraphDecoder.java:344)
        at jdk.internal.vm.compiler/org.graalvm.compiler.nodes.GraphDecoder.decode(GraphDecoder.java:650)
        at jdk.internal.vm.compiler/org.graalvm.compiler.replacements.PEGraphDecoder.decode(PEGraphDecoder.java:892)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.phases.InlineBeforeAnalysis.decodeGraph(InlineBeforeAnalysis.java:76)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.MethodTypeFlowBuilder.parse(MethodTypeFlowBuilder.java:195)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.MethodTypeFlowBuilder.apply(MethodTypeFlowBuilder.java:621)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.MethodTypeFlow.createFlowsGraph(MethodTypeFlow.java:167)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.MethodTypeFlow.ensureFlowsGraphCreated(MethodTypeFlow.java:153)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.flow.MethodTypeFlow.getOrCreateMethodFlowsGraphInfo(MethodTypeFlow.java:111)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.typestate.DefaultAnalysisPolicy.staticRootMethodGraph(DefaultAnalysisPolicy.java:209)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.PointsToAnalysis.lambda$addRootMethod$0(PointsToAnalysis.java:318)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.AbstractAnalysisEngine$1.run(AbstractAnalysisEngine.java:344)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.util.CompletionExecutor.executeCommand(CompletionExecutor.java:187)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.util.CompletionExecutor.lambda$executeService$0(CompletionExecutor.java:171)
        at java.base/java.util.concurrent.ForkJoinTask$RunnableExecuteAction.exec(ForkJoinTask.java:1423)
        at java.base/java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:387)
        at java.base/java.util.concurrent.ForkJoinPool.externalHelpQuiesce(ForkJoinPool.java:2260)
        at java.base/java.util.concurrent.ForkJoinPool.helpQuiescePool(ForkJoinPool.java:2297)
        at java.base/java.util.concurrent.ForkJoinPool.awaitQuiescence(ForkJoinPool.java:3565)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.util.CompletionExecutor.complete(CompletionExecutor.java:237)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.PointsToAnalysis.doTypeflow(PointsToAnalysis.java:529)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.PointsToAnalysis.finish(PointsToAnalysis.java:517)
        at org.graalvm.nativeimage.pointsto/com.oracle.graal.pointsto.AbstractAnalysisEngine.runAnalysis(AbstractAnalysisEngine.java:162)
        at org.graalvm.nativeimage.builder/com.oracle.svm.hosted.NativeImageGenerator.runPointsToAnalysis(NativeImageGenerator.java:784)
        ... 6 more
------------------------------------------------------------------------------------------------------------------------
                        4,0s (9,9% of total time) in 87 GCs | Peak RSS: 3,90GB | CPU load: 6,23
------------------------------------------------------------------------------------------------------------------------
Produced artifacts:
 /Users/auri/Code/quarkus/integration-tests/spring-data-jpa/target/quarkus-integration-test-spring-data-jpa-999-SNAPSHOT-native-image-source-jar/quarkus-integration-test-spring-data-jpa-999-SNAPSHOT-runner-build-output-stats.json (build_info)
========================================================================================================================
Finished generating 'quarkus-integration-test-spring-data-jpa-999-SNAPSHOT-runner' in 39,6s.
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time:  48.030 s
[INFO] Finished at: 2024-05-28T17:31:56+02:00
[INFO] ------------------------------------------------------------------------
[INFO] 15 goals, 9 executed, 6 from cache, saving at least 13s
[ERROR] Failed to execute goal io.quarkus:quarkus-maven-plugin:999-SNAPSHOT:build (default) on project quarkus-integration-test-spring-data-jpa: Failed to build quarkus application: io.quarkus.builder.BuildException: Build failure: Build failed due to errors
[ERROR]         [error]: Build step io.quarkus.deployment.pkg.steps.NativeImageBuildStep#build threw an exception: io.quarkus.deployment.pkg.steps.NativeImageBuildStep$ImageGenerationFailureException: Image generation failed. Exit code: 1
[ERROR]         at io.quarkus.deployment.pkg.steps.NativeImageBuildStep.imageGenerationFailed(NativeImageBuildStep.java:468)
[ERROR]         at io.quarkus.deployment.pkg.steps.NativeImageBuildStep.build(NativeImageBuildStep.java:258)
[ERROR]         at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:103)
[ERROR]         at java.base/java.lang.reflect.Method.invoke(Method.java:580)
[ERROR]         at io.quarkus.deployment.ExtensionLoader$3.execute(ExtensionLoader.java:849)
[ERROR]         at io.quarkus.builder.BuildContext.run(BuildContext.java:256)
[ERROR]         at org.jboss.threads.ContextHandler$1.runWith(ContextHandler.java:18)
[ERROR]         at org.jboss.threads.EnhancedQueueExecutor$Task.doRunWith(EnhancedQueueExecutor.java:2516)
[ERROR]         at org.jboss.threads.EnhancedQueueExecutor$Task.run(EnhancedQueueExecutor.java:2495)
[ERROR]         at org.jboss.threads.EnhancedQueueExecutor$ThreadBody.run(EnhancedQueueExecutor.java:1521)
[ERROR]         at java.base/java.lang.Thread.run(Thread.java:1583)
[ERROR]         at org.jboss.threads.JBossThread.run(JBossThread.java:483)

When debugging the issue, I discovered that several classes from io.springframework.aop were missing. To address this, I added these classes to the quarkus-spring-api dependency by creating a new module, quarkus-spring-api-aop. This module contains the necessary classes. If you want to reproduce the issue, you'll need to install it locally and point Quarkus to this version (6.1.SP1-SNAPSHOT).

You can find the updated module here: quarkus-spring-data-api PR #13. Please note that this is a pre-release version as I'm waiting to ensure no additional classes are needed before making an official release.

Despite these changes, the error persists. I experimented with --initialize-at-build-time without success. As shown in the following code, the error seems to be related to a method that creates a proxy for a class received as a parameter. Given that the parameter is generic, it's challenging to configure --initialize-at-build-time for all possible classes.

Captura de pantalla 2024-06-03 a las 10.18.23.png


I'm at a loss on how to resolve this issue and am not sure if it's possible to use this setup as intended. I think that some AOP functionality might be bypassed in certain Quarkus extensions, but I haven't been able to find any concrete examples.

Any guidance or suggestions on how to overcome this obstacle would be greatly appreciated.

Thank you!

Best regards

Max Rydahl Andersen

unread,
Jun 4, 2024, 8:39:57 AMJun 4
to Aurea Munoz Hernandez, Quarkus Development mailing list

All this would be great to have in https://github.com/quarkusio/quarkus-spring-data-api/pull/13

Any chance that we somehow updated dependencies elsewhere too soon that caused this?

/max
https://xam.dk/about

--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/quarkus-dev/d0b2b9bd-286a-4889-9c3f-7d9ba77fa2b5n%40googlegroups.com.

Max Rydahl Andersen

unread,
Jun 5, 2024, 9:19:27 AMJun 5
to Aurea Munoz Hernandez, Quarkus Development mailing list


> Hi,
>
> I'm not sure I understand the question, Max.
> Yes, that PR will need to be released.

I mean the PR says just "Add new classes" - where as this email has a lot of great context for that PR.
Thus I mean the content of this email would be great to have on that PR.

for now i just linked the pr to this thread if someone has similar issue can discover the context.

> The problem comes from the dependencies upgrading, yes. If we've done it
> too soon, I wouldn't know to say.
>
> I finally managed to resolve my problem with Georgios' suggestion. I'm
> checking that everything is ok to release a few artifacts again and update
> quarkus with final versions.

cool.

/max

> Aurea Muñoz Hernandez
>
> Software Engineer
>
> Red Hat <https://www.redhat.com/>
>
> amun...@redhat.com
> <https://www.redhat.com>
>> <https://github.com/quarkusio/quarkus-spring-data-api/pull/13> . Please
>> note that this is a pre-release version as I'm waiting to ensure no
>> additional classes are needed before making an official release.
>>
>> Despite these changes, the error persists. I experimented with
>> --initialize-at-build-time without success. As shown in the following
>> code, the error seems to be related to a method that creates a proxy for a
>> class received as a parameter. Given that the parameter is generic, it's
>> challenging to configure --initialize-at-build-time for all possible
>> classes.
>>
>> [image: Captura de pantalla 2024-06-03 a las 10.18.23.png]
>>
>>
>> I'm at a loss on how to resolve this issue and am not sure if it's
>> possible to use this setup as intended. I think that some AOP functionality
>> might be bypassed in certain Quarkus extensions, but I haven't been able to
>> find any concrete examples.
>>
>> Any guidance or suggestions on how to overcome this obstacle would be
>> greatly appreciated.
>>
>> Thank you!
>>
>> Best regards
>> --
>> You received this message because you are subscribed to the Google Groups
>> "Quarkus Development mailing list" group.
>> To unsubscribe from this group and stop receiving emails from it, send an
>> email to quarkus-dev...@googlegroups.com.
>> To view this discussion on the web visit
>> https://groups.google.com/d/msgid/quarkus-dev/d0b2b9bd-286a-4889-9c3f-7d9ba77fa2b5n%40googlegroups.com
>> <https://groups.google.com/d/msgid/quarkus-dev/d0b2b9bd-286a-4889-9c3f-7d9ba77fa2b5n%40googlegroups.com?utm_medium=email&utm_source=footer>
>> .
>>
>> --
>> You received this message because you are subscribed to a topic in the
>> Google Groups "Quarkus Development mailing list" group.
>> To unsubscribe from this topic, visit
>> https://groups.google.com/d/topic/quarkus-dev/o9KJAumg01c/unsubscribe.
>> To unsubscribe from this group and all its topics, send an email to
>> quarkus-dev...@googlegroups.com.
>> To view this discussion on the web visit
>> https://groups.google.com/d/msgid/quarkus-dev/C6C0222C-C062-4826-B2F0-F7E66EAFD0E2%40redhat.com
>> <https://groups.google.com/d/msgid/quarkus-dev/C6C0222C-C062-4826-B2F0-F7E66EAFD0E2%40redhat.com?utm_medium=email&utm_source=footer>
>> .
>>

Aurea Munoz Hernandez

unread,
Jun 9, 2024, 12:18:43 PMJun 9
to mand...@redhat.com, Quarkus Development mailing list
Hi,

I'm not sure I understand the question, Max.
Yes, that PR will need to be released.
The problem comes from the dependencies upgrading, yes. If we've done it too soon, I wouldn't know to say.

I finally managed to resolve my problem with Georgios' suggestion. I'm checking that everything is ok to release a few artifacts again and update quarkus with final versions.

Aurea Muñoz Hernandez

Software Engineer

Red Hat


On Tue, Jun 4, 2024 at 2:40 PM Max Rydahl Andersen <mand...@redhat.com> wrote:
You received this message because you are subscribed to a topic in the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/quarkus-dev/o9KJAumg01c/unsubscribe.
To unsubscribe from this group and all its topics, send an email to quarkus-dev...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/quarkus-dev/C6C0222C-C062-4826-B2F0-F7E66EAFD0E2%40redhat.com.

Aurea Munoz Hernandez

unread,
Jun 9, 2024, 12:18:43 PMJun 9
to mand...@redhat.com, Quarkus Development mailing list
Ah ah! ok!!!
Yes! you're right. Good catch.
Georgios just added a link to the PR ;-)



Aurea Muñoz Hernandez

Software Engineer

Red Hat


Georgios Andrianakis

unread,
Jun 9, 2024, 12:18:43 PMJun 9
to amun...@redhat.com, Quarkus Development mailing list
For this case, what needs to be done is to write a GraalVM substitution which essentially does not nothing for the constructor. It will likely looks like this:

@TargetClass(className = "org.springframework.data.domain.Sort")
public class Target_org_springframework_data_domain_Sort {

@Substitute
public Target_org_springframework_data_domain_Sort() {
}
}

--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.


--

Georgios Andrianakis

Independent Contractor


Georgios Andrianakis

unread,
Jun 9, 2024, 12:18:44 PMJun 9
to amun...@redhat.com, Quarkus Development mailing list
Or rather use TypeSort.

I expect this will likely be needed for other types as well
Reply all
Reply to author
Forward
0 new messages