graceful-fs
Advanced tools
Comparing version 4.2.7 to 4.2.8
@@ -57,3 +57,3 @@ var fs = require('fs') | ||
if (!err) { | ||
retry() | ||
resetQueue() | ||
} | ||
@@ -76,3 +76,3 @@ | ||
fs$closeSync.apply(fs, arguments) | ||
retry() | ||
resetQueue() | ||
} | ||
@@ -119,6 +119,6 @@ | ||
function go$readFile (path, options, cb, attempts = 0) { | ||
function go$readFile (path, options, cb, startTime) { | ||
return fs$readFile(path, options, function (err) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$readFile, [path, options, cb], attempts + 1, err]) | ||
enqueue([go$readFile, [path, options, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -140,6 +140,6 @@ if (typeof cb === 'function') | ||
function go$writeFile (path, data, options, cb, attempts = 0) { | ||
function go$writeFile (path, data, options, cb, startTime) { | ||
return fs$writeFile(path, data, options, function (err) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$writeFile, [path, data, options, cb], attempts + 1, err]) | ||
enqueue([go$writeFile, [path, data, options, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -162,6 +162,6 @@ if (typeof cb === 'function') | ||
function go$appendFile (path, data, options, cb, attempts = 0) { | ||
function go$appendFile (path, data, options, cb, startTime) { | ||
return fs$appendFile(path, data, options, function (err) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$appendFile, [path, data, options, cb], attempts + 1, err]) | ||
enqueue([go$appendFile, [path, data, options, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -185,6 +185,6 @@ if (typeof cb === 'function') | ||
function go$copyFile (src, dest, flags, cb, attempts = 0) { | ||
function go$copyFile (src, dest, flags, cb, startTime) { | ||
return fs$copyFile(src, dest, flags, function (err) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$copyFile, [src, dest, flags, cb], attempts + 1, err]) | ||
enqueue([go$copyFile, [src, dest, flags, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -206,6 +206,6 @@ if (typeof cb === 'function') | ||
function go$readdir (path, options, cb, attempts = 0) { | ||
function go$readdir (path, options, cb, startTime) { | ||
return fs$readdir(path, options, function (err, files) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$readdir, [path, options, cb], attempts + 1, err]) | ||
enqueue([go$readdir, [path, options, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -344,6 +344,6 @@ if (files && files.sort) | ||
function go$open (path, flags, mode, cb, attempts = 0) { | ||
function go$open (path, flags, mode, cb, startTime) { | ||
return fs$open(path, flags, mode, function (err, fd) { | ||
if (err && (err.code === 'EMFILE' || err.code === 'ENFILE')) | ||
enqueue([go$open, [path, flags, mode, cb], attempts + 1, err]) | ||
enqueue([go$open, [path, flags, mode, cb], err, startTime || Date.now(), Date.now()]) | ||
else { | ||
@@ -366,3 +366,27 @@ if (typeof cb === 'function') | ||
// keep track of the timeout between retry() calls | ||
var retryTimer | ||
// reset the startTime and lastTime to now | ||
// this resets the start of the 60 second overall timeout as well as the | ||
// delay between attempts so that we'll retry these jobs sooner | ||
function resetQueue () { | ||
var now = Date.now() | ||
for (var i = 0; i < fs[gracefulQueue].length; ++i) { | ||
// entries that are only a length of 2 are from an older version, don't | ||
// bother modifying those since they'll be retried anyway. | ||
if (fs[gracefulQueue][i].length > 2) { | ||
fs[gracefulQueue][i][3] = now // startTime | ||
fs[gracefulQueue][i][4] = now // lastTime | ||
} | ||
} | ||
// call retry to make sure we're actively processing the queue | ||
retry() | ||
} | ||
function retry () { | ||
// clear the timer and remove it to help prevent unintended concurrency | ||
clearTimeout(retryTimer) | ||
retryTimer = undefined | ||
if (fs[gracefulQueue].length === 0) | ||
@@ -372,14 +396,44 @@ return | ||
var elem = fs[gracefulQueue].shift() | ||
if (elem) { | ||
const [fn, args, attempts, err] = elem | ||
if (attempts < 10) { | ||
debug('RETRY', fn.name, args, `ATTEMPT #${attempts}`) | ||
fn.call(null, ...args, attempts) | ||
var fn = elem[0] | ||
var args = elem[1] | ||
// these items may be unset if they were added by an older graceful-fs | ||
var err = elem[2] | ||
var startTime = elem[3] | ||
var lastTime = elem[4] | ||
// if we don't have a startTime we have no way of knowing if we've waited | ||
// long enough, so go ahead and retry this item now | ||
if (startTime === undefined) { | ||
debug('RETRY', fn.name, args) | ||
fn.apply(null, args) | ||
} else if (Date.now() - startTime >= 60000) { | ||
// it's been more than 60 seconds total, bail now | ||
debug('TIMEOUT', fn.name, args) | ||
var cb = args.pop() | ||
if (typeof cb === 'function') | ||
cb.call(null, err) | ||
} else { | ||
// the amount of time between the last attempt and right now | ||
var sinceAttempt = Date.now() - lastTime | ||
// the amount of time between when we first tried, and when we last tried | ||
// rounded up to at least 1 | ||
var sinceStart = Math.max(lastTime - startTime, 1) | ||
// backoff. wait longer than the total time we've been retrying, but only | ||
// up to a maximum of 100ms | ||
var desiredDelay = Math.min(sinceStart * 1.2, 100) | ||
// it's been long enough since the last retry, do it again | ||
if (sinceAttempt >= desiredDelay) { | ||
debug('RETRY', fn.name, args) | ||
fn.apply(null, args.concat([startTime])) | ||
} else { | ||
const cb = args.pop() | ||
if (typeof cb === 'function') | ||
cb.call(null, err) | ||
// if we can't do this job yet, push it to the end of the queue | ||
// and let the next iteration check again | ||
fs[gracefulQueue].push(elem) | ||
} | ||
} | ||
setImmediate(retry) | ||
// schedule our next run if one isn't already scheduled | ||
if (retryTimer === undefined) { | ||
retryTimer = setTimeout(retry, 0) | ||
} | ||
} |
{ | ||
"name": "graceful-fs", | ||
"description": "A drop-in replacement for fs, making various improvements.", | ||
"version": "4.2.7", | ||
"version": "4.2.8", | ||
"repository": { | ||
@@ -6,0 +6,0 @@ "type": "git", |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Deprecated
MaintenanceThe maintainer of the package marked it as deprecated. This could indicate that a single version should not be used, or that the package is no longer maintained and any new vulnerabilities will not be fixed.
Found 1 instance in 1 package
31565
791
0