2013-08-19 5 views
19

Ich erstelle einen Updater, der Anwendungsdateien mit dem Knotenmodul request herunterlädt. Wie kann ich chunk.length verwenden, um die verbleibende Dateigröße zu schätzen? Hier ist ein Teil meiner Code:Download-Fortschritt in Node.js mit Anforderung erhalten

var file_url = 'http://foo.com/bar.zip'; 
var out = fs.createWriteStream('baz.zip'); 

var req = request({ 
    method: 'GET', 
    uri: file_url 
}); 

req.pipe(out); 

req.on('data', function (chunk) { 
    console.log(chunk.length); 
}); 

req.on('end', function() { 
    //Do something 
}); 
+0

ich habe innerhalb .zip: node-webkit.app/und wenn ich Daten extrahiere-> KANN NICHT laufen .app mehr:/mein code :: fs.writeFileSync (frameZipFilePath, Daten, "binary"); var zip = neue AdmZip (frameZipFilePath); zip.extractAllTo (Pfad.resolve ("", "tmp"), wahr); – miukki

Antwort

18

Dies sollten Sie die Gesamt erhalten Sie wollen:

req.on('response', function (data) { 
    console.log(data.headers[ 'content-length' ]); 
}); 

erhalte ich eine Inhaltslänge von 9404541

+0

Danke! Ist diese Länge in Bytes? – Harangue

+2

@ J4G Es sollte ja sein: http://stackoverflow.com/a/2773408. –

15
function download(url, callback, encoding){ 
     var request = http.get(url, function(response) { 
      if (encoding){ 
       response.setEncoding(encoding); 
      } 
      var len = parseInt(response.headers['content-length'], 10); 
      var body = ""; 
      var cur = 0; 
      var obj = document.getElementById('js-progress'); 
      var total = len/1048576; //1048576 - bytes in 1Megabyte 

      response.on("data", function(chunk) { 
       body += chunk; 
       cur += chunk.length; 
       obj.innerHTML = "Downloading " + (100.0 * cur/len).toFixed(2) + "% " + (cur/1048576).toFixed(2) + " mb\r" + ".<br/> Total size: " + total.toFixed(2) + " mb"; 
      }); 

      response.on("end", function() { 
       callback(body); 
       obj.innerHTML = "Downloading complete"; 
      }); 

      request.on("error", function(e){ 
       console.log("Error: " + e.message); 
      }); 

     }); 
    }; 
+1

Woher kommt '1048576'? Ist das eine kosmische Konstante? – Sukima

+0

Achten Sie auf die Anzahl der Bytes in einem Mega-Byte. – Sukima

+1

https://www.google.de/search?q=bytes+in+a+Mega-Byte&oq=bytes+in+a+Mega-Byte&aqs=chrome..69i57.1633j0j7&sourceid=chrome&espv=210&es_sm=91&ie=UTF- 8 – miukki

2

ich ein Modul geschrieben, das gerade tut was Sie wollen: status-bar.

var bar = statusBar.create ({ total: res.headers["content-length"] }) 
    .on ("render", function (stats){ 
     websockets.send (stats); 
    }) 

req.pipe (bar); 
+0

Ja, anfangs habe ich Ihr Modul verwendet, aber ich wollte in der GUI mit Websockets einen Fortschrittsbalken für den Benutzer anzeigen können. – Harangue

+0

Sie können das tun. Wenn die Renderfunktion aufgerufen wird, senden Sie die Statusleiste an den Client. Es ist eine Schnur, du kannst alles damit machen. –

+0

Richtig, aber irgendwann ist es einfacher, selbst etwas zu schreiben, als die Zeichenfolge eines anderen Moduls zu analysieren. :) Schätzen Sie den Tipp aber. – Harangue

6

das kühle node-request-progress Modul verwenden, könnten Sie so etwas wie dies in es2015 tun:

import { createWriteStream } from 'fs' 
import request from 'request' 
import progress from 'request-progress' 

progress(request('http://foo.com/bar.zip')) 
.on('progress', state => { 

    console.log(state) 

    /* 
    { 
     percentage: 0.5,  // Overall percentage (between 0 to 1) 
     speed: 554732,   // The download speed in bytes/sec 
     size: { 
     total: 90044871,  // The total payload size in bytes 
     transferred: 27610959 // The transferred payload size in bytes 
     }, 
     time: { 
     elapsed: 36.235,  // The total elapsed seconds since the start (3 decimals) 
     remaining: 81.403  // The remaining seconds to finish (3 decimals) 
     } 
    } 
    */ 

    }) 
    .on('error', err => console.log(err)) 
    .on('end',() => {}) 
    .pipe(createWriteStream('bar.zip')) 
1

Falls jemand will den Fortschritt ohne die Verwendung von anderen Bibliothek aber nur Wunsch wissen, dann können Sie verwenden Sie die folgende Methode:

function downloadFile(file_url , targetPath){ 
    // Save variable to know progress 
    var received_bytes = 0; 
    var total_bytes = 0; 

    var req = request({ 
     method: 'GET', 
     uri: file_url 
    }); 

    var out = fs.createWriteStream(targetPath); 
    req.pipe(out); 

    req.on('response', function (data) { 
     // Change the total bytes value to get progress later. 
     total_bytes = parseInt(data.headers['content-length' ]); 
    }); 

    req.on('data', function(chunk) { 
     // Update the received bytes 
     received_bytes += chunk.length; 

     showProgress(received_bytes, total_bytes); 
    }); 

    req.on('end', function() { 
     alert("File succesfully downloaded"); 
    }); 
} 

function showProgress(received,total){ 
    var percentage = (received * 100)/total; 
    console.log(percentage + "% | " + received + " bytes out of " + total + " bytes."); 
    // 50% | 50000 bytes received out of 100000 bytes. 
} 

downloadFile("https://static.pexels.com/photos/36487/above-adventure-aerial-air.jpg","c:/path/to/local-image.jpg"); 

die received_bytes Variable die Gesamt jeder gesendeten chunk Länge speichert und entsprechend der total_bytes, die Pro Gress ist retrieven.

1

Wenn Sie „Anfrage“ Modul verwenden und wollen Prozentsatz angezeigt Download, ohne zusätzliche Modul zu verwenden, können Sie den folgenden Code verwenden:

function getInstallerFile (installerfileURL) { 

    // Variable to save downloading progress 
    var received_bytes = 0; 
    var total_bytes = 0; 

    var outStream = fs.createWriteStream(INSTALLER_FILE); 

    request 
     .get(installerfileURL) 
      .on('error', function(err) { 
       console.log(err); 
      }) 
      .on('response', function(data) { 
       total_bytes = parseInt(data.headers['content-length']); 
      }) 
      .on('data', function(chunk) { 
       received_bytes += chunk.length; 
       showDownloadingProgress(received_bytes, total_bytes); 
      }) 
      .pipe(outStream); 
}; 

function showDownloadingProgress(received, total) { 
    var percentage = ((received * 100)/total).toFixed(2); 
    process.stdout.write((platform == 'win32') ? "\033[0G": "\r"); 
    process.stdout.write(percentage + "% | " + received + " bytes downloaded out of " + total + " bytes."); 
} 
Verwandte Themen