最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - Node.js WriteStream synchronous - Stack Overflow

programmeradmin2浏览0评论

I'm writing a purely synchronous, single threaded command line program in node.js, which needs to write a single binary file, for which I'm using WriteStream. My usage pattern is along the lines of:

var stream = fs.createWriteStream(file)
stream.write(buf1)
stream.write(buf2)

This seems to work, but the documentation says it's asynchronous and I want to make sure I'm not writing code that works 99% of the time. I don't care exactly when the data gets written as long as it's written in the specified order and no later than when the program exits, and the quantity of data is small so speed and memory consumption are not issues.

I've seen mention of stream.end() but it seems to work without it and I've also seen suggestions that calling it may actually be a bad idea if you're not using callbacks because it might end up getting called before all the data is written.

Is my approach correct (given that I want purely synchronous) or is there anything I need to watch out for?

I'm writing a purely synchronous, single threaded command line program in node.js, which needs to write a single binary file, for which I'm using WriteStream. My usage pattern is along the lines of:

var stream = fs.createWriteStream(file)
stream.write(buf1)
stream.write(buf2)

This seems to work, but the documentation says it's asynchronous and I want to make sure I'm not writing code that works 99% of the time. I don't care exactly when the data gets written as long as it's written in the specified order and no later than when the program exits, and the quantity of data is small so speed and memory consumption are not issues.

I've seen mention of stream.end() but it seems to work without it and I've also seen suggestions that calling it may actually be a bad idea if you're not using callbacks because it might end up getting called before all the data is written.

Is my approach correct (given that I want purely synchronous) or is there anything I need to watch out for?

Share Improve this question asked Jun 28, 2014 at 16:32 rwallacerwallace 33.4k42 gold badges133 silver badges276 bronze badges 5
  • 1 I'm not entirely sure if this would fit into your use case (and recognize that it may not be quite what you're looking for) but have you considered just using fs.write as a synchronous option? nodejs.org/api/… – imjared Commented Jun 28, 2014 at 16:40
  • @imjared Good question! the synchronous version of that would seem to do the job. What's the difference between the two? or put another way, given the existence of that, what's the reason for the existence of WriteStream? Is WriteStream intended primarily for writing text? – rwallace Commented Jun 28, 2014 at 16:47
  • 1 to be perfectly honest I don't have the best understanding of streams but whenever I've needed a synchronous approach to writing something. Here's a much better explanation than I could give: stackoverflow.com/a/8770026/628699 – imjared Commented Jun 28, 2014 at 16:59
  • Node is very centered around async IO. Why are you focusing so heavily on making all of your logic synchronous? – loganfsmyth Commented Jun 28, 2014 at 17:18
  • 4 @loganfsmyth Because I'm writing a straightforward command line program that by its nature has nothing to do with async IO. – rwallace Commented Jun 28, 2014 at 17:33
Add a comment  | 

3 Answers 3

Reset to default 4

You can do this, the only problem can be if you create two or more concurrent streams for the same path: the order of writes from different streams will be undefined. By the way, there is a synchronous fs write stream implementation in node: fs.SyncWriteStream. It's kind of private and requires fd as an argument, but if you really want it...

I'm working on a timing-critical API, where a new file has to have been written and its stream completely handled before the next action can be performed. The solution, in my case (and, quite possibly, that of the OP's question) was to use:

writer.on('finish', () => {
 console.error('All writes are now complete.');
});

as per the fs Event: 'finish' documentation

const writeToLocalDisk = (stream, path) => {
  return new Promise((resolve, reject) => {
    const istream = stream;
    const ostream = fs.createWriteStream(path);
    istream.pipe(ostream);
    istream.on("end", () => {
      console.log(`Fetched ${path} from elsewhere`);
      resolve();
    });
    istream.on("error", (err) => {
      console.log(JSON.stringify(err, null, 2));
      resolve();
    });
  });
};

// Then use an async function to perform sequential-like operation

async function sequential (stream) {
  const path = "";
  await writeToLocalDisk(stream, path);
  console.log('other operation here');
} 

发布评论

评论列表(0)

  1. 暂无评论