Some unit tests I'm writing are showing a problem with nested SFSBs where the
IsLocalInterceptor doesn't treat a call from a parent SFSB to a nested SFSB as local,
but Remoting optimizes it locally. This leads to an exception in the transaction
propagation handling. Key points are highlighted:
Caused by: java.lang.RuntimeException: cannot import a transaction context when a
transaction is already associated with the thread
| at
org.jboss.aspects.tx.TxPropagationInterceptor.invoke(TxPropagationInterceptor.java:62)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.stateful.StatefulInstanceInterceptor.invoke(StatefulInstanceInterceptor.java:93)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.remoting.ReplicantsManagerInterceptor.invoke(ReplicantsManagerInterceptor.java:51)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.security.AuthenticationInterceptor.invoke(AuthenticationInterceptor.java:77)
| at
org.jboss.ejb3.security.Ejb3AuthenticationInterceptor.invoke(Ejb3AuthenticationInterceptor.java:105)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.ENCPropagationInterceptor.invoke(ENCPropagationInterceptor.java:46)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.asynchronous.AsynchronousInterceptor.invoke(AsynchronousInterceptor.java:106)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.stateful.StatefulContainer.dynamicInvoke(StatefulContainer.java:333)
| at org.jboss.aop.Dispatcher.invoke(Dispatcher.java:106)
| at
org.jboss.aspects.remoting.AOPRemotingInvocationHandler.invoke(AOPRemotingInvocationHandler.java:82)
| at org.jboss.remoting.ServerInvoker.invoke(ServerInvoker.java:1008)
| at
org.jboss.remoting.transport.local.LocalClientInvoker.invoke(LocalClientInvoker.java:98)
| at org.jboss.remoting.Client.invoke(Client.java:589)
| at org.jboss.remoting.Client.invoke(Client.java:581)
| at
org.jboss.aspects.remoting.InvokeRemoteInterceptor.invoke(InvokeRemoteInterceptor.java:62)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.remoting.ClusterChooserInterceptor.invoke(ClusterChooserInterceptor.java:77)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.tx.ClientTxPropagationInterceptor.invoke(ClientTxPropagationInterceptor.java:61)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.security.SecurityClientInterceptor.invoke(SecurityClientInterceptor.java:53)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at org.jboss.ejb3.remoting.IsLocalInterceptor.invoke(IsLocalInterceptor.java:85)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.stateful.StatefulClusteredProxy.invoke(StatefulClusteredProxy.java:105)
| at $Proxy110.increment(Unknown Source)
| at
org.jboss.ejb3.test.stateful.nested.base.ParentStatefulBean.increment(ParentStatefulBean.java:58)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeTarget(MethodInvocation.java:121)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:110)
| at
org.jboss.ejb3.interceptor.InvocationContextImpl.proceed(InvocationContextImpl.java:166)
| at
org.jboss.ejb3.interceptor.EJB3InterceptorsInterceptor.invoke(EJB3InterceptorsInterceptor.java:63)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.cache.StatefulReplicationInterceptor.invoke(StatefulReplicationInterceptor.java:51)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.entity.ExtendedPersistenceContextPropagationInterceptor.invoke(ExtendedPersistenceContextPropagationInterceptor.java:57)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.entity.TransactionScopedEntityManagerInterceptor.invoke(TransactionScopedEntityManagerInterceptor.java:54)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.AllowedOperationsInterceptor.invoke(AllowedOperationsInterceptor.java:47)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at org.jboss.aspects.tx.TxPolicy.invokeInOurTx(TxPolicy.java:79)
| at org.jboss.aspects.tx.TxInterceptor$Required.invoke(TxInterceptor.java:193)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.tx.TxPropagationInterceptor.invoke(TxPropagationInterceptor.java:76)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.stateful.StatefulInstanceInterceptor.invoke(StatefulInstanceInterceptor.java:93)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.remoting.ReplicantsManagerInterceptor.invoke(ReplicantsManagerInterceptor.java:51)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.aspects.security.AuthenticationInterceptor.invoke(AuthenticationInterceptor.java:77)
| at
org.jboss.ejb3.security.Ejb3AuthenticationInterceptor.invoke(Ejb3AuthenticationInterceptor.java:105)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.ENCPropagationInterceptor.invoke(ENCPropagationInterceptor.java:46)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.asynchronous.AsynchronousInterceptor.invoke(AsynchronousInterceptor.java:106)
| at org.jboss.aop.joinpoint.MethodInvocation.invokeNext(MethodInvocation.java:101)
| at
org.jboss.ejb3.stateful.StatefulContainer.dynamicInvoke(StatefulContainer.java:333)
| at org.jboss.aop.Dispatcher.invoke(Dispatcher.java:106)
| at
org.jboss.aspects.remoting.AOPRemotingInvocationHandler.invoke(AOPRemotingInvocationHandler.java:82)
| at org.jboss.remoting.ServerInvoker.invoke(ServerInvoker.java:1008)
| at org.jboss.remoting.ServerInvoker.invoke(ServerInvoker.java:857)
| at
org.jboss.remoting.transport.socket.ServerThread.processInvocation(ServerThread.java:454)
| at org.jboss.remoting.transport.socket.ServerThread.dorun(ServerThread.java:527)
| at org.jboss.remoting.transport.socket.ServerThread.run(ServerThread.java:261)
What happens here is the parent bean has an increment() method, which delegates to a
nested SFSB's increment() method. The nested bean is @Remote. For some reason the
IsLocalInterceptor is not recognizing it should invoke the call locally.
This happens in a unit test where I force the failover of the parent SFSB. This is done
with the standard trick of adding a server side interceptor that checks a condition and
if met throws GenericClusteringException. The stack trace above is *not* from the call
that fails over; that works fine. It's the next call to the parent, and is the first
call after failover that the parent delegates delegates to the nested bean.
What's really got me stumped is AFAICT IsLocalInterceptor and
AOPRemotingInvocationHandler are both dealing with Dispatcher using the same Invocation
and the same metadata. But when IsLocalInterceptor queries Dispatcher, it says the
container isn't registered, while when AOPRemotingInvocationHandler asks Dispatcher to
handle the invocation, it finds the container just fine.
Any thoughts???
View the original post :
http://www.jboss.com/index.html?module=bb&op=viewtopic&p=4014012#...
Reply to the post :
http://www.jboss.com/index.html?module=bb&op=posting&mode=reply&a...