Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Autowired spring bean is not a proxy

I'm working on a very small application connecting to a MySQL database.

I'm trying to create table record but getting 'no transaction in progress'.

I have all the right stuff in place:

  • a service interface MyService and its implementation MyServiceImpl
  • I have annotated the service impl with @Service
  • In the controller I used the interface name for the field @Autowired MyService
  • I have the correct transaction configuration as it was originally generated by roo
  • There is a public method MyService.create(...) which MyServiceImpl implements

But,

When I remote debug and inspect the controller's myService field what I see is something like com.some.package.services.MyService@12345 (and NOT something like $Proxy73) which to me is not right, because what should be autowired is the proxy not he target bean (which is what I think this is). If I'm correct then it makes sense that there is no transaction as the annotation would only kick in when invoking a public method annotated with @Transactional on a proxy.

Please tell me why is spring injecting the target bean in this setup.

Thanks

like image 502
jakstack Avatar asked Jul 14 '12 18:07

jakstack


1 Answers

If you have AspectJ-enabled transaction management (<tx:annotation-driven mode="aspectj" .../>) application of transactions happens in-place in the same class, either during build (compile-time weaving) or on startup (load-time weaving).

No new classes are created (like when using cglib) and no proxies (like with ordinary interface-based AOP in Spring). Instead bytecode of MyServiceImpl was modified directly without you even noticing. Unfortunately the only way to see AOP is to decompile your classes. If you use javap -c MyServiceImpl you'll find plenty of references to Spring transaction layer.

like image 96
Tomasz Nurkiewicz Avatar answered Sep 28 '22 18:09

Tomasz Nurkiewicz