2010-11-07 7 views
16

Ho un bean senza stato con le transazioni gestite dal bean, e un metodo come questo:Come si propagherà UserTransaction?

@Stateless 
@TransactionManagement(TransactionManagementType.BEAN) 
public class ... { 

    @Resource 
    private UserTransaction ut; 
    @EJB 
    private OtherStatelessBeanLocal other; 

    public void invokeSomeMethods() 
     ut.begin(); 
     ... 

     // invoke other bean's methods here. 
     other.method(); 

     ... 
     ut.commit(); 

    } 

} 

Così come il UserTransaction propagano per il fagiolo OtherStatelessBeanLocal?

+0

bene non, giusto? –

risposta

32

L'oggetto UserTransaction è un oggetto fornito dal contenitore che include l'accesso alle chiamate API che il contenitore utilizza internamente, in particolare javax.transaction.TransactionManager. Il TransactionManager ha metodi come begin, commit, rollback e javax.transaction.Transaction getTransaction()

Sotto le coperte, il TransactionManager userà una tecnica ThreadLocal o simile per monitorare lo stato di transazione attuale con il filo. ThreadLocals sono oggetti molto semplici che possono essere facilmente descritti come static HashMap che utilizza il nome del thread come chiave e un oggetto di tua scelta come valore. Finché si rimane nello stesso thread, è possibile ottenere l'oggetto da qualsiasi punto della catena di chiamata. Questo è uno dei motivi per cui non è consentito avviare thread in un ambiente Java EE.

La propagazione della sicurezza funziona in modo simile, così come le ricerche JNDI che indicano magicamente lo spazio dei nomi del modulo o del componente java:comp/env del modulo o del componente giusto. In conclusione, non è possibile implementare un server di app senza ThreadLocals. La propagazione suona più attiva di quanto non sia, quando in realtà è semplicemente l'atto di non lasciare il filo in modo che il contenitore e tutti i soggetti coinvolti possano ancora trovare la tua "roba".

Indietro nei termini di gestione delle transazioni, l'oggetto che un TransactionManager terrà traccia nella sua ThreadLocal implementerà in genere (direttamente o indirettamente) entrambe le interfacce Transaction e TransactionSynchronizationRegistry. Tra queste due interfacce, il contenitore ha tutti i ganci necessari per tenere traccia di DataSource s, EntityManager s e altre risorse nella transazione corrente per conto dell'utente. Queste interfacce consentono inoltre al contenitore di offrire callback come SessionSynchronization, nonché i mezzi per eseguire altre operazioni per conto dell'utente al completamento della transazione, ad esempio il flushing/closing di EntityManager, l'invio di messaggi JMS in sospeso e la persistenza di tutti i timer creati dall'app nel corso della transazione.

+2

La risposta perfetta.+1 –

+0

In realtà no, perché non applica la conoscenza alla domanda posta. – Thomas

0

Per EJB3 si definisce normalmente la propagazione delle transazioni con l'annotazione @TransactionAttribute.

L'attributo di transazione di default per tutte le applicazioni EJB 3.0 è necessario:

Se un client richiama il metodo del bean mentre il client è associata a un contesto di transazione, il contenitore richiama il metodo del bean nel client di contesto di transazione.

del doc per tipo di transazione sono qui: http://download.oracle.com/javaee/6/api/javax/ejb/TransactionAttributeType.html

N.B. Il contesto di persistenza e la propagazione delle transazioni in genere avvengono insieme ma non sempre: attenzione. Ad esempio, i bean di sessione con stato possono avere un extended persistence context.

+0

Nota nel caso del contesto di persistenza ESTESA, il contesto di persistenza è ancora esclusivamente associato alla transazione e non disponibile per altre transazioni in virtù del fatto che non appena il bean di proprietà @ è coinvolto nella transazione, non è consentito lasciare il transazione fino a quando non esegue il commit o il rollback. Tutte le richieste su quel bean @Stateful al di fuori della transazione attenderanno la durata di @AccessTimeout prima di lanciare infine una qualche forma di ConcurrentAccessException. –

4

Sulla base di specifica EJB, non è possibile passare un contesto di transazione da un fagiolo (in questo caso la classe principale ...) con la transazione programmatico in un altro bean (in questo caso, altro) utilizzando un'operazione programmatica