Invalid EJB 1.
package com.foo.ejb;To fix it, just rename
import java.util.Properties;
import javax.annotation.PostConstruct;
import javax.ejb.Stateless;
@Stateless
public class InvalidBean1 implements HelloRemote {
@PostConstruct
private void init() {
System.out.println("InvalidBean1 PostConstruct method called.");
}
public void init(Properties props) {
System.out.println("InvalidBean1 public init(Properties) method, not a PostConstruct method.");
}
init(Properties)
to init2(Properties)
, and make sure init
method is not overloaded in the current class.Invalid EJB 2.
import javax.interceptor.AroundInvoke;To fix it, just rename
import javax.interceptor.InvocationContext;
@Stateless
public class InvalidBean2 implements HelloRemote {
@AroundInvoke
private Object intercept(InvocationContext inv)
throws Exception {
System.out.println("InvalidBean2 AroundInvoke method called.");
return inv.proceed();
}
public void intercept(Properties props) {
System.out.println("InvalidBean2 public intercept(Properties) method, not an AroundInvoke method.");
}
}
intercept(Properties)
to intercept2(Properties)
, and make sure intercept
method is not overloaded in the current class.Invalid interceptor class.
import javax.interceptor.InvocationContext;To fix it, just rename
import javax.interceptor.AroundInvoke;
public class InvalidInterceptor {
@AroundInvoke
private Object intercept(InvocationContext inv)
throws Exception {
System.out.println("InvalidInterceptor AroundInvoke method called.");
return inv.proceed();
}
public void intercept(Properties props) {
System.out.println("InvalidInterceptor public intercept(Properties) method, not an AroundInvoke method.");
}
}
intercept(Properties)
to intercept2(Properties)
, and make sure intercept
method is not overloaded in the current class.What will happen with these invalid apps? Since these overloaded methods are legal in java, so your apps will be able to build, maybe even deploy successfully. But when the EJB is instantiated, EJB container looks for a lifecycle or interceptor method only by name. It may or may not get the correct method, depending on container implementation, operation systems, and other unknown factors.
With JavaEE SDK 5/Glassfish/Sun Java System Application Server 9 on Sparc Solaris 10 , I was able to deploy and run my app successfully, and the correct lifecycle method is found and invoked. With the same appserver on Windows, accessing the EJB will always fail with the following error:
[#|2006-06-23T10:07:11.291-0400|INFO|sun-appserver-pe9.0|javax.enterprise.system.container.ejb|_ThreadID=16;_ThreadName=p: thread-pool-1; w: 3;|EJB5070: Exception creating stateless session bean : [{0}]It means on Windows, the appserver always gets the wrong, unannotated method by its overloaded name.
java.lang.IllegalArgumentException: wrong number of arguments
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at com.sun.ejb.containers.interceptors.BeanCallbackInterceptor$1.run(InterceptorManager.java:601)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.ejb.containers.interceptors.BeanCallbackInterceptor.intercept(InterceptorManager.java:595)
at com.sun.ejb.containers.interceptors.CallbackChainImpl.invokeNext(InterceptorManager.java:448)
at com.sun.ejb.containers.interceptors.InterceptorManager.intercept(InterceptorManager.java:204)
at com.sun.ejb.containers.StatelessSessionContainer.createStatelessEJB(StatelessSessionContainer.java:546)
at com.sun.ejb.containers.StatelessSessionContainer.access$100(StatelessSessionContainer.java:96)
at com.sun.ejb.containers.StatelessSessionContainer$SessionContextFactory.create(StatelessSessionContainer.java:746)
at com.sun.ejb.containers.util.pool.NonBlockingPool.getObject(NonBlockingPool.java:186)
at com.sun.ejb.containers.StatelessSessionContainer._getContext(StatelessSessionContainer.java:469)
at com.sun.ejb.containers.BaseContainer.getContext(BaseContainer.java:1566)
at com.sun.ejb.containers.BaseContainer.preInvoke(BaseContainer.java:1148)
at com.sun.ejb.containers.EJBObjectInvocationHandler.invoke(EJBObjectInvocationHandler.java:189)
at com.sun.ejb.containers.EJBObjectInvocationHandlerDelegate.invoke(EJBObjectInvocationHandlerDelegate.java:110)
...
This is a bug in the application, not in the appserver. Unfortunately, it's a restriction we have to live with.
Continue to part 2 and part 3
Tags: