【问题标题】:Node.js how to read a file and then write the same file with two separate functions?Node.js 如何读取一个文件,然后用两个单独的函数写入同一个文件?
【发布时间】:2013-07-12 19:12:26
【问题描述】:

我想要做的是读取一个文件,然后在我写入文件时能够使用该信息执行其他操作。例如:

读取文件 写入文件,同时进行 MD5 哈希、数字签名等。

我可以使用 fs.readfile 和 fs.writefile 作为一个操作,只需将文件从 Web 服务器复制到我的计算机,但我认为我仍然不能执行这些相同的操作。无论如何,跳过中间的东西。如何使用 fs.readfile 和 writefile 创建两个单独的函数来复制文件?这是我一直在做的事情,是的,我已经广泛阅读这些论坛以寻找答案。

var fs = require('fs');



function getData(srcPath) { 
fs.readFile(srcPath, 'utf8', function (err, data) {
        if (err) throw err;
        return data;
        }
    );
}


function writeData(savPath, srcPath) {
        fs.writeFile (savPath, (getData(srcPath)), function(err) {
        if (err) throw err;
            console.log('complete');
        }
    );
}
//getData ('./test/test.txt');
writeData ('./test/test1.txt','./test/test.txt');

我希望能够下载任何类型的文件并制作原始副本,并将 md5 哈希等附加到 JSON 文件。不过,这可能是以后的问题。

【问题讨论】:

  • getData 在您的代码中不执行任何操作。您需要在 readFile 的回调中调用 writeFile。如果你想 git-r-dun,总是有 fs.readFileSync(),它可以像你期望的那样工作。

标签: javascript node.js


【解决方案1】:

正如 dandavis 在他的评论中所建议的那样,readFile 什么都不做,因为它是一个异步调用。查看this answer 了解更多信息。

简而言之,异步调用永远不会等待结果返回。在您的示例中,getData 不会等待readFile() 返回您想要的结果,而是会立即完成。异步调用通常通过传递callbacks 来处理,这是readFilewriteFile 的最后一个参数。

无论如何,有两种方法可以做到这一点:

1.异步执行(这是正确的方法):

function copyData(savPath, srcPath) {
    fs.readFile(srcPath, 'utf8', function (err, data) {
            if (err) throw err;
            //Do your processing, MD5, send a satellite to the moon, etc.
            fs.writeFile (savPath, data, function(err) {
                if (err) throw err;
                console.log('complete');
            });
        });
}

2.同步执行。您的代码不必更改太多,只需将readFilewriteFile 分别替换为readFileSyncwriteFileSync警告:使用这种方法不仅违反最佳实践,而且违背了使用 nodejs 的目的(当然,除非你有非常正当的理由)。

编辑:根据 OP 的要求,这是分离这两种方法的一种可能方法,例如,使用回调:

function getFileContent(srcPath, callback) { 
    fs.readFile(srcPath, 'utf8', function (err, data) {
        if (err) throw err;
        callback(data);
        }
    );
}

function copyFileContent(savPath, srcPath) { 
    getFileContent(srcPath, function(data) {
        fs.writeFile (savPath, data, function(err) {
            if (err) throw err;
            console.log('complete');
        });
    });
}

这样,您将读取部分(getFileContent)与复制部分分开。

【讨论】:

  • 按您的说法,同步执行此操作会浪费时间。我只是认为将 readfile 和 writeful 划分为单独的函数会更容易,以防我在程序中只需要使用一个而不是另一个。尽管如此,如果我能正确地完成所有处理,这会更好。我只需要尝试一下,看看它是否有效。
  • 查看我的编辑,了解如何将读取与复制分开。您可以将相同的技术应用于 writeFile(例如传递回调)。
  • 我认为说同步执行此操作“违背了使用 nodejs 的目的”是言过其实的。是的,nodejs 确实使并鼓励一种编程风格成为可能,在这种风格中,任何可能需要一定时间的操作都是异步完成的。但是,在这种情况下,OP 使用 nodejs 的目的只是为了运行一个用 javascript 编写的程序,而使用同步调用对于这样的程序来说可能是一种非常合适的风格。
  • @Duncan “当然,除非你有非常正当的理由”:简单地运行一个用 JS 编写的程序是正当的理由
【解决方案2】:

我最近不得不使用这个,所以我将verybadallocs的答案转换为promises。

function readFile (srcPath) {
  return new Promise(function (resolve, reject) {
    fs.readFile(srcPath, 'utf8', function (err, data) {
      if (err) {
        reject(err)
      } else {
        resolve(data)
      }
    })
  })
}

function writeFile (savPath, data) {
  return new Promise(function (resolve, reject) {
    fs.writeFile(savPath, data, function (err) {
      if (err) {
        reject(err)
      } else {
        resolve()
      }
    })
  })
}

那么使用它们就很简单了。

readFile('path').then(function (results) {
  results += ' test manipulation'
  return writeFile('path', results)
}).then(function () {
  //done writing file, can do other things
})

用于异步/等待

const results = await readFile('path')
results += ' test manipulation'
await writeFile('path', results)
// done writing file, can do other things

【讨论】:

    【解决方案3】:

    要以非阻塞或异步方式读写文件,可以使用 es6 或更高版本的高级特性,如 Promise 或 Async/await,但必须注意 Polyfills (@ 987654321@) 或者如果只有几个读/写,你可以使用回调地狱。

    function readFiles(){
        fs.readFile('./txt/start.txt', 'utf-8', (err, data1)=>{
            if(err) return console.log(err);
            fs.readFile(`./txt/${data1}.txt`, 'utf-8', (err, data2)=>{
                if(err) return console.log(err);
                fs.readFile('./txt/append.txt', 'utf-8', (err, data3)=>{
                    if(err) return console.log(err);
                    writeFile('./txt/final.txt', `${data2}\n${data3}`);
                });
            });
        });
    }
    
    function writeFile(path, data){
        fs.writeFile(path,data,'utf-8',err=>{
            if(err){
                console.log(err);
            }
        })
    }
    readFiles();
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-04-26
      • 1970-01-01
      • 2021-12-05
      • 2011-03-13
      • 2019-03-04
      • 1970-01-01
      • 2013-07-12
      • 1970-01-01
      相关资源
      最近更新 更多