防抖的应用:短时间内需要请求多个资源合并成一个请求发送
题目:请求合并:短时间内需要请求多个资源合并成一个请求发送
防抖可以理解为:多次触发事件后,事件处理函数只执行一次
// 首先有一个接口其请求路径为 /path
// query有一个id参数支持传一个或者多个id
// /path?id=1
// /path?id=1,2,3
// /path?id=1,2
// 返回内容格式为(假设请求的query是 id=1,2)
const demoRes = {
1:{
data:{}
},
2:{
data:{}
}
}
// request的构成
request({
url:'/path',
query:{
id:''
}
})
// 下面是使用场景实现,每个方法回调最终拿到的是自己需要的内容
getArticle(3).then(res=>{})
getArticle(4).then(res=>{})
getArticle(5).then(res=>{})
getArticle(6).then(res=>{})
// 实现这个getArticle方法
// 新构建一个对象来在外部分发请求
class HandPosts {
constructor() {
this.promise = new Promise((res, rej) => {
this.resolve = res;
this.reject = rej;
});
}
}
// 使用这个类来获取我们的任务队列 以及处理请求
class InitTaskRunner {
constructor() {
this.tasks = [];
this.params = ''
}
// 塞入队列
createTask(id) {
// 有一个请求即将被发送
const deferred = new HandPosts();
// 暂时保存这个请求
this.tasks.push({ id, deferred });
if(this.tasks.length>1){
this.params = `${this.params},${id}`
}
else{
this.params = id
}
// 分发返回结果
return deferred.promise;
}
request(params){
let {query:{id:ids}} = params
ids = ids.split(",")
let res = {}
ids.forEach((e)=>{
res[e] = {data:{value:e}}
})
// 返回数据
return new Promise((resolve,reject) =>{
setTimeout(resolve(res),500)
})
}
// 开始处理
async execute() {
const tasks = this.tasks;
console.log(tasks)
// 清空所有请求
this.tasks = [];
try {
this.request({ url:'/path',query:{
id:this.params
}}).then(res => {
tasks.forEach(i => {
let id = i.id
let result = res[id]
i.deferred.resolve(result)
})
})
} catch(e) {
// 请求失败 全部reject
tasks.forEach(task => task.deferred.reject(e));
}
}
}
let taskRunner = new InitTaskRunner();
let timer;
function getArticle(id) {
//防抖
clearTimeout(timer);
timer = setTimeout(() => taskRunner.execute(), 300);
// 分发请求
return taskRunner.createTask(id);
}
// 模拟请求,改为发送入参
function getValue(set) {
return new Promise((resolve, reject) => {
setTimeout(() => {
resolve(Array.from(set).map((id) => ({ id, value: id + '' })));
}, 300);
});
}
getArticle(1).then((res) => {
console.log(res , 1);
});
getArticle(6).then((res) => {
console.log(res ,6);
});
getArticle(7).then((res) => {
console.log(res ,7);
});
getArticle(8).then((res) => {
console.log(res , 8);
});