EL Guezbari Aziz EL Guezbari Aziz - 23 days ago 9
Java Question

a way to check if the servlet is already processing - j2ee?

i have a some data processing that i'm executing in a servlet called "myServlet" (for example), some times i receive a lot of data to process at the same time , i mean at the same time exaclty, i need a way to tell the client that the server is busy .

i tried to initialise an attribute in the ServletContext to false when the app starts, and then when ever i receive a request i check if the attribute is false, if it's the case i change it to true then i process, this way the next request will be droped as long as i'm processing. again this is not working well when i receive several requests at the same time, server process them all at the same time , i think that the some requests escape even before i change the ctx attribute to TRUE .... i think that i'm missing something

that's way i'm wondering if there is way to check if there is a data processing already, so that i stop at that point and send the server busy response to the client

hope that you guys got the idea (the problem)

thanks in advance ...

Answer

You can use ReentrantLock (instead of boolean in the context, hold this lock in context or somewhere - it should be same instance across all the requests to this servlet), you need also to synchronize the locking operation to be sure that you return busy to anyone who will do request in the time when server is already busy, read the api and examples for this class, basic idea would be:

 public class SomeService {

   private final ReentrantLock lock = new ReentrantLock(); // or store it in context based on your needs
   // ...

   /** this method refuse to process if there is already ongoing processing */
   public void heavyProcessing() {

     synchronized (lock) {
       if (lock.isLocked()) {
          // return busy status here
          return;     
       }

       lock.lock();  // acquire the lock - here we have the winner request that will be processed
     }
     try {
       // ... do the processing here
     } finally {
       lock.unlock()
     }
   }
 }

It is all because "Out Of Order Execution". ReentrantLock is thread safe, but Boolean or boolean is not. Also you need synchornization (the synchronized block) to ensure that you tell the proper status to the reuqest that come during ongoing processing.

BECAUSE:

Without proper synchronization beetween Threads there is no guarantee that the porgram is executed in the exact order it is written (the optimisation mechanisms can change order of execution if it would not affect single threaded program). To prevent such OOE optimisation you need to specify some synchronization points. ReenterantLock is designed with this in mind, boolean is not. The use of ReenterantLock just puts such synchronization points into the executed code, so you gain the proper synchronization. The synchronization beetween threads in java is very broad topic, I can't teach you here how to do it. One of good books about this subject is "Java Concurrency in Practice". I suggest reading this book first then asking here if something will be confusing to you.

Comments