gecko/toolkit/components/downloads/test/unit/test_download_samename.js
Wes Johnston dfa1b6443c Bug 593815 - Tests for download files with the same name. [r=sdwilsh, a=blocker]
--HG--
extra : rebase_source : a2fc4fc7080afe15d2359ea454153f3faf8d4d4b
2010-11-22 19:36:42 -08:00

148 lines
5.0 KiB
JavaScript

/* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */
// This file tests Bug 593815 - specifically that after downloading two files
// with the same name, the download manager still points to the correct files
Components.utils.import("resource://gre/modules/Services.jsm");
Components.utils.import("resource://gre/modules/NetUtil.jsm");
do_load_manifest("test_downloads.manifest");
let httpserver = null;
let currentTest = 0;
function WindowContext() { }
WindowContext.prototype = {
QueryInterface: XPCOMUtils.generateQI([Ci.nsIInterfaceRequestor]),
getInterface: XPCOMUtils.generateQI([Ci.nsIURIContentListener,
Ci.nsILoadGroup]),
/* nsIURIContentListener */
onStartURIOpen: function (uri) { },
isPreferred: function (type, desiredtype) { return false; },
/* nsILoadGroup */
addRequest: function (request, context) { },
removeRequest: function (request, context, status) { }
};
let DownloadListener = {
set: null,
prevFiles : [],
init: function () {
Services.obs.addObserver(this, "dl-start", true);
Services.obs.addObserver(this, "dl-done", true);
},
observe: function (aSubject, aTopic, aData) {
if (aTopic == "dl-start") {
// pause the download if requested
if (this.set.doPause) {
let dl = aSubject.QueryInterface(Ci.nsIDownload);
downloadUtils.downloadManager.pauseDownload(dl.id);
do_timeout(1000, function() {
downloadUtils.downloadManager.resumeDownload(dl.id);
});
}
} else if (aTopic == "dl-done") {
// check that no two files have the same filename in the download manager
let file = aSubject.QueryInterface(Ci.nsIDownload).targetFile;
for each (let prevFile in this.prevFiles) {
do_check_neq(file.leafName, prevFile.leafName);
}
this.prevFiles.push(file);
// get the contents of the file
let fis = Cc["@mozilla.org/network/file-input-stream;1"].createInstance(Ci.nsIFileInputStream);
fis.init(file, -1, -1, 0);
var cstream = Cc["@mozilla.org/intl/converter-input-stream;1"].createInstance(Ci.nsIConverterInputStream);
cstream.init(fis, "UTF-8", 0, 0);
let val = "";
let (str = {}) {
let read = 0;
do {
read = cstream.readString(0xffffffff, str);
val += str.value;
} while (read != 0);
}
cstream.close();
// check if the file contents match the expected ones
if (this.set.doPause) {
do_check_eq(val, this.set.data + this.set.data); // files that have been paused have the same data twice
} else {
do_check_eq(val, this.set.data);
}
runNextTest(); // download the next file
}
},
QueryInterface: XPCOMUtils.generateQI([Ci.nsIObserver,
Ci.nsISupportsWeakReference])
}
/*
Each test will download a file from the server.
*/
function runNextTest()
{
if (currentTest == tests.length) {
httpserver.stop(do_test_finished);
return;
}
let set = DownloadListener.set = tests[currentTest];
currentTest++;
let channel = NetUtil.newChannel("http://localhost:4444" + set.serverURL);
let uriloader = Cc["@mozilla.org/uriloader;1"].getService(Ci.nsIURILoader);
uriloader.openURI(channel, true, new WindowContext());
}
// sends the responses for the files. sends the same content twice if we resume
// the download
function getResponse(aSet) {
return function(aMetadata, aResponse) {
aResponse.setHeader("Content-Type", "text/plain", false);
if (aMetadata.hasHeader("Range")) {
var matches = aMetadata.getHeader("Range").match(/^\s*bytes=(\d+)?-(\d+)?\s*$/);
aResponse.setStatusLine(aMetadata.httpVersion, 206, "Partial Content");
aResponse.bodyOutputStream.write(aSet.data, aSet.data.length);
return;
}
aResponse.setHeader("Accept-Ranges", "bytes", false);
aResponse.setHeader("Content-Disposition", "attachment; filename=test.txt;", false);
aResponse.bodyOutputStream.write(aSet.data, aSet.data.length);
}
}
// files to be downloaded. All files will have the same suggested filename, but
// should contain different data. doPause will cause the download to pause and resume
// itself
let tests = [
{ serverURL: "/test1.html", data: "Test data 1", doPause: false },
{ serverURL: "/test2.html", data: "Test data 2", doPause: false },
{ serverURL: "/test3.html", data: "Test data 3", doPause: true }
];
function run_test() {
// setup a download listener to run tests after each download finished
DownloadListener.init();
Services.prefs.setBoolPref("browser.download.manager.showWhenStarting", false);
httpserver = new nsHttpServer();
httpserver.start(4444);
do_test_pending();
// setup files to be download, each with the same suggested filename
// from the server, but with different contents
for(let i = 0; i < tests.length; i++) {
let set = tests[i];
httpserver.registerPathHandler(set.serverURL, getResponse(set));
}
runNextTest(); // start downloading the first file
}