从回调函数到 fs/promises,以在 Node.js 中处理文件系统
在这篇文章中,我将向你展示Node.js如何演变为与文件系统交互。
让我们从创建一个文件开始:
const fs = require("fs");
fs.writeFile("/tmp/test.js", "console.log('Hello world');", error => {
if (error) console.error(error);
else console.log("file created successfully!");
});
如果我们想要避免回调,在Node.js v8之前,我们必须手动将fs.writeFile函数转换为 promis 函数,或者使用bluebird或Q等第三方模块。
让我们手动将上面的代码转换为 Promise 并将其封装到一个函数中:
const fs = require("fs");
const writeFilePromise = (file, data) => {
return new Promise((resolve, reject) => {
fs.writeFile(file, data, error => {
if (error) reject(error);
resolve("file created successfully with handcrafted Promise!");
});
});
};
writeFilePromise(
"/tmp/test2.js",
"console.log('Hello world with handcrafted promise!');"
)
.then(result => console.log(result))
.catch(error => console.log(error));
随着Node.js V8的到来,'util.promisify()'允许我们将返回回调的 I/O 函数转换为返回 Promise 的 I/O 函数。
const fs = require("fs");
const util = require("util");
const writeFile = util.promisify(fs.writeFile);
writeFile("/tmp/test3.js", "console.log('Hello world with promisify!');")
.then(() => console.log("file created successfully with promisify!"))
.catch(error => console.log(error));
我们来看看async/await版本:
const fs = require("fs");
const { promisify } = require("util");
const writeFile = promisify(fs.writeFile);
async function main() {
await writeFile("/tmp/test4.js",
"console.log('Hello world with promisify and async/await!');");
console.info("file created successfully with promisify and async/await!");
}
main().catch(error => console.error(error));
在最新版本(Node.js V10 )中, fs库的函数可以直接返回 Promise,省去了旧方法中的额外步骤和开销。这得益于其fs/promises API。
const fsp = require("fs/promises");
try {
await fsp.writeFile("/tmp/test5.js", "console.log('Hello world with Node.js v10 fs/promises!'");
console.info("File created successfully with Node.js v10 fs/promises!");
} catch (error){
console.error(error);
}
注意,我使用的是顶层 await(我的await代码不在async函数内部)。此功能目前仍处于实验阶段,因此如果您想体验它,请使用以下标志:-- experimental-repl-await。
fs /promises API 提供以下方法:
access、copyFile、open、read、write、rename、truncate、ftruncate、rmdir、fdatasync、fsync、mkdir、readdir、readlink、symlink、fstat、lstat、stat、link、unlink、fchmod、chmod、lchmod、lchown、fchown、chown、utimes、futimes、realpath、mkdtemp、writeFile、appendFile 和 readFile。
更新:
在Node 13中,即使使用ESM模块也能正常工作:
import { promises as fs } from 'fs';
try {
await fs.writeFile("/tmp/test6.js", "console.log('Hello world with Node.js v13 fs.promises!'");
console.info("File created successfully with Node.js v13 fs.promises!");
} catch (error){
console.error(error);
}