From 9f9c636e64d3f4706cefd89046251d612a4d766a Mon Sep 17 00:00:00 2001 From: piyo Date: Mon, 8 Nov 2021 21:06:28 +0900 Subject: [PATCH] feat(rule): add `maxRetryTime` option (#136) * feat(rule): add `maxRetryTime` option * docs: add `maxRetryTime` * fix: change default value of maxRetryTime 0 -> 10 * docs: change default value of maxRetryTime * fix: prefer to use After-Retry value --- ReadMe.md | 7 ++++++- src/no-dead-link.js | 15 +++++++++++---- 2 files changed, 17 insertions(+), 5 deletions(-) diff --git a/ReadMe.md b/ReadMe.md index 13da00b..6fde2d0 100644 --- a/ReadMe.md +++ b/ReadMe.md @@ -66,7 +66,8 @@ The default options are: "preferGET": [], "ignoreRedirects": false, "retry": 3, - "userAgent": "textlint-rule-no-dead-link/1.0" + "userAgent": "textlint-rule-no-dead-link/1.0", + "maxRetryTime": 10 } } } @@ -151,6 +152,10 @@ The default max retry count is `3`. Customize `User-Agent` http header. +### maxRetryTime + +The max of allow waiting time [second] for retry, if response header has `Retry-After`. + ## Tests ``` diff --git a/src/no-dead-link.js b/src/no-dead-link.js index 5b766b0..d12b7e9 100644 --- a/src/no-dead-link.js +++ b/src/no-dead-link.js @@ -20,7 +20,8 @@ const DEFAULT_OPTIONS = { interval: 500, // The length of time in milliseconds before the interval count resets. Must be finite. [Experimental] intervalCap: 8, // The max number of runs in the given interval of time. [Experimental] keepAlive: false, // {boolean} if it is true, use keepAlive for checking request [Experimental] - userAgent: 'textlint-rule-no-dead-link/1.0' // {String} a UserAgent + userAgent: 'textlint-rule-no-dead-link/1.0', // {String} a UserAgent, + maxRetryTime: 10, // (number) The max of waiting seconds for retry, if response returns `After-Retry` header. }; // Adopted from http://stackoverflow.com/a/3809435/951517 @@ -186,11 +187,17 @@ const createCheckAliveURL = (ruleOptions) => { // try to fetch again if not reach max retry count if (currentRetryCount < maxRetryCount) { - // exponential retry - // 0ms -> 100ms -> 200ms -> 400ms -> 800ms ... - await waitTimeMs((currentRetryCount ** 2) * 100); + const retrySeconds = res.headers.get('Retry-After'); + // If the response has `Retry-After` header, prefer it + // else exponential retry: 0ms -> 100ms -> 200ms -> 400ms -> 800ms ... + const retryWaitTimeMs = retrySeconds !== null ? retrySeconds * 1000 : currentRetryCount ** 2 * 100; + const maxRetryTimeMs = ruleOptions.maxRetryTime * 1000; + if (retryWaitTimeMs <= maxRetryTimeMs) { + await waitTimeMs(retryWaitTimeMs); + } return isAliveURI(uri, 'GET', maxRetryCount, currentRetryCount + 1); } + return { ok: res.ok, message: `${res.status} ${res.statusText}`,