Infinispan also uses Transaction.registerSynchronization.
I should point out that timing of when
Transaction.registerSynchronization() is called is also important. Any
component that registers their sync via
Transaction.registerSynchronization and they register their sync too
late in the game, will get the "Synchronizations are not allowed" ISE.
My understanding of "Too late in the game", would be attempting to
register the sync after commit has been called to start ending the
transaction.
Note from Jonathan Halliday about the same:
"
per the JTA spec, interposed Synchronizations must be called after
non-interposed ones. Since hibernate is using interposed
Synchronizations, the tx has already passed the point at which it can
call non-interposed Synchronizations. Therefore it does not allow them
to be registered, on the basis that there needs to be some way to spot
that they are not going to get called, otherwise you'd spend hours
scratching your head and wondering why the Synchronization was not
getting invoked. There is a corner case where you don't give a toss
about beforeCompletion and want the Synchronization only for
afterCompletion, but there is no way in the API to indicate that so we
play it safe and disallow uniformly.
"
In the
http://pastie.org/1836698 case that caused a "Synchronizations
are not allowed" exception, Hibernate had already registered its
synchronization via
TransactionSynchronizationRegistry.registerInterposedSynchronization()
early enough. Its our AS7 connection pool management that is being
called to get a database connection and that triggers the call to
Transaction.registerSynchronization().
In summary, I think the following components need to be involved in this
discussion and how likely they are to work with
TransactionSynchronizationRegistry.registerInterposedSynchronization:
AS7 JPA subsystem and Hibernate persistence provider. We can easily
change a few lines of code that uses Hibernate JTAPlatform support for
choosing how to register syncs.
AS7 EJB3.1 is already trying to use TSR for registering its syncs and
currently expects to continue using it.
AS7 datasource/ connection pool management (IronJacamar). Is not yet
using TransactionSynchronizationRegistry.registerInterposedSynchronization.
Infinispan does not yet use
TransactionSynchronizationRegistry.registerInterposedSynchronization
(some discussion started on infinispan-dev(a)lists.jboss.org).
Seam (2+3) details are below already. It sounds like some work on Seam3
could be needed. Lets continue discussing the below, so we know if we
can avoid changing Seam3.
On 06/01/2011 05:45 PM, Stuart Douglas wrote:
Seam 2 or Seam 3?
Thanks for answering for both. I'm just looking for what would break,
so this is helpful.
Seam 2 registers it's synchronisations using an EJB that holds onto the
synchronisations and calling them in the appropriate EJB callback method, so this should
have a minimal effect.
Good to hear.
Seam 3 currently uses the TransactionManager, however the strategy used is pluggable.
Originally it used the same approach as Seam 2, however it was changed to work around an
AS6 bug where
the same EJB could not be deployed in two different applications. If this does cause
problems I will do a point release that provides an AS7 compatible synchronisations
implementation.
At what point in the transaction, When does Seam 3 use
Transaction.registerSynchronization()? Before the transaction commit
has been initiated? Or after?
If before, I think we are okay with not changing it. If it could be
either before/after, a pluggable solution would be helpful. :)
Stuart
On 02/06/2011, at 6:05 AM, Scott Marlow wrote:
> I cross posted a link to this email, on the Hibernate-dev/Infinispan-dev
> project mail lists.
>
> Can anyone answer on the impact on seam, if we switched to using TSR in AS7?
>
>
> On 05/31/2011 04:06 PM, Scott Marlow wrote:
>> We are supposed to be able to use
>> TransactionSynchronizationRegistry.registerInterposedSynchronization
>> (TSR) in our containers but I wanted to bring up an ordering issue that
>> can happen.
>>
>> If you look at
http://pastie.org/1836698, you can see what happened when
>> Hibernate registered a synchronization object with the TSR and we tried
>> after to get a database connection from the connection pool.
>>
>> Basically, once a synchronization object is registered with the TSR, the
>> other way of registering a synchronization object through the
>> Transaction registerSynchronization() cannot be used (or you get the
>> above linked IllegalStateException error).
>>
>> The short term fix was to avoid registering Hibernate with the TSR and
>> instead use the Transaction registerSynchronization(). This helped
>> avoid the ISE exception as the TSR sync ordering check is avoided.
>>
>> The Transaction registerSynchronization(), has no ordering requirements
>> but as we have seen, the TSR registerInterposedSynchronization does.
>>
>> I think we need to be consistent across our projects and either use TSR
>> or avoid it (to avoid the "Synchronizations are not allowed!" JTA
>> error). If/when we use it, we need to coordinate the switch over to it,
>> so that all projects have time to switch to it.
>>
>> I'm hoping someone will tell me that there is an easier path to use TSR
>> registerInterposedSynchronization in some of our projects. What do you
>> think?
>>
>> The other question, is how/when we should we coordinate a switch over to
>> use TSR (assuming there is agreement that we should coordinate the switch)?
>>
>> Scott
>> _______________________________________________
>> jboss-as7-dev mailing list
>> jboss-as7-dev(a)lists.jboss.org
>>
https://lists.jboss.org/mailman/listinfo/jboss-as7-dev
>
> _______________________________________________
> jboss-as7-dev mailing list
> jboss-as7-dev(a)lists.jboss.org
>
https://lists.jboss.org/mailman/listinfo/jboss-as7-dev