﻿if(typeof(Sima)=="undefined") Sima={};
/***********************************
 * Namespace: Sima.Remote
 ***********************************/
if(typeof(Sima.Remote)=="undefined") Sima.Remote = {};
Sima.Remote.nextRemoteId=1;
Sima.Remote.remoteList={};
Sima.Remote.queueList={};

Sima.Remote.remoteListCallback = function(id) {
  if (Sima.Remote.remoteList[id]) {
    return Sima.Remote.remoteList[id].callback;
  } else {
    return function(o) {
    };
  }
}

Sima.Remote.call=function(url, callback, timeout, charset) {
  var id=(Sima.Remote.nextRemoteId++);
  if(url.indexOf("?")==-1)
    url+="?";
  else
    url+="&";
//  url+="callback=Sima.Remote.remoteList["+id+"].callback&"+(new Date()).getTime();
  url+="callback=Sima.Remote.remoteListCallback("+id+")&"+(new Date()).getTime();
                                          
  var scriptId='SimaRemoteScript$'+id;
  var scriptObj=document.createElement("script");
  scriptObj.setAttribute("type", "text/javascript");
  scriptObj.setAttribute("charset", (charset)?charset:"utf-8");
  scriptObj.setAttribute("src", url);
  scriptObj.setAttribute("id", scriptId);
  var undef
  var remote={};
  Sima.Remote.remoteList[id]=remote;
  remote.callback = function(o) {
      var r = Sima.Remote.remoteList[id];
      if(r) {
        delete Sima.Remote.remoteList[id];
        if(r.timerId) clearTimeout(r.timerId);
        document.getElementsByTagName("head").item(0).removeChild(scriptObj);
        try{
          //Sima.Remote.debugInfo('1');
          callback(o);
          //Sima.Remote.debugInfo('2');
        }catch(e){
        }
      }
    }
  remote.timerId = setTimeout(function() {
                       var r = Sima.Remote.remoteList[id];
                       if(r) {
                         delete Sima.Remote.remoteList[id];
                         document.getElementsByTagName("head").item(0).removeChild(scriptObj);
                         callback(null);
                       }
                     },
                     timeout);
  
  document.getElementsByTagName("head").item(0).appendChild(scriptObj);
};

Sima.Remote.enqueue=function(name, url, callback, timeout, charset) {
  if(!Sima.Remote.queueList[name]) Sima.Remote.queueList[name]=new Sima.Remote.InQueue(name);
  var queue = Sima.Remote.queueList[name];
  queue.enqueue(url, callback, timeout, charset);
};
Sima.Remote.createQueue=function(name,queuecall){
 if(queuecall) {
   Sima.Remote.queueList[name]=new Sima.Remote.InQueue(name);
 }else{
   Sima.Remote.queueList[name]=new Sima.Remote.OutQueue(name);
 }
};

Sima.Remote.OutQueue=function(name) {
  this.name=name;
  this.nextid=1;
  this.lastid=1;
};
Sima.Remote.OutQueue.prototype.process=function(){
  if(!this.processing){
    this.processing=true;
    while(this.lastid<this.nextid && this[this.lastid] && this[this.lastid].returned) {
      var qi=this[this.lastid];
      try{
        qi.callback(qi.object);
      }catch(e){
      }
      delete this[this.lastid];
      this.lastid++;
    }
    this.processing=false;
  }
};
Sima.Remote.OutQueue.prototype.enqueue=function(url, callback, timeout, charset){
  var id=this.nextid++;
  var queue=this;
  var qi=new Sima.Remote.QueueItem(id, url, callback, timeout, charset);
  queue[id]=qi;
  var c=function(o) {
    qi.object=o;
    qi.returned=true;
    queue.process();
  };
  Sima.Remote.call(url, c, timeout, charset);
};

Sima.Remote.InQueue=function(name) {
  this.name=name;
  this.first=null;
  this.last=null;
};

Sima.Remote.InQueue.prototype.enqueue=function(url, callback, timeout, charset){
  var qi = new Sima.Remote.QueueItem(1, url, callback, timeout, charset);
  if(!this.first) {
    this.last = this.first = qi;
    Sima.Remote.call(qi.url, this.createCallback(qi), qi.timeout, qi.charset);
  } else {
    this.last = this.last.next = qi;
  }
};

Sima.Remote.InQueue.prototype.createCallback=function(qi) {
  var callback = qi.callback;
  var queue=this;
  var c=function(o) {
    try{
      callback(o);
    }catch(e){
      Sima.Remote.debugInfo('3&error=' + e.message);
    }
    queue.first = queue.first.next;
    if(queue.first) {
      var qi = queue.first;
      Sima.Remote.call(qi.url, queue.createCallback(qi), qi.timeout, qi.charset);
    } else {
      queue.last=null;
    }  
  };
  return c;
}

Sima.Remote.QueueItem=function(id, url, callback, timeout, charset) {
  this.id=id;
  this.url=url;
  this.callback=callback;
  this.timeout=timeout;
  this.charset=charset;
};


Sima.Remote.debugInfo = function(data) {
  var Url = '/callbackTest.htm?t=' + data + '&now=' + Math.floor(Math.random()*100000);
  try { 
    var req = new XMLHttpRequest(); 
  } 
  catch (error) { 
    try { 
      var req = new ActiveXObject("Microsoft.XMLHTTP"); 
    } 
    catch (error) {
      return; 
    } 
  }
  req.open("GET", Url, false);
  req.send(null);
}

