2015-12-07 48 views
6

Node.jsの大きなファイルを進捗情報で高速にコピーする機会はありますか?Node.jsの進行状況情報を含む高速ファイルコピー?

ソリューション1:。fs.createReadStream()パイプ(...)はネイティブCP

参照より遅い5まで、役に立たない=:NPMパッケージ「で(情報が可能である進行、Fastest way to copy file in node.js progress-ストリーム "):

fs = require('fs'); 
    fs.createReadStream('test.log').pipe(fs.createWriteStream('newLog.log')); 

この方法で唯一の問題は、「cp source dest」と比較して5倍の時間がかかります。完全なテストコードについては、下の付録も参照してください。

ソリューション2:私の最後の、 "coreutilsの" を使用して、Node.jsのためのネイティブモジュールを書く:=役に立たない

ソリューション3ソリューション1と遅いのrsync ---情報= progress2 =同じ(cpなどのLinuxソース)またはその他の関数Fast file copy with progress

ソリューション3よりも優れている人はいますか?私はネイティブコードを避けたいですが、それは最も適しているようです。

ありがとうございました!パッケージ推奨またはヒント(すべてのfs **を試してみました)を歓迎します!

付録:

テストコード、パイプや進捗使用:

var path = require('path'); 
var progress = require('progress-stream'); 
var fs = require('fs'); 
var _source = path.resolve('../inc/big.avi');// 1.5GB 
var _target= '/tmp/a.avi'; 

var stat = fs.statSync(_source); 
var str = progress({ 
    length: stat.size, 
    time: 100 
}); 

str.on('progress', function(progress) { 
    console.log(progress.percentage); 
}); 

function copyFile(source, target, cb) { 
    var cbCalled = false; 


    var rd = fs.createReadStream(source); 
    rd.on("error", function(err) { 
     done(err); 
    }); 

    var wr = fs.createWriteStream(target); 

    wr.on("error", function(err) { 
     done(err); 
    }); 

    wr.on("close", function(ex) { 
     done(); 
    }); 

    rd.pipe(str).pipe(wr); 

    function done(err) { 
     if (!cbCalled) { 
      console.log('done'); 
      cb && cb(err); 
      cbCalled = true; 
     } 
    } 
} 
copyFile(_source,_target); 

更新:速い(!詳細な進行に)C版はここで実装される:https://github.com/MidnightCommander/mc/blob/master/src/filemanager/file.c#L1480を。

+0

Haveあなたはgrunt(grunt-contrib-copyを使って)か、単純な 'require( 'child_process')のどちらかを試しました。 – jperezov

+0

ここであなたの目標は何ですか? Nodeはおそらく 'cp'のようなネイティブツールほど速くないので、あなたはなぜこれを実装したいのかという特定の理由が必要でしょうか? – robertklep

+0

@jperezovはい、他のすべてと同様にやっています。進歩はよかった、ええ! – xamiro

答えて

1

処理が遅くなる側面は、console.logに関連しています。このコードに見てみましょう:にconsole.logで

:にconsole.logなし692.950ms

:382.540ms

ここ

const fs = require('fs'); 
const sourceFile = 'large.exe' 
const destFile = 'large_copy.exe' 

console.time('copying') 
fs.stat(sourceFile, function(err, stat){ 
    const filesize = stat.size 
    let bytesCopied = 0 

    const readStream = fs.createReadStream(sourceFile) 

    readStream.on('data', function(buffer){ 
    bytesCopied+= buffer.length 
    let porcentage = ((bytesCopied/filesize)*100).toFixed(2) 
    console.log(porcentage+'%') // run once with this and later with this line commented 
    }) 
    readStream.on('end', function(){ 
    console.timeEnd('copying') 
    }) 
    readStream.pipe(fs.createWriteStream(destFile)); 
}) 

は、400メガバイトのファイルをコピーし、実行時間があります

関連する問題