如何解决取消抖动的用户输入上的竞争条件
How to resolve race conditions on debounced user input?
例如,假设一个页面返回基于去抖动用户文本的搜索结果。
如何解释端点具有高度可变延迟的情况,在这种情况下,第二次调用可以在第一次调用之前返回。
例如
用户正在键入"books and movies",键上弹出500毫秒
用户在中间稍微停顿一下,因此字符串为"books",这会触发搜索调用。
用户继续键入并完成,触发带有"图书和电影"的第二次调用
第二个调用首先返回,根据"图书和电影"填充列表。
然后,被延迟的第一个调用返回,并根据"books"重新呈现列表。
用户只看到"books"并感到困惑。
解决这个问题的可靠方法是通过一个按钮手动触发呼叫。虽然我想避免这种情况,所以我增加了弹跳,但我想知道是否有更好的方法。
我们假设您使用jQuery进行ajax调用。
一种解决方案是使用池化系统:基本上是一个包含ajax请求的数组。每次发出新的请求时,都会中止池中的所有请求。因此,您要确保最后一个请求将是唯一一个将结束的请求。
以下是池的实现:
jQuery.xhrPool = [];
jQuery.xhrPool.abortAll = function () {
jQuery(this).each(function (idx, jqXHR) {
jqXHR.abort();
});
jQuery.xhrPool.length = 0;
};
下面是一个关于如何将其与GitHub的"搜索存储库API"一起使用的示例(https://developer.github.com/v3/search/#search-存储库):
jQuery.xhrPool = [];
jQuery.xhrPool.abortAll = function () {
jQuery(this).each(function (idx, jqXHR) {
jqXHR.abort();
});
jQuery.xhrPool.length = 0;
};
$(document).ready(function(){
$("#SearchField").autocomplete({
source: function( request, response ) {
// First we abort all other request
jQuery.xhrPool.abortAll();
$.ajax({
url: "https://api.github.com/search/repositories",
method: "get",
dataType: "jsonp",
data: {
q: request.term
},
beforeSend: function (jqXHR) {
// Before sending the request we add it to the pool.
jQuery.xhrPool.push(jqXHR);
},
success: function(data) {
var items = new Array();
for(var i=0;i<data.data.items.length;i++)
{
items.push(data.data.items[i].name);
}
response(items);
}
});
},
minLength: 3,
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.11.4/jquery-ui.min.js"></script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/jqueryui/1.11.4/jquery-ui.css" >
<input type="text" id="SearchField" />
Javascript同步工作,因此如果您正确编写代码,就不可能出现竞争条件。
我猜您正在使用ajax(ajax应该是异步的,永远不要使用同步,一旦进行同步,就无法返回)来获取查询结果。你可能正在使用这样的代码:
var req=new XMLHttpRequest();
req.onreadystatechange=function(){
if (req.readyState==4){
if (req.status==200){
// Your callback here which shows autocomplete suggestions maybe?
}
}
}
抓住那个req
变量。因此,一旦你做了一个新的请求,你可以简单地丢弃旧的请求,比如:
req.onreadystatechange=null;
您也可以中止ajax请求,如:
req.abort();
相关文章:
- 使用javascript搜索具有用户输入的数组
- React Native通过Navigator将用户输入数据传递到选项卡栏IOS中的组件
- 如何使用JavaScript中的用户输入创建序列/序列
- 如何在用户输入时实例化数组
- 如何从客户端的数组中获取用户输入和返回值
- 如何在用户输入 javascript 时更改值
- 如何从多个不同的html页面获得mongodb文档的用户输入
- PayPal按钮是否有一个简单的选项,其中金额基于一些用户输入
- 从表单中获取用户输入执行计算(操作顺序)并输出回该表单
- 我确实有一个表单,如果用户输入了输入,它应该检查否定或空的输入框,并抛出一条警告消息
- 如果用户输入的长度小于最小长度,则显示错误消息
- 随机生成用户输入
- 如果图像标记是用javascript编写的,并且需要用户输入,那么图像不会随页面加载吗
- Javascript:使用用户输入搜索数组
- 根据用户输入的数字生成文本框
- 如何通过获取用户输入和使用按钮来运行JavaScript函数
- 使用用户输入修改链接
- 如何解决取消抖动的用户输入上的竞争条件
- 从用户输入中制作数组动画,如打字机(javascript)
- 如何在视图中保存用户输入内容,并在离开页面时对控制器进行后期调用