情況
我有一個需要~X seconds決議的異步函式。持續時間取決于網路延遲,因此無法預測。該功能由用戶輸入觸發(想想“將當前表單值保存到服務器”)
我想防止此功能同時運行多次。
我還想對函式的呼叫“排隊”,以便在合適的時候呼叫。
問題
(A) 這個“耐心”異步函式的概念是否有一個術語。
(B) 是否有一種工具(類似于debounce)可以采用異步功能并將其變成“耐心”功能。
uj5u.com熱心網友回復:
該答案基于@danh的答案。
該函式queuePromise接受一個回傳承諾的函式。每當呼叫佇列函式時,它的承諾都會鏈接到前一次呼叫的承諾。
@danh 的答案與此之間的主要區別在于,排隊的函式可以接收引數,而承諾是一個簡單的let變數。
const queuePromise = fn => {
let pending = Promise.resolve()
return (...args) => {
const func = () => fn(...args)
return pending = pending.then(func, func)
}
}
const demo = name => id => {
console.log(`started ${name} ${id}`)
return new Promise((resolve, reject) => {
setTimeout(() => {
// example of a failed promise in the middle of the chain
if(id === 2) reject(`failed ${name} ${id}`)
else resolve(`ended ${name} ${id}`)
}, 500)
})
}
const patientFoo = queuePromise(demo('foo'))
patientFoo(1).then(console.log).catch(console.log)
patientFoo(2).then(console.log).catch(console.log)
patientFoo(3).then(console.log).catch(console.log)
const patientBar = queuePromise(demo('bar'))
patientBar(1).then(console.log).catch(console.log)
patientBar(2).then(console.log).catch(console.log)
patientBar(3).then(console.log).catch(console.log)
uj5u.com熱心網友回復:
下面,makePatient將給定函式包裝在另一個函式中,該函式僅在解決先前呼叫鏈后才呼叫它。
function pause() {
return new Promise(resolve => {
setTimeout(resolve, 1000)
})
}
function foo(str) {
return pause().then(() => console.log(str));
}
function bar(str) {
return pause().then(() => console.log(str));
}
function makePatient(fn) {
let pending = Promise.resolve();
return (...params) => {
return pending = pending.then(() => fn(...params)).catch(console.log);
}
}
let patientFoo = makePatient(foo);
let patientBar = makePatient(bar);
patientFoo('foo');
patientFoo('foo');
patientFoo('foo');
patientBar('bar');
patientBar('bar').finally(() => console.log("all the bars are closed"));
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/419462.html
標籤:
上一篇:vue組件不顯示計算屬性
下一篇:尋找JS異步生成器的批處理方法
