wood burning stoves 2.0*
The moose likes EJB Certification (SCBCD/OCPJBCD) and the fly likes Injecting a Stateful Session Bean into a servlet Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Certification » EJB Certification (SCBCD/OCPJBCD)
Bookmark "Injecting a Stateful Session Bean into a servlet" Watch "Injecting a Stateful Session Bean into a servlet" New topic
Author

Injecting a Stateful Session Bean into a servlet

Duran Harris
Ranch Hand

Joined: Nov 09, 2008
Posts: 598

Hi all,

I'm reading EJB3 in Action and I'm wondering how to use stateful beans from a web client like a servlet or JSP. I know that I can't inject it into an instance variable of the servlet,but I would just like to confirm the validity of the following :

Could I not just inject the stateful bean into a local variable of the doPost method?Aren't the local variables of the servlet thread-safe?

And I have another question regarding datasources and connections.I see in the EJB3 in Action examples they open and close java.sql.Connections with the @PostConstruct and @PreDestroy methods respectively...Isn't this very wasteful???Considering that every single bean in the pool has it's own connection?Or am I missing something here?

Thanks...



===>SCJP 1.5(72%)<===
==>SCWCD1.5(76%)<===
Tom Kowalski
Ranch Hand

Joined: Feb 17, 2009
Posts: 72
You can't use Dependency Injection (@) in the methods. So this won't work. Servlet's local variables are thread safe, so if you want to use session bean, you should use lookup method from the InitialContext.

It all depends of the type of the bean, if you have got stateful bean you shouldn't use DI, but if the beans are stateless you can use it and don't worry about thread safe.

And now your second question. Again it depends of the bean type. If the bean is stateless there will be just a few (probably, but it ofcourse depends on the configuration) beans in the pool, and all the 'users' will use them - these few beans . When they will be created (@PostConstruct) - the data connections will be open, and thanks to this, everybody will use it. Stateless beans are not created very othen. It would be very bad if you would open connection in the business method - then, every request would open the connection - this would be inefficient.


SCJP, SCWCD, OCUP
Duran Harris
Ranch Hand

Joined: Nov 09, 2008
Posts: 598

Okay thank you.

Also I am having a strange issue with glassfish.I have a web project and an EJB 3 project inside the same EAR.I can't seem to access my bean via the Local interface.Only the remote interface.I have also tried using ejb-local-ref in the xml but this didn't help.Either way I get the following stack trace:

[#|2009-12-13T19:33:50.875+0200|SEVERE|sun-appserver9.1|javax.enterprise.system.tools.deployment|_ThreadID=43;_ThreadName=Thread-2957;_RequestID=4716fad7-35a5-4e30-8387-c8c12bdce3c2;|Exception occured in J2EEC Phasejava.lang.RuntimeException: Cannot resolve reference Unresolved Ejb-Ref servlets.TestEJBServlet/hiyaTwo@jndi: @null@ejb.HelloBeanLocal@Session@null
com.sun.enterprise.deployment.backend.IASDeploymentException: Error loading deployment descriptors for module [WebLocal] -- Cannot resolve reference Unresolved Ejb-Ref servlets.TestEJBServlet/hiyaTwo@jndi: @null@ejb.HelloBeanLocal@Session@null
at com.sun.enterprise.deployment.backend.Deployer.loadDescriptors(Deployer.java:390)
at com.sun.enterprise.deployment.backend.ModuleDeployer.loadDescriptors(ModuleDeployer.java:423)
at com.sun.enterprise.deployment.backend.WebModuleDeployer.deploy(WebModuleDeployer.java:157)
at com.sun.enterprise.deployment.backend.ModuleDeployer.doRequestFinish(ModuleDeployer.java:179)
at com.sun.enterprise.deployment.phasing.J2EECPhase.runPhase(J2EECPhase.java:191)
at com.sun.enterprise.deployment.phasing.DeploymentPhase.executePhase(DeploymentPhase.java:108)
at com.sun.enterprise.deployment.phasing.PEDeploymentService.executePhases(PEDeploymentService.java:919)
at com.sun.enterprise.deployment.phasing.PEDeploymentService.deploy(PEDeploymentService.java:279)
at com.sun.enterprise.deployment.phasing.PEDeploymentService.deploy(PEDeploymentService.java:788)
at com.sun.enterprise.management.deploy.DeployThread.deploy(DeployThread.java:187)
at com.sun.enterprise.management.deploy.DeployThread.run(DeployThread.java:223)
Caused by: java.lang.RuntimeException: Cannot resolve reference Unresolved Ejb-Ref servlets.TestEJBServlet/hiyaTwo@jndi: @null@ejb.HelloBeanLocal@Session@null
at com.sun.enterprise.deployment.util.EjbBundleValidator.accept(EjbBundleValidator.java:430)
at com.sun.enterprise.deployment.WebBundleDescriptor.visit(WebBundleDescriptor.java:1406)
at com.sun.enterprise.deployment.archivist.WebArchivist.validate(WebArchivist.java:188)
at com.sun.enterprise.deployment.archivist.ApplicationArchivist.openArchive(ApplicationArchivist.java:790)
at com.sun.enterprise.deployment.archivist.ApplicationArchivist.openArchive(ApplicationArchivist.java:744)
at com.sun.enterprise.deployment.backend.Deployer.loadDescriptors(Deployer.java:349)
... 10 more
|#]

And my code looks like this:


It's strange because it won't even deploy if I try inject the Local interface.As soon as I comment out the Local injection it runs fine though.Can anyone tell me where I'm going wrong?
Tom Kowalski
Ranch Hand

Joined: Feb 17, 2009
Posts: 72
Are you sure that the session beans and the servlet are parts of the same application? (In other words, have you made EE Application, where you have got: ejb part (session beans), and war part (servlet)?

P.S Injecting session beans is one of the most stressful things at the beginning of EJB learning. Really.
Duran Harris
Ranch Hand

Joined: Nov 09, 2008
Posts: 598

Don't know if this proves it:
If I right-click the EAR and select Properties->Build->Packaging I can see both the web project and the ejb-project.It says "Location in archive: /".ie. both are located in the root of the EAR

Although there is a missing project there(one that I deleted before)I'm still very new to Netbeans...

PS. I think the most stressful thing is figuring out what the attributes on the annotations do(ie. beanName,mappedName,beanInterface,name)I tried multiple combinations today but the only way I could get the stuff working is by not using any of the attributes...Also the JMS/messaging chapters in EJB 3 in Action are baffling me,gonna do transactions first and then come back to them.
Tom Kowalski
Ranch Hand

Joined: Feb 17, 2009
Posts: 72
Yeah, they are in this same application. Strange. Sorry, I won't be able to help you.

Anyway, I agree with you, beans attributes (name, mappedName etc.) are quite stupid :P. It's really hard to find anywhere good information about how to use them properly (from A to Z). Here is a webpage which can be quite useful while you are learning about it: https://glassfish.dev.java.net/javaee5/ejb/EJB_FAQ.html#SessionBeanGlobalJNDINameAssignment
Duran Harris
Ranch Hand

Joined: Nov 09, 2008
Posts: 598

Thanks!!
Duran Harris
Ranch Hand

Joined: Nov 09, 2008
Posts: 598

But wait a minute..why is everyone telling me that the ejb-jar and the WAR must be in the same EAR??
I just checked the specs and it defines 'local access' as a client running in the same container as the bean...
See.....
Use of a session bean’s local interface(s) entails the collocation of the local client and the session. The
local client of an enterprise bean must be collocated in the same container as the bean. The local client
view is not location-independent.


But then in another section it states in the same JVM....That explains it....


So then why doesn't my local interface work!!I only have one instance of Glassfish..!Do you think my Glassfish has it's webserver and ejb container running on different JVM's on my machine??
 
With a little knowledge, a cast iron skillet is non-stick and lasts a lifetime.
 
subject: Injecting a Stateful Session Bean into a servlet
 
Similar Threads
InitialContext Lookup returns the same Stateful Session Bean Reference everytime ...
EJB usage ... some basic knowledge gathering
EJB Dependency Injection problem
DI doubt in Session Bean
using stateful beans (Java EE5) so that new instances become created in the right way