2013-10-30 8 views

Antwort

20

withTransaction ist ein bisschen hackish, weil es Ihnen ermöglicht, transaktionale Arbeit überall zu tun, aber es ist am besten, Ihre Bedenken zu trennen und die Arbeit in einem transaktionalen Dienst zu erledigen. Ein Service ist standardmäßig transaktional, es sei denn, Sie fügen static transactional = false hinzu und können auf Klassen- und/oder Methodenebene mit der @Transactional Annotation abgestimmt werden. Sie sollten Ihren Code einfach in eine Service-Methode einfügen, ohne withTransaction oder withSession zu verwenden.

withSession ist eine bequeme Möglichkeit, auf den aktuellen Hibernate Session zuzugreifen (normalerweise der vom OpenSessionInView-Interceptor registrierte). Wenn Sie die Sitzung löschen oder andere Arbeit ausführen möchten, die nicht von GORM verfügbar gemacht wird, ist dies eine Möglichkeit, auf diese zuzugreifen, ohne auf die sessionFactory oder die thread-local-Besitzer zuzugreifen, die Spring verwendet.

Eine etwas gültige Verwendung von withTransaction außerhalb eines Transaktions Service-Methode ist es, eine Hibernate Session zu binden, wenn Sie außerhalb eines Controllers Anfrage sind (das heißt, wenn es keine automatisch erstellten Session). withTransaction startet eine Transaktion und erstellt bei Bedarf eine Session und hält sie für die Dauer der Sperrung offen. So können Sie es verwenden, um Lazy-Loading-Ausnahmen zu vermeiden. Wir benötigen eine andere Möglichkeit, dies ohne den Overhead einer Transaktion zu tun, wenn Sie gerade aus der Datenbank lesen und keine Transaktionsschreibvorgänge benötigen. Aber jetzt funktioniert dieser Ansatz. Wenn Sie jedoch Datenbankschreibvorgänge ausführen, verschieben Sie den Code in eine Servicemethode.

+0

Danke Burt. Ich habe Datensätze stapelweise analysiert und festgestellt, dass ich die 'withSession'-Verknüpfung benötigte, da der Aufruf von' sessionFactory.getCurrentSession(). Clear() 'mühsam wurde. –

+0

Diese Antwort ist nicht streng zutreffend. Es gibt viele Fälle, in denen Sie ein Rollback in einem Dienst ausführen möchten, ohne eine Ausnahme für den Aufrufer zu verursachen. In diesem Fall ist die einzige Option die Verwendung von Transaction. –

+4

Sie möchten fast nie eine Transaktion mit einer Ausnahme rückgängig machen, es sei denn, Sie befinden sich wirklich in einem Ausnahmezustand. Das typische Antipattern der Verwendung einer ungeprüften Ausnahme zum Rollback einer Transaktion nutzt einen Nebeneffekt und ist wegen der Kosten der Ausnahme ineffizient, und insbesondere bei Verwendung von Groovy. Aber 'withTransaction' ist _nicht_ der einzig richtige Weg dies zu tun. Verwenden Sie einfach TransactionAspectSupport.currentTransactionStatus(). SetRollbackOnly() ' –

3

Session und TransactionStatus sind zwei völlig verschiedene Dinge. Die Sitzung ist eine Abstraktion, die Ihnen Zugriff auf alle Hibernate-Funktionen gewährt, während der TransactionStatus zur Steuerung der aktuellen Transaktion verwendet werden kann.

withSession kann verwendet werden, wenn Sie einen direkten Zugang benötigen Funktionen zu überwintern. Dies kann nützlich sein, wenn Sie eine Hibernate-Funktion verwenden möchten, die nicht direkt von Grails/GORM unterstützt wird.