为什么我的代码应该暂停但仍要执行?

问题描述 投票:0回答:1

我有一个API,该API在每分钟可以发送到该API提供的任何端点的请求数(50 /分钟)方面受到限制。

在下面的代码部分中,我以URL作为属性过滤对象orders,每个具有提供数据的URL的对象都应存储在我的successfullResponsesapp.component.ts中。

Promise.all(
orders.map(order => this.api.getURL(order.resource_url).catch(() => null))
).then(responses => {
  const successfulResponses = responses.filter(response => response != null)
  for(let data of successfulResponses) {
       // some other requests should be sent with data here
  }
});

有超过50个orders要检查,但是我一次只能检查最多50个orders,因此我尝试在服务中处理它。我设置了第一个请求发送的第一个日期。之后,我将新请求的日期与第一个请求的日期进行比较。如果相差超过60,则将当前日期设置为新日期,然后再次将maxReq设置为50。如果小于60,则检查是否还有请求,如果是,我发送请求,如果不是,我只是等待一分钟:

sleep(ms){
    return new Promise(resolve => setTimeout(resolve, ms));
}
async getURL(){
      if(!this.date){
        let date = new Date();
        this.date = date;
      }
      if((new Date().getSeconds() - this.date.getSeconds() > 60 )){
        this.maxReq = 50;
        this.date = new Date();
        return this.http.get(url, this.httpOptions).toPromise();
      } else {
        if(this.maxReq > 0){
          this.maxReq -= 1;
          return this.http.get(url, this.httpOptions).toPromise();
        } else{
          console.log("wait");
         await this.sleep(60*1000);
         this.maxReq = 50;
         this.date = new Date();
         return this.http.get(url, this.httpOptions).toPromise();
        }
      }
  }

但是app.component.ts中的代码不等待功能getURL(),而是对请求执行更多代码,这导致我发送“太多的请求太快”的问题。我该怎么办?

javascript angular typescript api asynchronous
1个回答
0
投票

我在尝试将诺言与多个异步功能结合使用时遇到了类似的问题。忘记是很容易的事情,但是为了使它们全部等待,您必须在调用有问题的函数的根行上使用await。

我不确定,但是我的假设是您的await this.sleep(60*1000);行的确在等待超时发生,但是在执行此操作的同时,称为getURL()的代码正在执行其余的行,因为它在await之前没有.then(或类似名称,例如getURL())。

在我的案例中,我发现此问题的方法是使用一个好的调试工具(我使用了Chrome DevTools自己的调试功能)。我建议您做同样的事情,在所有位置添加断点,并查看每行代码的位置。

这是一个简短粗略的示例,以显示我的意思:

// This code increments a number from 1 to 2 to 3 and returns it each time after a delay of 1 second.

async function loop() {
    for (i = 1; i <= 3; i++) {
        console.log('Input start');
        /* The following waits for result of aSync before continuing.
           Without 'await', it would execute the last line
           of this function whilst aSync's own 'await'
           waited for its result. */
        await aSync(i);
        console.log('Input end');
    }
}

async function aSync(num) {
    console.log('Return start');
    /* The following waits for the 1-second delay before continuing.
       Without 'await', it would return a pending promise immediately
       each time. */
    let result = await new Promise(
        // I'm not using arrow functions to show what it's doing more clearly.
        function(rs, rj) {
            setTimeout(
                function() {
                    /* For those who didn't know, the following passes the number
                       into the 'resolved' ('rs') parameter of the promise's executor
                       function. Without doing this, the promise would never be fulfilled. */
                    rs(num);
                }, 1000
            )
        }
    );
    console.log(result);
    console.log('Return end');
    
}

loop();
© www.soinside.com 2019 - 2024. All rights reserved.