Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
HomeAnnouncementsWhite Papers
Discussion GroupsFirst AidDatabasesJavaBeansGUIJava 3DVirtual MachineCORBASecurityToolsGeneral
Java DirectoryOpen Source ProjectsSample Book ChaptersUser GroupsWeb Resources
Related Topics
Databases.NETMore Topics ...

Java Forum / General / March 2006

Tip: Looking for answers? Try searching our database.

Non-blocking notification mechanism via RMI

Thread view: 
kittyhawk - 29 Mar 2006 00:36 GMT
Hi folks,

I want to trigger a method on some remote object via RMI to process
some data. But the client invoking the method should not block while
the remote object is processing. Instead, I would like the remote
object to notify the client as soon as the job is done.

Of course, one could hand over the client's reference so that the
remote object could invoke a client's method. But, first, the server
will block as long as the client is doing something in its called
method, and second, the client has to be accessible via RMI, too. The
latter fact even causes that the method is actually processed on the
server instead of on the client side. So, any System.out.println() will
show up on the server, not on the client.
I cann't span separate threads to do the callbacks. That's set. I have
also looked into some design patterns, but didn't find anything
suitable for RMI problems at first glance.

All I want is a simple notification mechanism. Non-blocking on the
client, non-blocking on the server. Just a ping from the server to the
client, like "Hey, job is done. Fetch your result."

Thanks in advance for any help!

Thomas
Alex Molochnikov - 29 Mar 2006 01:30 GMT
> Hi folks,
>
> I want to trigger a method on some remote object via RMI to process
> some data. But the client invoking the method should not block while
> the remote object is processing. Instead, I would like the remote
> object to notify the client as soon as the job is done.

Launch a new thread on the server from the method called by the client, and
return immediately. Any processing to be done by the request from the client
should be done in that new thread.

> Of course, one could hand over the client's reference so that the
> remote object could invoke a client's method. But, first, the server
> will block as long as the client is doing something in its called
> method,

Same deal on the client: start a new thread and return.

> ...and second, the client has to be accessible via RMI, too. The
> latter fact even causes that the method is actually processed on the
> server instead of on the client side. So, any System.out.println() will
> show up on the server, not on the client.

Any method called on the client's objects (i.e. those that exist in the
client's address space) will be executed on the client. What makes you think
that you are seeing the client's System.out stream on the server?

> I cann't span separate threads to do the callbacks. That's set.

And the reason is?

If you want the server to send a message to the client not as a response to
the client's call, but originating from the server, and want to use RMI for
this, the callback is your only choice. Essentially, you want to turn your
client into an improvised server, that will listen to the "real" server's
call - this is exactly what the callback mechanism does.

> I have also looked into some design patterns, but didn't
> find anything suitable for RMI problems at first glance.
>
> All I want is a simple notification mechanism. Non-blocking on the
> client, non-blocking on the server. Just a ping from the server to the
> client, like "Hey, job is done. Fetch your result."

If you want to stay out of J2EE, the RMI can do this, but only if you are
willing/can use threads. Otherwise, you could try JMS - its asynchronous
messaging is suited perfectly for your task.

AM
kittyhawk - 29 Mar 2006 10:42 GMT
Alex Molochnikov schrieb:

> > Hi folks,
> >
[quoted text clipped - 45 lines]
>
> AM
I simply can't use a separate thread for each client task because my
component must also work on devices with limited memory and weak
processing power. Even the reduced overhead by using a thread pool is
way too much. All I can use is one thread within the remote object,
i.e. the server.
But I will look into JMS. Probably it will solve my headache...
Leon Lambert - 29 Mar 2006 12:51 GMT
You don't need one thread per client. You just need 1 worker thread.
Have it pull requests from a synchronized queue. Have the RMI calls post
to the queue in a synchronized fashion. This is a pretty common way of
handling problems like this whether they are local or remote.

Hope this helps
Leon Lambert

> Alex Molochnikov schrieb:
>
[quoted text clipped - 48 lines]
> i.e. the server.
> But I will look into JMS. Probably it will solve my headache...
kittyhawk - 29 Mar 2006 13:30 GMT
That makes sense. But how do I notify the client when the job is done?
My first idea:
Let the client call stub.someMethod(xzy, this) where xyz is the actual
argument needed for the computation, and this is the refrenze to the
client object.
As soon as the job is done, the remote object could then call
((MyClientClass).processingJob.getReferenzeToClientObj()).notiy()

This callback has to go through RMI back to the client. So, the client
has to implement the Remote interface. Am I right? When I did this, it
worked, but any System.out.println() showed up on the remote side
instead of on the client side. Additionally, the remote object blocks
until the notify() method returns. Since I cann't assume a "frindly"
client, the notify method coul never return. Even if a use a separat
for each callback, the thread will wait as long as notify() is
executed. If notify() calculates a while(true){}, a bunch of waiting
threads will eat up my resources.

Probably I should say it more clearly: The problem is that I cannot
assume any time bound. Neither on the server side, nor on the client.
The server object has to be accessible via RMI, the client don't. A
worker thread on the server side fetching job for a queue is okay. But
I still don't see how the remote object notifies the client without
blocking until notify() returns.

Leon Lambert schrieb:

> You don't need one thread per client. You just need 1 worker thread.
> Have it pull requests from a synchronized queue. Have the RMI calls post
[quoted text clipped - 56 lines]
> > i.e. the server.
> > But I will look into JMS. Probably it will solve my headache...
Leon Lambert - 30 Mar 2006 13:03 GMT
Its fairly easy to create a callback mechanism. Doing a google search
should find lots of examples. I'll paste in some snippits of somthing i
did that hopefully points you in the right direction. The remote
software would provide the callback object to the server. If you are
saying that you don't want to use a remote callback mechanism then there
really isn't much you can do but block. Another approach is to have the
server post answers to a client specific queue and have the client
periodically remotely dequeue answers. This is not as clean as callbacks
 but is a bit simpler to implement.

Following is the interface to me callback object
interface EventCallbackInterface extends Remote
{
/**
    This will tell the client that the server is still alive
*    @throws RemoteException will be thrown if a network error occurs
*/
    public void deadManCheck() throws RemoteException;
/**
    An object has changes has occured
*    @param index is an unique event identifier
*    @param reason is the reason for the change
*    @param record is which record changed
*    @throws RemoteException will be thrown if a networking error occurs
*/
    public void handleChange(int index,int reason,RtdrRecordData
record) throws RemoteException;
}

Following is the class the implements it.
/**
*    This class provides a callback mechanism from an rtdr server to the client
*    @author  Leon Lambert
*    @version 1.00, 08/01/98
*    @since   JDK1.2
*/
class EventCallbackImpl extends UnicastRemoteObject implements
EventCallbackInterface
{
/**
*    Rtdr that is managing this connection
*/
    RemoteRtdr        remoteRtdr;

/**
*    Allocate an instance to manage callbacks to this client
*    @param    remoteRtdr is an interface to the remote rtdr
*    @exception    RemoteException will be thrown for RMI errors
*/
    public EventCallbackImpl(RemoteRtdr remoteRtdr) throws RemoteException
    {
        this.remoteRtdr = remoteRtdr;
    }

/**
*    The is called to provide a deadman point. This will fail on the server
if i'm dead.
*    @exception    RemoteException will be thrown for RMI errors
*/
    public    void            deadManCheck() throws RemoteException
    {
    }

/**
* Callback point to handle changes that this client has subscribed to
*    @param    index for the event reference
*    @param    reason for the change
*    @param    record is the one with the change
*    @exception    RemoteException will be thrown for RMI errors
*/
public    void    handleChange(int index,int reason,RtdrRecordData record)
throws RemoteException
{
    try
    {
        RemoteOHCRefNum   remoteOHCRefNum = remoteRtdr.findEvent(index);
        remoteOHCRefNum.handleChange(record,reason);
    }
    catch (Exception ex)
    {
    }
    }
}

> That makes sense. But how do I notify the client when the job is done?
> My first idea:
[quoted text clipped - 83 lines]
>>> i.e. the server.
>>> But I will look into JMS. Probably it will solve my headache...
EJP - 29 Mar 2006 07:09 GMT
> I want to trigger a method on some remote object via RMI to process
> some data. But the client invoking the method should not block while
[quoted text clipped - 8 lines]
> server instead of on the client side. So, any System.out.println() will
> show up on the server, not on the client.

That would only happen if you supplied a Serializable client callback so
its code executed at the server. You should be supplying an *exported
remote object* as the callback (e.g. extends UnicastRemoteObject), just
like the server.

> I cann't span separate threads to do the callbacks. That's set.

You don't have to do that to execute the callback, but you do have to
start a new thread at the server to handle the actual *task* so that the
remote method implementation can return immediately to the client. That
thread will also execute the server side of the callback when it is done.

However I would question why you (a) must use RMI *and* (b) must have
this fully asynchronous model. The requirements are clearly in conflict.
You can do it but it's not a great fit.
Chris Uppal - 29 Mar 2006 09:11 GMT
> All I want is a simple notification mechanism. Non-blocking on the
> client, non-blocking on the server. Just a ping from the server to the
> client, like "Hey, job is done. Fetch your result."

If you don't want remote METHOD CALL semantics, why are you using RMI at all ?

   -- chris
Patrick May - 29 Mar 2006 21:07 GMT
> I want to trigger a method on some remote object via RMI to process
> some data. But the client invoking the method should not block while
> the remote object is processing. Instead, I would like the remote
> object to notify the client as soon as the job is done.
[ . . . ]
> All I want is a simple notification mechanism. Non-blocking on the
> client, non-blocking on the server. Just a ping from the server to
> the client, like "Hey, job is done. Fetch your result."

    A couple of people have mentioned JMS elsethread; that may be a
good fit for your requirements.  Another Java technology to consider
is Jini (http://www.jini.org).  What you seem to want to do could be
done with a simple master-worker pattern via a JavaSpace.

Regards,

Patrick

------------------------------------------------------------------------
S P Engineering, Inc.    | The experts in large scale distributed OO
                        | systems design and implementation.
         pjm@spe.com    | (C++, Java, Common Lisp, Jini, CORBA, UML)


Free Magazines

Get these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...

Oracle MagazineNetwork ComputingComputer WorldBio-IT WorldeWeekInformation WeekInfosecurity
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2008 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.