2017-10-19 78 views
0

我想测试ajax请求是否相同,因此可以中止或采取其他警报措施?在刷新时避免完全相同的客户端ajax请求

实际上,客户端可以通过几个表单元素来改变请求,然后点击刷新按钮。

我已经做了很差的尝试来捕捉相同的请求。需要保持定时器刷新功能。

<script type="text/javascript" src="http://code.jquery.com/jquery-latest.js"></script> 

<script type="text/javascript"> 

    var current_request_id = 0; 
    var currentRequest = null; 
    var lastSuccessfulRequest = null; 

    function refreshTable() { 
     $('#select').html('Loading'); 
     window.clearTimeout(timer); 

     //MY CATCH FOR DUPLICATE REQUEST NEEDS WORK 
     if (lastSuccessfulRequest == currentRequest) 
     { 
      //currentRequest.abort(); 
      alert('Duplicate query submitted. Please update query before resubmission.'); 
     } 

     var data = { 
      "hide_blanks": $("#hide_blanks").prop('checked'), 
      "hide_disabled": $("#hide_disabled").prop('checked'), 
     }; 

     json_data = JSON.stringify(data); 

     current_request_id++; 
     currentRequest = $.ajax({ 
      url: "/calendar_table", 
      method: "POST", 
      data: {'data': json_data}, 
      request_id: current_request_id, 
      beforeSend : function(){ 
       if(currentRequest != null) { 
        currentRequest.abort(); 
       } 
      }, 
      success: function(response) { 
       if (this.request_id == current_request_id) { 
        $("#job_table").html(response); 
        $("#error_panel").hide(); 
        setFixedTableHeader(); 
       } 
      }, 
      error: function(xhr) { 
       if (this.request_id == current_request_id) { 
        $("#error_panel").show().html("Error " + xhr.status + ": " + xhr.statusText + "<br/>" + xhr.responseText.replace(/(?:\r\n|\r|\n)/g, "<br/>")); 
       } 
      }, 
      complete: function(response) { 
       if (this.request_id == current_request_id) { 
        $("#select").html("Refresh"); 
        window.clearTimeout(timer); 
        stopRefreshTable(); 
        window.refreshTableTimer = window.setTimeout(refreshTable, 10000); 

        lastSuccessfulRequest = currentRequest; 
       } 
      } 
     }); 
    } 




    //TIMER STUFF TO refreshTable() 
    //THIS SECTION WORKS FINE 
    var startDate = new Date(); 
    var endDate = new Date(); 
    var timer = new Date(); 
    function startRefreshTable() { 
     if(!window.refreshTableTimer) { 
      window.refreshTableTimer = window.setTimeout(refreshTable, 0); 
     } 
    } 
    function stopRefreshTable() { 
     if(window.refreshTableTimer) { 
      self.clearTimeout(window.refreshTableTimer); 
     } 
     window.refreshTableTimer = null; 
    } 
    function resetActive(){ 
     clearTimeout(activityTimeout); 
     activityTimeout = setTimeout(inActive, 300000); 
     startRefreshTable(); 
    } 

    function inActive(){ 
     stopRefreshTable(); 
    } 
    var activityTimeout = setTimeout(inActive, 300000); 
    $(document).bind('mousemove click keypress', function(){resetActive()}); 

</script> 


<input type="checkbox" name="hide_disabled" id="hide_disabled" onchange="refreshTable()">Hide disabled task<br> 
<br><br> 
<button id="select" type="button" onclick="refreshTable();">Refresh</button> 
+1

“是相同的”......与......完全相同?之前的请求?以前的任何请求?还有别的吗?从什么意义上来说是相同的来自同一个用户?完全相同的参数?相同的标题?请澄清您的确切要求。你现在这样做的方式很幼稚。 $ .ajax返回一个Deferred对象,你无法用任何有意义的方式与另一个对象进行真正的“平等”比较,也不会告诉你任何关于请求的内容 - 它是为你添加回调而设计的,以便处理响应。一旦你澄清了你的意思,我们可以找到一个更好的方法来做到这一点 – ADyson

+1

另外一个方面说明:jQuery的'.bind'被jQuery 1.7中的'.on'取代,现在完全弃用。应该没有理由继续使用它,或者更糟糕的是,将其用于新代码。 http://api.jquery.com/bind/ – ADyson

+0

当然,有一种方法可以在不发布一百行代码的情况下表达您的观点。阅读并遵循[mcve]。 – Tomalak

回答

0

我会使用的.ajaxSend.ajaxSuccess全球处理的权力。

我们将使用ajaxSuccess来存储缓存,并且ajaxSend会先尝试读取它,如果成功,它将立即触发请求的成功处理程序,并中止即将完成的请求。否则它会让它成为...

var ajax_cache = {}; 
function cache_key(settings){ 
    //Produce a unique key from settings object; 
    return settings.url+'///'+JSON.encode(settings.data); 
} 
$(document).ajaxSuccess(function(event,xhr,settings,data){ 
    ajax_cache[cache_key(settings)] = {data:data}; 
    // Store other useful properties like current timestamp to be able to prune old cache maybe? 
}); 
$(document.ajaxSend(function(event,xhr,settings){ 
    if(ajax_cache[cache_key(settings)]){ 
     //Add checks for cache age maybe? 
     //Add check for nocache setting to be able to override it? 
     xhr.abort(); 
     settings.success(ajax_cache[cache_key(settings)].data); 
    } 
}); 

我在这里证明是一个非常幼稚的,但功能的方法来你的问题。这有利于使你可以拥有的每一个Ajax调用都能工作,而无需改变它们。您需要在此基础上进行构建以考虑失败,并确保从缓存命中发出的请求流产不会被分派以中止处理程序。

0

这里一个有效的选项是JSON.Stringify()对象并比较字符串。如果对象相同,则生成的序列化字符串应该相同。

如果您直接从响应中使用已经过JSON化的字符串,则可能会导致轻微的差异,因此您必须通过测试进行双重检查。

此外,如果您试图弄清楚如何在跨页加载中使用它,请使用localStorage.setItem("lastSuccessfulRequest", lastSuccessfulRequest)localStorage.getItem("lastSuccessfulRequest")。 (如果没有,请告诉我,我将删除此内容。)