我试图创建一个完整的路径,如果它不存在。
代码如下所示:
var fs = require('fs');
if (!fs.existsSync(newDest)) fs.mkdirSync(newDest);
只要只有一个子目录(像'dir1'这样的newDest),这段代码就能很好地工作,但是当有一个目录路径('dir1/dir2')时,它就会失败
错误:ENOENT,没有这样的文件或目录
我希望能够用尽可能少的代码行创建完整的路径。
我读到fs上有一个递归选项,并尝试了这样做
var fs = require('fs');
if (!fs.existsSync(newDest)) fs.mkdirSync(newDest,'0777', true);
我觉得递归地创建一个不存在的目录应该这么简单。我是否遗漏了一些东西,或者我是否需要解析路径并检查每个目录,如果它不存在,则创建它?
我对Node很陌生。也许我使用的是旧版本的FS?
找不到创建具有所需权限的目录的示例。
使用您想要的权限以异步递归方式创建目录。
下面是一个简单的nodejs解决方案
节点v18.12.1
Ubuntu 18
//-----------------------------
const fs = require('fs');
const fsPromises = fs.promises;
const checkDirAccess = async (userDir) => {
try {
await fsPromises.access(userDir, fs.constants.R_OK | fs.constants.W_OK);
console.log(` ${userDir} Dir existss`);
return userDir;
} catch (err) {
if(err.errno = -2)
return await crDir(userDir);
else
throw err;
}
}
const crDir = async (userDir) => {
try {
let newDir = await fsPromises.mkdir(userDir, { recursive: true, mode: 0o700});
// When userDir is created; newDir = undefined;
console.log(` Created new Dir ${newDir}`);
return newDir;
} catch (err) {
throw err;
}
}
const directoryPath = ['uploads/xvc/xvc/xvc/specs', 'uploads/testDir11', 'uploads/xsXa/', 'uploads//xsb//', 'uploads//xsV/'];
const findDir = async() => {
try {
for (const iterator of directoryPath) {
let dirOK = await checkDirAccess(iterator);
if(dirOK)
console.log(`found ${dirOK}`)
}
} catch (error) {
console.error('Error : ', error);
}
}
一种选择是使用shelljs模块
npm install shelljs
var shell = require('shelljs');
shell.mkdir('-p', fullPath);
从那一页开始:
可用的选项:
P:全路径(如有必要将创建中间dirs)
正如其他人所注意到的,还有其他更专注的模块。但是,除了mkdirp之外,它还有大量其他有用的shell操作(比如which, grep等等…),并且它可以在windows和*nix上工作
编辑:评论建议这在没有mkdir cli实例的系统上不起作用。事实并非如此。这就是shelljs的重点——创建一个可移植的跨平台shell类函数集。它适用于偶数窗户。
递归创建目录的异步方法:
import fs from 'fs'
const mkdirRecursive = function(path, callback) {
let controlledPaths = []
let paths = path.split(
'/' // Put each path in an array
).filter(
p => p != '.' // Skip root path indicator (.)
).reduce((memo, item) => {
// Previous item prepended to each item so we preserve realpaths
const prevItem = memo.length > 0 ? memo.join('/').replace(/\.\//g, '')+'/' : ''
controlledPaths.push('./'+prevItem+item)
return [...memo, './'+prevItem+item]
}, []).map(dir => {
fs.mkdir(dir, err => {
if (err && err.code != 'EEXIST') throw err
// Delete created directory (or skipped) from controlledPath
controlledPaths.splice(controlledPaths.indexOf(dir), 1)
if (controlledPaths.length === 0) {
return callback()
}
})
})
}
// Usage
mkdirRecursive('./photos/recent', () => {
console.log('Directories created succesfully!')
})
Exec在windows上可能很乱。还有一个更“nodie”的解决方案。基本上,您有一个递归调用来查看目录是否存在,并深入子目录(如果存在)或创建它。下面是一个函数,它将创建子函数,并在完成时调用一个函数:
fs = require('fs');
makedirs = function(path, func) {
var pth = path.replace(/['\\]+/g, '/');
var els = pth.split('/');
var all = "";
(function insertOne() {
var el = els.splice(0, 1)[0];
if (!fs.existsSync(all + el)) {
fs.mkdirSync(all + el);
}
all += el + "/";
if (els.length == 0) {
func();
} else {
insertOne();
}
})();
}