stateful session bean with both remote and local interfaces
The JEE Tutorial says "it is possible for an enterprise bean to allow both remote and local access".
But when calling my stateful bean ShoppingCart which has both remote and local interfaces I get 2 stateful session ShoppingCart beans created when I only want 1.
My code for the client is as follows:
@Stateful
public class ShoppingClientFacadeEJBBean implements ShoppingClientFacadeEJBRemote {
@EJB
private ShoppingCartEJBRemote shoppingCartEJBBeanRemote;
@EJB
private ShoppingCartEJBLocal shoppingCartEJBBeanLocal;
Is there a solution to this problem?
Thanks.
# 1
Hi,
I don't think it's possible. It's pretty rare (if at all useable) to specify remote and local interfaces in a single EJB as your example has showed it may incur troubles with instances.
As described in the Java EE 5.0 Specification p. 62 (EE.5.2.2Sharing of Environment Entries):
In general, lookups of objects in the JNDI java: namespace are required to return a new instance of the requested object every time.
with some exception described later, but they do not refer to EJBs.
The spec notes that:
A new instance of the requested object must be returned on each lookup.
and annotations are just shortcuts for looking up resources in a component's naming context (java:comp/env) by yourself and therefore must obey the rules cited above.
Why do you want to access the same bean locally and remotely? If you can get at it locally wouldn't it obviate the need for the remote intf?
Jacek
# 2
Hi Jacek,
Thanks for your comments on the spec - I'll look it up. Was it like this under J2EE ( I don't remember it being so) ?
I'm building a version of the Petstore 1.3.2 in JEE and with the web tier accessing the EJB tier remotely (the Petstore only does it locally).
As I'm sure you know, the Petstore uses an event driven architecture with a ShoppingController, ShoppingClientFacade and ShoppingCart - all stateful session beans. Updates to the cart are performed by an event passed from the web tier to the Controller, which invokes a coresponding action handler, which gets a reference to the Shoppingcart from the ShoppingClientFacade and does its work. For performance reasons the ShoppingClientFacade and ShoppingCart should be accessed through local interfaces (this is what the blueprints recommends).
However to get the cart contents the web tier in the Petstore retrieves the interface to the ShoppingClientFacade from the controller and from there a reference to ShoppingCart. As in my version the web tier is remote I need remote interfaces for these. Hence you can see why I want both remote and local interfaces to the facade and the cart.
This architecture is a direct copy of the Petstore 1.3.2 (which I really like). It seem strange that I can't do it. I'm sure that there must be a solution without doing everything with only remote or local interfaces.
Any thoughts or ideas would be much appreciated.
Peter
# 3
Hi,I haven't taken a look at Java Pet Store 2.0 Reference Application, Early Access yet, but there might be the answer for your questions. Go and get it from https://blueprints.dev.java.net/petstore/.I'm looking forward to hearing from you if that helped.Jacek
# 4
Hi Jacek,
Thanks for your thoughts. I took a look at the Petstore 2.0 - it doesn't use EJB session beans and seems to be a completely different architecture from earlier versions. So that's not a lot of help.
Interestingly one aspect it demonstrates is how to use the new persistence outside of the ejb containier - some of the entities are mapped directly to pages via the faces-config page.
This is a diversion to the problem however. Has EJB 3 removed our ability to control the creation of EJBs so that we can't now retrieve both a local and a remote reference to a stateful session bean ?
Any other ideas would be appreciated.
Peter