wood burning stoves 2.0*
The moose likes EJB and other Java EE Technologies and the fly likes EJB3.0 & calling remote interface. Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login


Win a copy of OCM Java EE 6 Enterprise Architect Exam Guide this week in the OCMJEA forum!
JavaRanch » Java Forums » Java » EJB and other Java EE Technologies
Bookmark "EJB3.0 & calling remote interface." Watch "EJB3.0 & calling remote interface." New topic
Author

EJB3.0 & calling remote interface.

Kevin P Smith
Ranch Hand

Joined: Feb 18, 2005
Posts: 362
Hi guys, me again!

After several attempts at using deployment descriptors for my sample EJB3.0 app I have decided to go the other route (as recommended to me by someone here a few days ago) and chosen Annotations!

From what I have found I think I've done it correct. The only problem is the presentation level (JSPs / Servlets for now) can not see the EJB Module classes. I can import them in the Servlet, but when executing the app I get a:-

Exception: javax.naming.NamingException: ejb ref resolution error for remote business interfacecom.myproject.sample1.SampleRemote [Root exception is java.lang.ClassNotFoundException: com.myproject.sample1.SampleRemote]

Ideally I want to deploy the WAR and EJB Jar as separate apps, because long term I'm thinking of having them on separate machines.

I have deployed this to a Sun Java WebApp 9.0 Server

So basically I need to know how to call a EJB (using Remote Interface) from a Servlet within a separate App?



Once again, many thanks for any help.
[ October 15, 2007: Message edited by: Keith Seller ]
Shailesh Kini
Ranch Hand

Joined: Oct 17, 2001
Posts: 153
Hello Keith,

You should be able to get the remote reference to your EJB in the servlet using @EJB annotation. Please refer to this link below.

web page


Shailesh Kini.
Kevin P Smith
Ranch Hand

Joined: Feb 18, 2005
Posts: 362
Nope, sorry.

I think it's because as I say, I am running the EJB in a separate JAR file to the Client WAR file.

ejb_client.war - JSP, Servlets
ejb_module.jar - EJBs

Kevin P Smith
Ranch Hand

Joined: Feb 18, 2005
Posts: 362
Just to add to this, I read in TheServerSide forums a thread with someone having the same problem as me and it was usggested that WAR files can not call EJBs from separate JARS!

Is this true? I find it very hard to believe because that surely defeats the entire point of the Remote Interface!!!

They suggested copying the EJB jar (ejb_module.jar in my case) or at least it's interfaces into a new JAR file which is then copied into the lib folder of the WAR file. This seems like madness! Surely if I do that, I might as well have all the classes under the same WAR/JAR and forget Remote Interfacing?

Taken from theserverside.com
-----------------------------

So a WAR in the same EAR of an EJB-jar can see automatically the EJB-jar classes/interfaces (this is also common behaviour since EJB 2.0). WARs in different EARs can't.

There are several workarounds. But first of all, you need to package the EJB "client" classes (interfaces, VOs etc.) into a separate JAR (let's call it "ejb-client.jar"). The possibilities are:

1. (I dislike this) You can put this ejb-client.jar in the server classpath, by editing the "startWebLogic.bat" file (curiously, there is no "lib/ext" folder in WLS8);

2. You can copy this ejb-client.jar into the WEB-INF/lib folder of each web application (I think BEA recommends this procedure);

3. You can try to fiddle with the application manifest file Class-Path entry, inserting a path like "../EJBEAR.ear/ejb-jar.jar"), therefore putting the EJBs original JAR in the client application classloader (there is no need of an ejb-client.jar then). This is a bit too low level, and it is hard to figure out the correct Class-Path entry;

[ October 16, 2007: Message edited by: Keith Seller ]
Kevin P Smith
Ranch Hand

Joined: Feb 18, 2005
Posts: 362
just to add some more to this (again).

i have tried what I think the above was suggesting, which is create another JAR file fir the EJB Interfaces and imported this into the Client WAR WEB-INF/lib folder.

I have deployed both the EJB jar and Client war files again and tried running the app.

The problem is,as soon as I make a call to a Remote Iterface Method i get the following error:

[#|2007-10-16T14:07:36.173+0100|SEVERE|sun-appserver-pe9.0|javax.enterprise.system.container.web|_ThreadID=12;_ThreadName=httpWorkerThread-8080-0;_RequestID=27abee96-8da0-487d-81a1-26788c38a6b7;|StandardWrapperValve[SampleServlet]: Servlet.service() for servlet SampleServlet threw exception
java.lang.NullPointerException
at com.myproject.servlets.SampleServlet.doPost(SampleServlet.java:23)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:727)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:820)
at org.apache.catalina.core.ApplicationFilterChain.servletService(ApplicationFilterChain.java:397)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:278)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:566)
at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:536)
at org.apache.catalina.core.StandardContextValve.invokeInternal(StandardContextValve.java:240)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:179)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:566)
at com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:73)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:182)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:566)
at com.sun.enterprise.web.VirtualServerPipeline.invoke(VirtualServerPipeline.java:120)
at org.apache.catalina.core.ContainerBase.invoke(ContainerBase.java:939)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:137)
at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:566)
at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:536)
at org.apache.catalina.core.ContainerBase.invoke(ContainerBase.java:939)
at org.apache.coyote.tomcat5.CoyoteAdapter.service(CoyoteAdapter.java:231)
at com.sun.enterprise.web.connector.grizzly.ProcessorTask.invokeAdapter(ProcessorTask.java:667)
at com.sun.enterprise.web.connector.grizzly.ProcessorTask.processNonBlocked(ProcessorTask.java:574)
at com.sun.enterprise.web.connector.grizzly.ProcessorTask.process(ProcessorTask.java:844)
at com.sun.enterprise.web.connector.grizzly.ReadTask.executeProcessorTask(ReadTask.java:287)
at com.sun.enterprise.web.connector.grizzly.ReadTask.doTask(ReadTask.java:212)
at com.sun.enterprise.web.connector.grizzly.TaskBase.run(TaskBase.java:252)
at com.sun.enterprise.web.connector.grizzly.WorkerThread.run(WorkerThread.java:75)


So something is still obviously wrong.

Also how would the remote Interface on the WAR know where the EJB Bean is under the JAR?

Cheers
Shailesh Kini
Ranch Hand

Joined: Oct 17, 2001
Posts: 153
Hello Keith,

Please refer to this link -> Remote EJB
Kevin P Smith
Ranch Hand

Joined: Feb 18, 2005
Posts: 362
Got it working, I now have a war file calling EJBs from a jar file (for now on the same WebApp) but looking at the properties I just change the hostname/port if it's on a different machine. It was this bit of code under GlassFish EJB FAQs that sorted it.

Properties props = new Properties();
props.setProperty("java.naming.factory.initial", "com.sun.enterprise.naming.SerialInitContextFactory");
props.setProperty("java.naming.factory.url.pkgs", "com.sun.enterprise.naming");
props.setProperty("java.naming.factory.state", "com.sun.corba.ee.impl.presentation.rmi.JNDIStateFactoryImpl");

// optional. Defaults to localhost. Only needed if web server is running
// on a different host than the appserver
props.setProperty("org.omg.CORBA.ORBInitialHost", "localhost");

// optional. Defaults to 3700. Only needed if target orb port is not 3700.
props.setProperty("org.omg.CORBA.ORBInitialPort", "3700");
Anand Kumar Singh
Greenhorn

Joined: Oct 18, 2007
Posts: 22
If you want to deploy the WAR and EJB Jar as separate apps separate machines, then all EJB call will be Remote Call , in this case @EJB annotaction will not work.Write Jndi lookup call for remote interface in WAR application which will act as delegare , will gave you remote object , by this object you can call EJb Bean methods in your servlet.



Bean CODE:
-----------------
@Stateless
@RemoteBinding(jndiBinding = "MeterInfoDAORemote")
@LocalBinding(jndiBinding = "MeterInfoDAOLocal")
public class MeterInfoDAOEJB implements MeterInfoDAORemote, MeterInfoDAOLocal {
------
---
-
}

Client CODE:
-------------------

public class MeterInfoDelegatet{

public MeterInfoDAOLocal meterInfoLocal;

public static MeterInfoDAOLocal getMeterInfoDAO(){
try {
Properties properties = new Properties();
properties.put("java.naming.factory.initial",
"org.jnp.interfaces.NamingContextFactory");
properties.put("java.naming.factory.url.pkgs",
"=org.jboss.namingrg.jnp.interfaces");
properties.put("java.naming.provider.url", "jnp://localhost:1099");

Context ctx = new InitialContext(properties);
meterInfoLocal= (MeterInfoDAOLocal) ctx.lookup("MeterInfoDAOLocal");

// call business method using meterInfoLocal object

} catch (NamingException ne) {
// log.error("Naming Exception Encountered : "+ne);
}

return meterInfoLocal;

}


SCJP 5, SCWCD 5, SCBCD 5,
SCEA 5,
OCUP Fundamental,
OCUP Intermediate,
OCUP Advanced,
IBM Certified Solution Designer - Object Oriented Analysis and Design, vUML 2
 
I agree. Here's the link: http://aspose.com/file-tools
 
subject: EJB3.0 & calling remote interface.