Main Menu

[Fwd: EJB remote communication between two applications within same
server]

You are here:

[Fwd: EJB remote communication between two applications within same
server]

October 21, 2008 - 05:49

Anonymous

Hi,

I have two enterprise applications (two ear's containing one ejb-jar
each) running in the same server. Now one bean of app1 should call a
method of a bean in app2.

I have created a bean (HelloBean) in app2 with a remote interface
(HelloRemote) implementing a method "public String sayHello()" and
annotated the interface with @Remote. The bean in app1 should call this
method, so I created a bean in app1 with a reference "private
HelloRemote helloRemote" and annotated the reference with @EJB. So far,
so good.

Thus my app1 now has a compiletime dependency to app2, because of the
interface "HelloRemote". When deploying the two ears into the server, I
get a ClassNotFoundException for this interface in app1. That seems to
be correct since applications are separated by different classloaders...

Now my question is, how to proceed in this case!? Do I have to duplicate
the remote interface so that the class file of this interface exists in
both ear's? And what should be done if the remote method should return a
custom class object? Is there a way of sharing classes between two
applications or has each common class to be duplicated? Or am I totally
wrong? ;-)

1. You can duplicate all the client view classes in both the ear files.
Client view classes include remote interface and its transitive closure.

2. Create a jar file called common.jar with all client view classes,
place it in domain_dir/lib/applibs. You don't have to package client
view classes in any of the ear files. While deploying both the apps, use
--libraries option like this:
'asadmin deploy --libraries=common.jar app1.ear'
'asadmin deploy --libraries=common.jar app2.ear'
I have not tried this myself, but I think this should work. Let us know
how it goes.

Option #2 will lead to sharing of classes.

Thanks,
Sahoo

Sebastian Hofmann wrote:
> Hi,
>
> I have two enterprise applications (two ear's containing one ejb-jar
> each) running in the same server. Now one bean of app1 should call a
> method of a bean in app2.
>
> I have created a bean (HelloBean) in app2 with a remote interface
> (HelloRemote) implementing a method "public String sayHello()" and
> annotated the interface with @Remote. The bean in app1 should call this
> method, so I created a bean in app1 with a reference "private
> HelloRemote helloRemote" and annotated the reference with @EJB. So far,
> so good.
>
> Thus my app1 now has a compiletime dependency to app2, because of the
> interface "HelloRemote". When deploying the two ears into the server, I
> get a ClassNotFoundException for this interface in app1. That seems to
> be correct since applications are separated by different classloaders...
>
> Now my question is, how to proceed in this case!? Do I have to duplicate
> the remote interface so that the class file of this interface exists in
> both ear's? And what should be done if the remote method should return a
> custom class object? Is there a way of sharing classes between two
> applications or has each common class to be duplicated? Or am I totally
> wrong? ;-)
>
> Thanks for advice...
> Sebastian
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@glassfish.dev.java.net
> For additional commands, e-mail: users-help@glassfish.dev.java.net
>
>

On 10/21/08 05:49, Sebastian Hofmann wrote:
> Hi,
>
> I have two enterprise applications (two ear's containing one ejb-jar
> each) running in the same server. Now one bean of app1 should call a
> method of a bean in app2.
>
> I have created a bean (HelloBean) in app2 with a remote interface
> (HelloRemote) implementing a method "public String sayHello()" and
> annotated the interface with @Remote. The bean in app1 should call this
> method, so I created a bean in app1 with a reference "private
> HelloRemote helloRemote" and annotated the reference with @EJB. So far,
> so good.
>
> Thus my app1 now has a compiletime dependency to app2, because of the
> interface "HelloRemote". When deploying the two ears into the server, I
> get a ClassNotFoundException for this interface in app1. That seems to
> be correct since applications are separated by different classloaders...
>
> Now my question is, how to proceed in this case!? Do I have to duplicate
> the remote interface so that the class file of this interface exists in
> both ear's? And what should be done if the remote method should return a
> custom class object? Is there a way of sharing classes between two
> applications or has each common class to be duplicated? Or am I totally
> wrong? ;-)
>
> Thanks for advice...
> Sebastian
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscribe@glassfish.dev.java.net
> For additional commands, e-mail: users-help@glassfish.dev.java.net
>
>

Yes, you should replicate the HelloRemote interface within the caller's application (app1). The remote interface serves as the contract between the caller and callee. This allows you to run app1 anywhere you want, either within the same JVM as the callee or a different JVM, without any change in semantics. This is also referred to as location transparency. It's one of the main benefits of the Remote EJB view.

App1 has a compile-time dependency on the remote interface, not on app2. For example, you could have deployed two different enterprise beans that both expose the HelloRemote interface. App1 could work with either of them and that selection could be made at deployment time or even as late as as runtime.

Any other classes needed for parameter types or return types of the remote interface methods are also part of the client contract, so they would need to be packaged within the caller as well.

I understand the benefit of this solution. Would it be possible to put the remote interface and the classes needed for parameters and return types in a separate jar and deploy it with each ear? Or has the interface to be placed inside an ejb-jar?

That way there might be a versionable artifact containing the "contract". I think this should be a better way than simply duplicating the interface, because one does not have to keep them in sync!?