在客户下拉框里输入「北京」,敲了五个字符发了五次请求,最后停在 bj 的结果上,列表里全是拼音匹配的无关项。乍看像缓存或者权限的锅,追下去往往不是。

let timer, seq = 0;
input.addEventListener('input', e => {
  clearTimeout(timer);
  const kw = e.target.value.trim();
  if (kw.length < 2) return;
  timer = setTimeout(async () => {
    const id = ++seq;
    const list = await search(kw);
    if (id === seq) render(list);
  }, 300);
});

追下去是这么回事:input 事件每次都直接发请求,没有防抖,也没有丢弃过期响应。先发的慢请求后到,把后发的快结果覆盖了,看起来就是越搜越乱。

「远程搜索防抖」相关的验证我通常做两遍,改完一次、隔天再看一次,确认不是临时生效。接口问题先分清是没发出去、发出去了没收到,还是收到了处理失败。

偶发问题先统计频率,一小时几次和一天一次,查法完全不同。改完顺手把文档补一句,省得下次自己重新推一遍。

具体做法是,输入停 300 毫秒再发请求,输入变化时清掉上一个定时器;给每次请求打序号,回调只认最新那个序号的结果;少于两个字符或关键词没变就直接跳过。

验收就看一点,连续输入五个字符只发出一次请求,列表结果与最后的关键词一致。

作者 9823189