Distinguish Between Network Lag Time and Server Load
When
servers are busy, requests take a longer time to handle. Most of the
time, the client simply waits longer. But sometimes, when servers are
very busy, a request will simply time out, and an instance of
RemoteException
will be thrown. In this latter case, retry logic turns out to be
fairly painful: if the server is too busy and cannot handle
additional requests, the last thing in the world the client should do
is send the request again, especially if the request
isn’t very important, or can wait awhile.
One way to deal with this is to use what I call the bouncer pattern. The idea is to define a new subclass of
Exception, called ServerIsBusy,
add it to all the remote methods, and then throw instances of
ServerIsBusy whenever the server is too busy to
handle additional requests.
In the simplest implementation, the server simply keeps track of the
number of pending requests and throws an instance of
ServerIsBusy whenever there are too many pending
requests, as in the following implementation of the
Bouncer
class:
public class Bouncer { private static final int MAX_NUMBER_OF_REQUESTS = 73; private static in CURRENT_NUMBER_OF_REQUESTS; private static ServerIsBusy REUSABLE_EXCEPTION = new ServerIsBusy( ); public synchronized static void checkNumberOfRequestsLimit throws ServerIsBusy { if (MAX_NUMBER_OF_REQUESTS == CURRENT_NUMBER_OF_REQUESTS ) { throw REUSABLE_EXCEPTION; } CURRENT_NUMBER_OF_REQUESTS++; } public synchronized static ...