Monday, January 24, 2011

"Thread.Sleep" Implementation for Javascript

In Javascript, we dont have Thread.sleep functionality. Which leads to lot of inconvenience while designing a complex JS based application.
I faced a similar kind of situation in last week. I had a very bulk data in Javascript and had to do lot of calculation/processing with those data. But most of all browser started complaining after certain point saying "Stop Running This script?".
After googeling, I found that this is because browser feels that javascript fall into endless loop and this is just a preventive warning. But in production environment, such popup costs me a lot! And I need to get rid of it.
One probable solution was to put "break" in execution and make browsers happy. If I can put a break in my long execution, browser will not see any 'endless loops'!

But.. Javascript doesn't have Thread.sleep! We just have setTimeout function. So I played with this function , and implemented "Thread.sleep" kind of functionality which can solve my problem.
Here is a sampole code for this implementation:
  <script>
    BatchProcessor = function(op, interval){
        var ref = this;
        var batchIndex = 0;
        var _args = new Array();
        this.addBatch = function(value){
            _args.push(value);
        }
        this.startJob = function(){
            if(batchIndex<_args.length)    //This is first time. Run it without interval.
                op(_args[batchIndex++]);
            if(batchIndex<_args.length)
                setTimeout(function(){ref.startJob(ref);},interval);
            else
                alert('its done');
        }
    }
   
    //Your actual Worker!
    doSomeWork = function(values){
        var startValue = values[0];
        var endValue = values[1];
        //Do some work for this batch!
        alert('Started from:'+startValue+'  Ended with:'+endValue);
    }
   
    //Some testing..
    var myProcessor = new BatchProcessor(doSomeWork,1000);
    myProcessor.addBatch(new Array(0,1000));
    myProcessor.addBatch(new Array(1001,2000));
    myProcessor.addBatch(new Array(2001,3000));
    myProcessor.startJob();
  </script>


This script has divided a long task - to process 3000 records into 3 small chunks which can be executed with 1 sec of interval.
Depending upon requirement one can modify this script to stack the function itself.