From d2011f8deaf0950a4c9b27d4b3af90882289802d Mon Sep 17 00:00:00 2001 From: Fyodor Perejoguine Date: Wed, 24 Apr 2019 16:09:16 +0200 Subject: [PATCH] Queue now gets flushed and every function call throws error, after a single error reaches its maximum retries. --- src/index.ts | 15 +++++++++++++-- test/test.ts | 10 ++++++++-- 2 files changed, 21 insertions(+), 4 deletions(-) diff --git a/src/index.ts b/src/index.ts index 23becaf..9b2a23d 100644 --- a/src/index.ts +++ b/src/index.ts @@ -85,7 +85,7 @@ export default class CallHandler { const wait = this.getBackoff(e, attemptNr); if (wait) { const result = timeout(wait, () => this.sendReq(request, attemptNr + 1)); - this.blockRequests(result, this.rateLim) + if (attemptNr === 0) this.blockRequests(result, this.rateLim); return await result; } else { // If getBackoff returns undefined that means no more retries should be made and error passed upward. @@ -99,9 +99,20 @@ export default class CallHandler { this.requestsLastPeriod = this.requestsLastPeriod + amount; try { await promise; - } finally { this.requestsLastPeriod = this.requestsLastPeriod - amount; return await this.checkQueue(); + } catch (e) { + this.requestsLastPeriod = this.requestsLastPeriod - amount; + return await this.flushQueue(e); + } + } + + // Remove all requests from the queue and reject their promises with the provided Error. + private flushQueue(reason: Error) { + while (this.queue.length > 0) { + // Pop requests off the queue and reject their promise + const re = this.queue.shift(); + if (re && re.passPromise) { re.passPromise(new Promise((res, rej) => rej(reason))) }; } } diff --git a/test/test.ts b/test/test.ts index 94f2708..c4c0234 100644 --- a/test/test.ts +++ b/test/test.ts @@ -142,7 +142,12 @@ describe('RequestHandler', () => { } }); - const func = async () => reqHandler.call(() => secondFetch()); + let errcount = 0; + const func = async () => reqHandler.call(() => secondFetch()) + .catch((e) => { + errcount += 1; + }); + const looper = new Looper(func, 20); let promise; @@ -159,7 +164,8 @@ describe('RequestHandler', () => { error = e; } const delta = Date.now() - timeA; - + await new Promise((res) => setTimeout(() => res(), 1000)); + expect(errcount).toBeGreaterThan(30); expect(delta).toBeLessThan(800); expect(delta).toBeGreaterThanOrEqual(700); expect(error).toBeTruthy();