When running the jdbc-tx
sample in sb-3.0.x
branch from spring-native, it fails with:
java.lang.IllegalStateException: Failed to execute CommandLineRunner
at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:769) ~[jdbc-tx:3.0.0-SNAPSHOT]
at org.springframework.boot.SpringApplication.callRunners(SpringApplication.java:750) ~[jdbc-tx:3.0.0-SNAPSHOT]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:318) ~[jdbc-tx:3.0.0-SNAPSHOT]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1301) ~[jdbc-tx:3.0.0-SNAPSHOT]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1290) ~[jdbc-tx:3.0.0-SNAPSHOT]
at app.main.SampleApplication.main(SampleApplication.java:23) ~[jdbc-tx:0.0.1.BUILD-SNAPSHOT]
Caused by: java.lang.IllegalArgumentException: Expected transaction
at org.springframework.util.Assert.isTrue(Assert.java:121) ~[na:na]
at app.main.Runner.run(Runner.java:53) ~[jdbc-tx:0.0.1.BUILD-SNAPSHOT]
at org.springframework.boot.SpringApplication.callRunner(SpringApplication.java:766) ~[jdbc-tx:3.0.0-SNAPSHOT]
... 5 common frames omitted
This is the run method:
@Override
@Transactional
public void run(String... args) throws Exception {
Assert.isTrue(TransactionSynchronizationManager.isActualTransactionActive(), "Expected transaction");
try {
find(1L);
}
catch (EmptyResultDataAccessException e) {
entities.update(ADD_FOO, 1L, "Hello");
}
}
I guess that @Transactional
doesn't work in native-image.
Comment From: sdeleuze
Related to #28688.
Comment From: sdeleuze
I have improved the support for @Transactional
with this commit that makes @Transactional
annotated with @Reflective
and registers proxy hints for SpringProxy
but the jdbc-tx
sample here still fails when compiled as a native executable with error creating bean with name 'userEndpoints': Unsatisfied dependency expressed through method 'userEndpoints' parameter 0: No qualifying bean of type 'app.main.Finder<app.main.model.Foo>' available: expected at least 1 bean which qualifies as autowire candidate. Dependency annotations: {} error
, like if proxied beans can't be injected in native. Notice here we have @Component public class Runner implements CommandLineRunner, Finder<Foo> { ... }
that needs to be injected in @Bean public RouterFunction<?> userEndpoints(Finder<Foo> entities) { ... }
.This samples works correctly on JVM + AOT so this issue is native specific.
Comment From: sdeleuze
As discussed with @sbrannen, we need to replace the SpringProxyRuntimeHintsRegistrar
by an AOT processor that will register dynamically the required proxies like here CommandLineRunner.class, Finder.class, SpringProxy.class, Advised.class, DecoratingProxy.class
+ reflection entries for proxied interfaces with declared methods.