4 回答
TA贡献1777条经验 获得超10个赞
创建一个函数,以确保仅使用惰性承诺对 id 发出一个请求。
const URL = 'whatever'
let idPromise // so lazy 🦥
const getId = async () => {
const response = await fetch(URL)
if (!response.ok) {
throw response
}
return (await response.json()).id
}
const initialise = () {
if (!idPromise) {
idPromise = getId()
}
return idPromise
}
// and assuming you're using a module system
export default initialise
现在,您所要做的就是在任何其他呼叫前面加上前缀,以获取ID,这只会发生一次initialise()
import initialise from 'path/to/initialise'
async function handleEvent(e) {
const id = await initialise()
// do stuff with the ID
}
TA贡献1803条经验 获得超3个赞
当前接受的响应依赖于全局变量,这并不理想。另一种选择是使用类。
class IDManager {
getId(URL) {
if (this.id) {
return this.id;
}
this.id = fetch(URL)
return this.id
}
}
然后,当您调用 时,您只需等待结果即可。如果之前未发出任何请求,则将发送网络请求。如果已经存在挂起的请求,则每次调用都将等待相同的结果。如果承诺已经解决,您将立即获得结果。getId
const idManager = new IDManager();
async function handleEvent() {
const id = await idManager.getId(URL);
// Do stuff with the ID.
}
TA贡献1798条经验 获得超3个赞
不清楚为什么你的函数被“e”参数化。我会用更直接的方式写它:
async function request(URL) {
let response = fetch(URL)
if (response.ok) {
let json = await response.json();
return json.id;
}
return false;
}
然后,如果您的呼叫顺序很重要,请逐个写下它们。如果没有,那么你可以使用Promise.all(Promise.allSettled maybe)一次运行它们。https://developer.mozilla.org/ru/docs/Web/JavaScript/Reference/Global_Objects/Promise/all
TA贡献1852条经验 获得超1个赞
事实证明,解决这个问题的方法与之前的答案略有不同。我想我会发布我最终如何使它工作。来自@phil和@vaelin的答案确实帮助我弄清楚了这一点。
这是我的解决方案...
class IDManager {
async fetchID (resolve,reject ) {
const response = await fetch( URL, { } ) ;
const id = await response.json() ;
resolve( id );
}
async getID() {
if ( this.id === undefined ) {
if ( this.promise === undefined ) {
var self = this;
this.promise = new Promise( this.fetchID ).then( function(id) { self.id = id;} );
}
await this.promise;
}
return this.id;
}
}
问题是等待获取getID调用需要几秒钟。在那段时间里,经常有多个调用getID,所有这些都启动了另一个获取。我通过将 fetch 和 response.json 调用包装在另一个立即创建的 promise 中来避免这种情况,从而避免了重复。
添加回答
举报