Node.js转换文件流并写入同一文件导致空文件

时间:2016-12-23 12:10:49

标签: node.js stream node-streams

我正在尝试使用节点文件流和自定义转换功能修改一些文件。这是转换函数:

const TransformStream = function() {
  Transform.call(this, {objectMode: true});
};
util.inherits(TransformStream, Transform);

TransformStream.prototype._transform = function(chunk, encoding, callback) {
  let line = chunk.toString()
  if (!this.findLinesMode && lineStartRe.test(line)) {
    this.findLinesMode = true
    this.lines = []
  }
  if (this.findLinesMode) {
    this.lines.push(line)
  }
  if (this.findLinesMode && lineEndRe.test(line)) {
    this.findLinesMode = false
    line = this.lines.join('').replace(re, (str, match) => match.trim())
  }
  if (!this.findLinesMode) {
    this.push(line + '\n')
  }

  callback()
};

我尝试在以下代码中使用它:

byline(fs.createReadStream(filePath, {encoding: 'utf8'}))
  .pipe(new TransformStream())
  .pipe(fs.createWriteStream(filePath))

但是,该文件最终为空。

我确信变换器代码按预期工作,因为我尝试将其传递给process.stdout,输出正是我想要的。

我的问题是:我做错了什么,我可以尝试修复它?

1 个答案:

答案 0 :(得分:2)

这对你的变换器代码来说不是问题,但是你打开一个文件进行写入的问题可能在你甚至从它上面读取之前就被覆盖了。

在shell中也是如此。如果您运行:

cat < file.txt > file.txt

或:

tr a-z A-Z < x.txt > x.txt

会导致文件变空。

您必须通过管道传输到临时文件,然后用新文件替换旧文件。或者将旧的名称重命名为其他临时名称,以正确的名称打开新文件,并将重命名的文件传输到旧文件,从而使您的转换成为可能。

确保使用安全的方式来创建临时文件的名称。您可以使用以下模块: