Im Fall 1 wird @Transactional auf jede öffentliche Einzelmethode angewendet. Private und geschützte Methoden werden von Spring ignoriert.
Spring wendet die Annotation auf Klassenebene auf alle öffentlichen Methoden dieser Klasse an, die wir nicht mit @Transactional annotiert haben. Wenn wir die Annotation jedoch auf eine private oder geschützte Methode setzen, ignoriert Spring sie fehlerfrei.
In Fall 2 wird @Transactional nur auf Methode2 () angewendet, nicht auf Methode1 ()
Fall 1: - Aufrufen von Methode1 () -> Eine Transaktion wird gestartet. Wenn method1 () method2 () aufruft, wird keine neue Transaktion gestartet, da bereits eine vorhanden ist
Fall 2: - Aufrufen von Methode1 () -> Es wird keine Transaktion gestartet. Wenn method1 () method2 () aufruft, wird KEINE neue Transaktion gestartet. Dies liegt daran, dass @Transactional nicht funktioniert, wenn eine Methode aus derselben Klasse aufgerufen wird. Es würde funktionieren, wenn Sie method2 () aus einer anderen Klasse aufrufen würden.
Aus dem Federreferenzhandbuch :
Im Proxy-Modus (Standardeinstellung) werden nur externe Methodenaufrufe abgefangen, die über den Proxy eingehen. Dies bedeutet, dass der Selbstaufruf einer Methode innerhalb des Zielobjekts, die eine andere Methode des Zielobjekts aufruft, zur Laufzeit nicht zu einer tatsächlichen Transaktion führt, selbst wenn die aufgerufene Methode mit @Transactional markiert ist. Außerdem muss der Proxy vollständig initialisiert sein, um das erwartete Verhalten bereitzustellen, sodass Sie sich in Ihrem Initialisierungscode, dh @PostConstruct, nicht auf diese Funktion verlassen sollten.
@Transactional
on a class gilt für jede Methode im Service. Es ist eine Abkürzung. In der Regel können Sie@Transactional(readOnly = true)
eine Serviceklasse festlegen , wenn Sie wissen, dass alle Methoden auf die Repository-Ebene zugreifen. Sie können das Verhalten dann mit@Transactional
on-Methoden überschreiben, die Änderungen in Ihrem Modell ausführen. Leistungsprobleme zwischen 1) und 2) sind nicht bekannt.quelle
Angenommen, Sie haben die folgende Klasse:
@Transactional(readOnly = true) public class DefaultFooService implements FooService { public Foo getFoo(String fooName) { // do something } // these settings have precedence for this method @Transactional(readOnly = false, propagation = Propagation.REQUIRES_NEW) public void updateFoo(Foo foo) { // do something } }
Die
@Transactional
Anmerkung auf Klassenebene wird auf jede Methode in der Klasse angewendet.Jedoch , wenn ein Verfahren mit Anmerkungen versehen ist
@Transactional
(wieupdateFoo(Foo foo)
) , wird dies auf der Klassenebene definierten Vorrang vor den Transaktions Einstellungen übernehmen.Mehr Info:
quelle
Zitat von hier
Da dieser Mechanismus auf Proxys basiert, werden nur 'externe' Methodenaufrufe abgefangen, die über den Proxy eingehen. Dies bedeutet, dass 'Selbstaufruf', dh eine Methode innerhalb des Zielobjekts, die eine andere Methode des Zielobjekts aufruft, zur Laufzeit nicht zu einer tatsächlichen Transaktion führt, selbst wenn die aufgerufene Methode mit @Transactional markiert ist!
quelle
@Transactional
Anmerkungen versehenen Methode und der mit@Transactional
Anmerkungen versehenen Klasse.@Transactional
. Die verknüpfte Dokumentation wird jetzt aktualisiert. Aus Gründen der Nachwelt heißt es in der neuesten Dokumentation: Das Spring-Team empfiehlt, nur konkrete Klassen (und Methoden konkreter Klassen) mit der Annotation @Transactional zu versehen, anstatt Schnittstellen mit Anmerkungen zu versehen.