javascript - json stringify writeStream完成后如何解决promise?
问题描述
我正在使用 npm 的 big-json 来解决JSON.stringify()
大型嵌套对象的限制。
一旦对象被字符串化,我就会将它保存到文件系统中。
然而,这整个过程减慢了我的整体处理速度——我假设这与我现在可能正在等待流超时或在它关闭之前发生的事情有关。
这是我的代码:
const fs = require('fs-extra');
const json = require('big-json');
function offlineSave(objArr){
return new Promise((resolve, reject) => {
let promises = [];
for(let obj of objArr){
const filePath = path.join(__dirname, `${obj}.json`);
//this used to be a promisified fs.writeFile() - which seemed to be faster
promises.push(saveStreamPromise(filePath,obj));
}
Promise.all(promises)
.then((msg) =>{
resolve(`Saved ${msg.length} files`);
});
});
}
let saveStreamPromise = function(filePath, obj){
return new Promise((resolve, reject) =>{
let stream = fs.createWriteStream(filePath, { flag: 'w+' });
const stringifyStream = json.createStringifyStream({ body: obj});
stringifyStream.on('data', strChunk =>{
stream.write(strChunk);
});
//is this the correct way to return a promise upon stringify complete?
stringifyStream.on('end', () =>{
stream.end();
resolve(`${obj} saved!`);
});
});
}
解决方案
您的代码正在侦听读取流的结束。虽然这可能有效,但最好监听写入流的结束,这样您只有在数据提交到磁盘后才解决承诺。
最好将两个流的错误处理添加到任何一个流上的任何错误都拒绝承诺:
function saveStreamPromise(filePath, obj){
return new Promise((resolve, reject) =>{
let stream = fs.createWriteStream(filePath, { flag: 'w+' });
const stringifyStream = json.createStringifyStream({ body: obj});
stringifyStream.on('data', strChunk =>{
stream.write(strChunk);
});
// resolve when read stream and write stream are done
stringifyStream.on('end', () =>{
stream.end(function() {
resolve('object saved!');
});
}).on('error', reject);
stream.on('error', reject);
});
}
我还建议您使用.pipe()
自动将一个流馈送到另一个流,如下所示:
function saveStreamPromise(filePath, obj){
return new Promise((resolve, reject) =>{
let stream = fs.createWriteStream(filePath, { flag: 'w+' });
const stringifyStream = json.createStringifyStream({ body: obj});
stringifyStream.pipe(stream);
// when using pipe, the write stream will automatically close when the
// readable gets to the end of its data
stream.on('error', reject).on('close', function() {
resolve('object saved!');
});
stringifyStream.on('error', reject);
}
而且,${obj} saved!
只会给你类似“[object object] 已保存!” 这不太可能是你想要的。
推荐阅读
- sorting - Power BI/排序/是否有基于共享度量对多个视觉对象进行排序?
- c# - 如何将依赖注入与 [SwaggerOperationFilter] 一起使用?
- import - 在 Python 中安装或导入?
- java - 如何在纯 Java 中创建 GET 端点?
- c# - 如何将 MVVM 与 EF 一起使用(在 SQLite 中使用非常复杂的数据库)?
- javascript - 在 Javascript Chrome 扩展函数中添加计时器
- excel - 如何使用 VBA 在 Excel 中跳过缺少 html 标记的行
- c++ - 在 C++ 中打印乘号
- node.js - 预检请求未通过访问控制检查:它没有 HTTP ok 状态问题,我不知道为什么,我正确导入了所有内容
- android - Android compose Card在使用半透明颜色时有边框