mirror of https://github.com/lukechilds/node.git
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
281 lines
7.0 KiB
281 lines
7.0 KiB
'use strict'
|
|
var util = require('util')
|
|
var test = require('tap').test
|
|
var requireInject = require('require-inject')
|
|
var dezalgo = require('dezalgo')
|
|
var mkdirp = require('mkdirp')
|
|
var path = require('path')
|
|
|
|
test('gently/force', function (t) {
|
|
t.plan(5)
|
|
|
|
linkOk(t, 'gently=true, force=false, works', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: true,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: true}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkNotOk(t, 'gently=true, force=false, does not work', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: true,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: false}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'gently=false, force=false, aok', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: false,
|
|
abs: true,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: false}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'gently=true, force=true, aok', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: true,
|
|
force: true,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: false}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'gently=false, force=true, aok', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: false,
|
|
abs: true,
|
|
force: true,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: false}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
})
|
|
|
|
test('abs, noabs', function (t) {
|
|
t.plan(4)
|
|
|
|
linkOk(t, 'abs', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: true,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: true}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'/foo/bar/wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'relative', {
|
|
// args
|
|
from: 'wibble',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: false,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: true}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/bar/wibble': {isLink: false}},
|
|
stat: {'/foo/bar/wibble': true},
|
|
symlink: {'wibble': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'relative ..', {
|
|
// args
|
|
from: '../wibble/bark/blump',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: false,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: true}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/wibble/bark/blump': {isLink: false}},
|
|
stat: {'/foo/wibble/bark/blump': true},
|
|
symlink: {'../wibble/bark/blump': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
|
|
linkOk(t, 'relative .. deep', {
|
|
// args
|
|
from: 'zib/zap/../../../wibble/bark/blump',
|
|
to: '/foo/bar/baz',
|
|
gently: true,
|
|
abs: false,
|
|
force: false,
|
|
|
|
// expect
|
|
rm: {'/foo/bar/baz': {gently: true}},
|
|
mkdir: {'/foo/bar': true},
|
|
lstat: {'/foo/wibble/bark/blump': {isLink: false}},
|
|
stat: {'/foo/wibble/bark/blump': true},
|
|
symlink: {'../wibble/bark/blump': {'/foo/bar/baz': 'junction'}},
|
|
readlink: {}
|
|
})
|
|
})
|
|
|
|
function linkOk (t, msg, opts) {
|
|
testLink(opts, function (err) {
|
|
t.ifError(err, msg)
|
|
})
|
|
}
|
|
|
|
function linkNotOk (t, msg, opts) {
|
|
testLink(opts, function (err) {
|
|
t.ok(err, msg)
|
|
})
|
|
}
|
|
|
|
function platformPath (unixPath) {
|
|
if (unixPath[0] === '/') {
|
|
return path.resolve(unixPath)
|
|
} else {
|
|
return path.join.apply(path, unixPath.split('/'))
|
|
}
|
|
}
|
|
|
|
function platformerize (obj) {
|
|
Object.keys(obj).forEach(function (key) {
|
|
var newKey = platformPath(key)
|
|
if (typeof obj[key] === 'object') {
|
|
platformerize(obj[key])
|
|
} else if (typeof obj[key] === 'string') {
|
|
obj[key] = platformPath(obj[key])
|
|
}
|
|
if (newKey !== key) {
|
|
obj[newKey] = obj[key]
|
|
delete obj[key]
|
|
}
|
|
})
|
|
}
|
|
|
|
function testLink (opts, cb) {
|
|
var mkdirpMock = dezalgo(function (dir, cb) {
|
|
if (opts.mkdir[dir]) {
|
|
cb()
|
|
} else {
|
|
cb(new Error('mkdirp failed: ' + util.inspect(dir)))
|
|
}
|
|
})
|
|
// sync version used by istanbul for test coverage
|
|
// we shouldn't have to do this ;.;
|
|
// require-inject and/or instanbul will need patching
|
|
mkdirpMock.sync = mkdirp.sync
|
|
|
|
// convert any paths in our opts into platform specific paths, for windows support.
|
|
platformerize(opts)
|
|
|
|
var link = requireInject('../../lib/utils/link.js', {
|
|
'../../lib/npm.js': {
|
|
config: {
|
|
get: function (name) {
|
|
if (name !== 'force') return new Error('unknown config key: ' + name)
|
|
return opts.force
|
|
}
|
|
}
|
|
},
|
|
'../../lib/utils/gently-rm.js': dezalgo(function (toRemove, gently, cb) {
|
|
if (opts.rm[toRemove] && opts.rm[toRemove].gently === gently) {
|
|
cb()
|
|
} else {
|
|
cb(new Error('Removing toRemove: ' + util.inspect(toRemove) +
|
|
' gently: ' + util.inspect(gently) +
|
|
' not allowed: ' + util.inspect(opts.rm)))
|
|
}
|
|
}),
|
|
'mkdirp': mkdirpMock,
|
|
'graceful-fs': {
|
|
'stat': dezalgo(function (file, cb) {
|
|
if (opts.stat[file]) {
|
|
cb(null, {})
|
|
} else {
|
|
cb(new Error('stat failed for: ' + util.inspect(file)))
|
|
}
|
|
}),
|
|
'lstat': dezalgo(function (file, cb) {
|
|
if (opts.lstat[file]) {
|
|
var linkStat = opts.lstat[file]
|
|
cb(null, {
|
|
isSymbolicLink: function () {
|
|
return linkStat.isLink
|
|
}
|
|
})
|
|
} else {
|
|
cb(new Error('lstat failed for: ' + util.inspect(file)))
|
|
}
|
|
}),
|
|
'symlink': dezalgo(function (from, to, type, cb) {
|
|
if (!cb) {
|
|
cb = type
|
|
type = null
|
|
}
|
|
if (opts.symlink[from] && opts.symlink[from][to] === type) {
|
|
cb()
|
|
} else {
|
|
cb(new Error('symlink failed from: ' + util.inspect(from) + ' to: ' + util.inspect(to) + ' type: ' + util.inspect(type)))
|
|
}
|
|
}),
|
|
'readlink': function (file, cb) {
|
|
if (opts.readlink[file]) {
|
|
cb()
|
|
} else {
|
|
cb(new Error('readlink failed for: ' + util.inspect(file)))
|
|
}
|
|
}
|
|
}
|
|
})
|
|
link(opts.from, opts.to, opts.gently, opts.abs, cb)
|
|
}
|
|
|