Skip to content

Commit

Permalink
Refactor rimraf
Browse files Browse the repository at this point in the history
  • Loading branch information
JPeer264 committed Feb 19, 2017
1 parent 3843d5f commit b9d8b45
Showing 1 changed file with 41 additions and 46 deletions.
87 changes: 41 additions & 46 deletions lib/remove/rimraf.js
Original file line number Diff line number Diff line change
@@ -1,22 +1,21 @@
module.exports = rimraf
rimraf.sync = rimrafSync
'use strict'

var assert = require('assert')
var path = require('path')
var fs = require('graceful-fs')
const fs = require('graceful-fs')
const path = require('path')
const assert = require('assert')

var isWindows = (process.platform === 'win32')
const isWindows = (process.platform === 'win32')

function defaults (options) {
var methods = [
const methods = [
'unlink',
'chmod',
'stat',
'lstat',
'rmdir',
'readdir'
]
methods.forEach(function (m) {
methods.forEach(m => {
options[m] = options[m] || fs[m]
m = m + 'Sync'
options[m] = options[m] || fs[m]
Expand All @@ -26,6 +25,8 @@ function defaults (options) {
}

function rimraf (p, options, cb) {
let busyTries = 0

if (typeof options === 'function') {
cb = options
options = {}
Expand All @@ -39,18 +40,14 @@ function rimraf (p, options, cb) {

defaults(options)

var busyTries = 0

rimraf_(p, options, function CB (er) {
if (er) {
if (isWindows && (er.code === 'EBUSY' || er.code === 'ENOTEMPTY' || er.code === 'EPERM') &&
busyTries < options.maxBusyTries) {
busyTries++
var time = busyTries * 100
let time = busyTries * 100
// try again, with the same exact callback as this one.
return setTimeout(function () {
rimraf_(p, options, CB)
}, time)
return setTimeout(() => rimraf_(p, options, CB), time)
}

// already gone
Expand Down Expand Up @@ -79,7 +76,7 @@ function rimraf_ (p, options, cb) {

// sunos lets the root user unlink directories, which is... weird.
// so we have to lstat here and make sure it's not a dir.
options.lstat(p, function (er, st) {
options.lstat(p, (er, st) => {
if (er && er.code === 'ENOENT') {
return cb(null)
}
Expand All @@ -93,7 +90,7 @@ function rimraf_ (p, options, cb) {
return rmdir(p, options, er, cb)
}

options.unlink(p, function (er) {
options.unlink(p, er => {
if (er) {
if (er.code === 'ENOENT') {
return cb(null)
Expand All @@ -120,11 +117,11 @@ function fixWinEPERM (p, options, er, cb) {
assert(er instanceof Error)
}

options.chmod(p, 666, function (er2) {
options.chmod(p, 666, er2 => {
if (er2) {
cb(er2.code === 'ENOENT' ? null : er)
} else {
options.stat(p, function (er3, stats) {
options.stat(p, (er3, stats) => {
if (er3) {
cb(er3.code === 'ENOENT' ? null : er)
} else if (stats.isDirectory()) {
Expand All @@ -138,6 +135,8 @@ function fixWinEPERM (p, options, er, cb) {
}

function fixWinEPERMSync (p, options, er) {
let stats

assert(p)
assert(options)
if (er) {
Expand All @@ -155,7 +154,7 @@ function fixWinEPERMSync (p, options, er) {
}

try {
var stats = options.statSync(p)
stats = options.statSync(p)
} catch (er3) {
if (er3.code === 'ENOENT') {
return
Expand All @@ -182,7 +181,7 @@ function rmdir (p, options, originalEr, cb) {
// try to rmdir first, and only readdir on ENOTEMPTY or EEXIST (SunOS)
// if we guessed wrong, and it's not a directory, then
// raise the original error.
options.rmdir(p, function (er) {
options.rmdir(p, er => {
if (er && (er.code === 'ENOTEMPTY' || er.code === 'EEXIST' || er.code === 'EPERM')) {
rmkids(p, options, cb)
} else if (er && er.code === 'ENOTDIR') {
Expand All @@ -198,23 +197,20 @@ function rmkids (p, options, cb) {
assert(options)
assert(typeof cb === 'function')

options.readdir(p, function (er, files) {
if (er) {
return cb(er)
}
var n = files.length
if (n === 0) {
return options.rmdir(p, cb)
}
var errState
files.forEach(function (f) {
rimraf(path.join(p, f), options, function (er) {
options.readdir(p, (er, files) => {
if (er) return cb(er)

let n = files.length
let errState

if (n === 0) return options.rmdir(p, cb)

files.forEach(f => {
rimraf(path.join(p, f), options, er => {
if (errState) {
return
}
if (er) {
return cb(errState = er)
}
if (er) return cb(errState = er)
if (--n === 0) {
options.rmdir(p, cb)
}
Expand All @@ -227,6 +223,8 @@ function rmkids (p, options, cb) {
// tie up the JavaScript thread and fail on excessively
// deep directory trees.
function rimrafSync (p, options) {
let st

options = options || {}
defaults(options)

Expand All @@ -236,7 +234,7 @@ function rimrafSync (p, options) {
assert.equal(typeof options, 'object', 'rimraf: options should be object')

try {
var st = options.lstatSync(p)
st = options.lstatSync(p)
} catch (er) {
if (er.code === 'ENOENT') {
return
Expand All @@ -258,11 +256,9 @@ function rimrafSync (p, options) {
} catch (er) {
if (er.code === 'ENOENT') {
return
}
if (er.code === 'EPERM') {
} else if (er.code === 'EPERM') {
return isWindows ? fixWinEPERMSync(p, options, er) : rmdirSync(p, options, er)
}
if (er.code !== 'EISDIR') {
} else if (er.code !== 'EISDIR') {
throw er
}
rmdirSync(p, options, er)
Expand All @@ -281,11 +277,9 @@ function rmdirSync (p, options, originalEr) {
} catch (er) {
if (er.code === 'ENOENT') {
return
}
if (er.code === 'ENOTDIR') {
} else if (er.code === 'ENOTDIR') {
throw originalEr
}
if (er.code === 'ENOTEMPTY' || er.code === 'EEXIST' || er.code === 'EPERM') {
} else if (er.code === 'ENOTEMPTY' || er.code === 'EEXIST' || er.code === 'EPERM') {
rmkidsSync(p, options)
}
}
Expand All @@ -294,8 +288,9 @@ function rmdirSync (p, options, originalEr) {
function rmkidsSync (p, options) {
assert(p)
assert(options)
options.readdirSync(p).forEach(function (f) {
rimrafSync(path.join(p, f), options)
})
options.readdirSync(p).forEach(f => rimrafSync(path.join(p, f), options))
options.rmdirSync(p, options)
}

module.exports = rimraf
rimraf.sync = rimrafSync

0 comments on commit b9d8b45

Please sign in to comment.