Transactional Configuration in Spring Boot

Опубликовано: 05 Июль 2026
на канале: Java Code House
134
4

Now, the Transactional annotation can be placed on interfaces, classes,
or both class and interface methods.
But, Spring recommends that you only annotate concrete classes
and methods of concrete classes with the AtTransactional annotation,
as opposed to annotating interfaces.
You certainly can place the AtTransactional annotation on an interface or an interface method,
but this works only as you would expect it to if you are using interface-based proxies.
The fact that Java annotations are not inherited from interfaces means that if you are using
class-based proxies, that is, proxy target class set to true or the weaving-based aspect
mode set to aspect J, then the transaction settings are not recognized by the proxying
and weaving infrastructure, and the object will not be wrapped in a transactional proxy,
which would be decidedly bad.
What does that mean?
This is about the transaction configuration in Spring.
When using XML-based configuration, there will be a line like the following,
in the config file, which would enable annotation-driven transaction management.
These are the settings or the attributes which can be set on this tag.
There is transaction manager, the mode, the proxy target class, and the order.
Since we are using Java-based configuration, let's look at the annotation which would be
used to provide the same configuration as above.
So it is the AtEnableTransactionManagement annotation, and it has these three optional elements,
mode, order, and proxy target class.
Regardless of the mode of configuration, that is either XML or Java-based configuration,
so long as we have not specifically set these attributes, the default values apply.
So let's look at each one.
The proxy target class could be either true or false.
The default value is false, in which case JDK interface-based proxies are created.
If this attribute is set to true, then cglib proxies will be used, which are class-based,
and therefore any at-transactional annotations on interfaces will be ignored.
Now the mode.
There are two values that can be applied to the mode attribute, proxy and AspectJ.
The default value of mode attribute is proxy, which processes annotated beans to be proxied
using Spring's AOP framework, which would proxy interfaces annotated with at-transactional.
But when the mode is set to AspectJ,
the interfaces annotated with at-transactional will be ignored, because
the aspect that interprets at-transactional annotations is the annotation-transaction aspect.
When using this aspect you must annotate the implementation class
and all methods within that class, not the interface if any, that the class implements.
AspectJ follows Java's rule that annotations on interfaces are not inherited.
So, as mentioned earlier, because this is a Spring Boot application,
transaction management is enabled by the framework,
without me having to add the at-enable-transaction-management annotation.
So, that means I'm using the default settings for proxy-target-class and mode.
So, as of now, I have no restrictions as to where to place the at-transactional annotation,
but it is safer to follow the recommendation in case those need to be changed.
There are a couple of things to keep in mind when using proxy mode, which is the default setting.
First, only external method calls will be transactional.
Even though a method is marked with at-transactional annotation,
if it is called within another method of the same object, it will not have transactional behavior.
The second one is that you should apply the at-transactional annotation only to methods
with public visibility. If you annotate protected private or package visible methods with the
at-transactional annotation, no error is raised, but the annotated method does not exhibit
the configured transactional settings. So, if you want transactional behavior in
either self-invocations or non-public methods, consider the use of AspectJ mode instead of proxy.
To summarize, Spring recommends to only annotate concrete classes and methods of concrete classes
with at-transactional. When using default configuration settings,
a method would be transactional only if it is called externally and if it is of public
visibility. I highly recommend reading the documentation for Spring transaction management,
as we cannot cover everything here.