Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is interface-based proxying?

I was reading this regarding to where to place Transactional(interface vs implementation):

The Spring team's recommendation is that you only annotate concrete classes with the @Transactional annotation, as opposed to annotating interfaces. You certainly can place the @Transactional annotation on an interface (or an interface method), but this will only work as you would expect it to if you are using interface-based proxies. The fact that annotations are not inherited means that if you are using class-based proxies then the transaction settings will not be recognised by the class-based proxying infrastructure and the object will not be wrapped in a transactional proxy (which would be decidedly bad). So please do take the Spring team's advice and only annotate concrete classes (and the methods of concrete classes) with the @Transactional annotation.

So the question is what is interface-based proxy exactly and how can I see if it is used? Is it some configuration or it is the way how I instantiate/use instances?

like image 498
melonT Avatar asked Aug 02 '17 14:08

melonT


People also ask

How many types of proxy are there in spring framework?

Spring used two types of proxy strategy one is JDK dynamic proxy and other one is CGLIB proxy. JDK dynamic proxy is available with the JDK.

What is Cglib proxying in spring?

CGLIB is a code generation library. Spring uses CGLIB, to generate proxies. Spring AOP defaults to using standard JDK dynamic proxies for AOP proxies. This enables any interface (or set of interfaces) to be proxied.

How does JDK dynamic proxy work?

JDK Dynamic Proxies allow one to create implementations of Java interfaces at runtime by the means of Reflection. A proxy may be seen as a subject that will forward method calls to target instances and eventually return any result produced by the target instance to the caller.

What is JDK proxy?

JDK proxy (dynamic proxy): The JDK proxy creates a new proxy object by implementing interfaces of the target object and delegating method calls. CGLIB proxy: The CGLIB proxy creates a new proxy object by extending the target object and delegating method calls.


1 Answers

If Spring cannot create a JDK proxy (or if you force Spring to create a CGLIB proxy by setting proxyTargetClass to true) then the code will not execute in a transactional context because (as the Spring docs state):

The fact that annotations are not inherited means that if you are using class-based proxies then the transaction settings will not be recognised by the class-based proxying infrastructure and the object will not be wrapped in a transactional proxy

So, I think your concerns are:

How can you be sure that Spring does not create a CGLIB proxy

You must be configuring AOP based transactional support. If you are doing this by using <tx:annotation-driven/> then the default value for proxy-target-class (false) will suffice though could be explicit about this by setting: <tx:annotation-driven proxy-target-class=“false"></tx:annotation-driven>. If you are configuring transactional support in some other way (using Java config, for example) then just ensure that the value of TransactionProxyFactoryBean.proxyTargetClass is false.

How can you be sure that your @Transactional annotations are respected

This is easy, just annotate the concrete class with the @Transactional annotation instead of annotating the interfaces. This avoids any issues with proxying.

In summary, Spring should use interface based proxying as long as TransactionProxyFactoryBean.proxyTargetClass is false however, if you annotate a concrete class rather than an implementation then the issue of proxying won't affect transactional support.

like image 92
glytching Avatar answered Sep 21 '22 18:09

glytching