On Feb 21, 2007, at 12:24 AM, Guido Anzuoni wrote:

Craig L Russell <Craig.Russell <at> Sun.COM> writes:


Hi Guido,

Thanks for your comments.

On Feb 12, 2007, at 4:39 AM, Guido Anzuoni wrote:

when
it associate the PM with the transaction, but there could be
ordering issues
with other Synchronization objects referencing
the same PM.

I believe that this scenario is covered already in the specification.
The PM is responsible to call the user's registered Synchronization
instance during transaction completion. The proxy does not complicate
this existing usage.

Well, maybe it's too late, but, you know, thinking process might
take some time :)
I have some extra comments on closing PM in a JTA scenario.
You say that actually the real PM is closed by the afterCompletion
registered by the real PersistenceManager.
I disagree on this.
PersistenceManager outlives the transaction boundaries, either global or local.
You can have the following usage:
PersistenceManager pm = ...
UserTransaction ut = ...
ut.begin();
pm.makePersistent();
ut.commit();
...
ut.begin();
pm.makePersistent();
ut.commit();
..
pm.close();

I think this case doesn't need a proxy at all. The proxy is needed if your use case requires binding to a different pm each time, based on the existence of a container-managed transaction. If you want to manage the life cycle of the pm yourself, and manage transactions yourself, there is no need for a proxy.

In a proxy-based scenario the real PM has a lifecycle that is completely bound to the (global) transaction lifespan: it is created when the user requires
a PM the first time and is closed by the proxy upon completion
(Synchronization.afterCompletion on the JTA transaction).
This lead to the assumption that:
1. no PM (proxy) can be acquired without an open JTA transaction

Actually, I've updated the spec such that in the case of using the proxy without a JTA transaction, a PM will be created that does its work outside a transaction.

2. Synchronization.afterCompletion of the proxy should be called **after** any other Synchronization that might be registered by the real implementation on the JTA transaction itself (this is critical because JTA does not enforce any
ordering in Synchronization objects).

This is done by containers that implement javax.transaction.TransactionSynchronizationRegistry, a new feature of Java EE 5. JDO implementations that use non-TSR containers need to have a private contract with the container so that the proper ordering is done.

An alternative to guarantee that
the proxy Synchronization.afterCompletion is invoked after
any "finalization" actions performed by the PM, is to register the synchro on pm.currentTransaction(), but this would "consume" the only slot available.

We looked at allowing users to register multiple synchronizations with the JDO Transaction, but concluded that it would be a rare case where the synchronizations would truly be independent.

This would not be a big problem, because the real pm remains almost hidden
to the app (unless JDOHelper.getPersistenceManager(o) is called).

The current design does allow the user to get access to the "real PM" but I don't think that this is a major problem. Any code that deliberately bypasses the proxy usage by storing the real PM and using it out of scope will simply get a "PM has been closed" exception.

What I like is the JDO implementations being unaware of PersistenceManagerProxy,
so it is responsibility of the proxy to close the real pm.

Me too.

Craig

Guido.




Craig Russell
Architect, Sun Java Enterprise System http://java.sun.com/products/jdo
408 276-5638 mailto:[EMAIL PROTECTED]
P.S. A good JDO? O, Gasp!

Attachment: smime.p7s
Description: S/MIME cryptographic signature

Reply via email to