fs.createWriteStream是否不立即创建文件? [英] fs.createWriteStream does not immediately create file?

查看:129
本文介绍了fs.createWriteStream是否不立即创建文件?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我从http 函数进行了简单的下载,如下所示(为简化起见,省略了错误处理):

I have made a simple download from http function as below (error handling is omitted for simplifcation):

function download(url, tempFilepath, filepath, callback) {
    var tempFile = fs.createWriteStream(tempFilepath);
    http.request(url, function(res) {
        res.on('data', function(chunk) {
            tempFile.write(chunk);
        }).on('end', function() {
            tempFile.end();
            fs.renameSync(tempFile.path, filepath);
            return callback(filepath);
        })
    });
}

但是,由于我异步调用download()数十次,它很少报告fs.renameSync错误,并抱怨在tempFile.path找不到文件.

However, as I call download() tens of times asynchronously, it seldom reports error on fs.renameSync complaining it cannot find file at tempFile.path.

Error: ENOENT, no such file or directory 'xxx'

我使用了相同的URL列表来对其进行测试,但它大约30%的时间都失败了.一次下载一个相同的URL列表.

I used the same list of urls to test it, and it failed about 30% of time. The same list of urls worked when downloaded one by one.

经过更多测试,我发现下面的代码

Testing some more, I found out that the following code

fs.createWriteStream('anypath');
console.log(fs.exist('anypath'));
console.log(fs.exist('anypath'));
console.log(fs.exist('anypath'));

并不总是打印true,但有时第一个答案打印false.

does not always print true, but sometimes the first answer prints false.

我怀疑太多的异步fs.createWriteStream调用不能保证文件的创建.这是真的?有什么方法可以保证文件的创建吗?

I am suspecting that too many asynchronous fs.createWriteStream calls cannot guarantee the file creation. Is this true? Are there any methods to guarantee file creation?

推荐答案

在您从流中收到'open'事件之前,您不应该在tempFile写入流上调用write.在看到该事件之前,该文件将不存在.

You shouldn't call write on your tempFile write stream until you've received the 'open' event from the stream. The file won't exist until you see that event.

对于您的功能:

function download(url, tempFilepath, filepath, callback) {
    var tempFile = fs.createWriteStream(tempFilepath);
    tempFile.on('open', function(fd) {
        http.request(url, function(res) {
            res.on('data', function(chunk) {
                tempFile.write(chunk);
            }).on('end', function() {
                tempFile.end();
                fs.renameSync(tempFile.path, filepath);
                return callback(filepath);
            });
        });
    });
}

供您测试:

var ws = fs.createWriteStream('anypath');
ws.on('open', function(fd) {
    console.log(fs.existsSync('anypath'));
    console.log(fs.existsSync('anypath'));
    console.log(fs.existsSync('anypath'));
});

这篇关于fs.createWriteStream是否不立即创建文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆