|
1 /* Any copyright is dedicated to the Public Domain. |
|
2 http://creativecommons.org/publicdomain/zero/1.0/ */ |
|
3 |
|
4 // This file tests Bug 593815 - specifically that downloaded files |
|
5 // are cleaned up correctly when a download is cancelled |
|
6 |
|
7 Components.utils.import("resource://gre/modules/Services.jsm"); |
|
8 Components.utils.import("resource://gre/modules/NetUtil.jsm"); |
|
9 do_load_manifest("test_downloads.manifest"); |
|
10 |
|
11 let httpserver = null; |
|
12 let currentTest = 0; |
|
13 |
|
14 function WindowContext() { } |
|
15 WindowContext.prototype = { |
|
16 QueryInterface: XPCOMUtils.generateQI([Ci.nsIInterfaceRequestor]), |
|
17 getInterface: XPCOMUtils.generateQI([Ci.nsIURIContentListener, |
|
18 Ci.nsILoadGroup]), |
|
19 |
|
20 /* nsIURIContentListener */ |
|
21 onStartURIOpen: function (uri) { }, |
|
22 isPreferred: function (type, desiredtype) { return false; }, |
|
23 |
|
24 /* nsILoadGroup */ |
|
25 addRequest: function (request, context) { }, |
|
26 removeRequest: function (request, context, status) { } |
|
27 }; |
|
28 |
|
29 let DownloadListener = { |
|
30 set : null, |
|
31 init: function () { |
|
32 Services.obs.addObserver(this, "dl-start", true); |
|
33 Services.obs.addObserver(this, "dl-done", true); |
|
34 Services.obs.addObserver(this, "dl-cancel", true); |
|
35 Services.obs.addObserver(this, "dl-fail", true); |
|
36 }, |
|
37 |
|
38 // check that relevant cancel operations have been performed |
|
39 // currently this just means removing the target file |
|
40 onCancel: function(aSubject, aTopic, aData) { |
|
41 let dl = aSubject.QueryInterface(Ci.nsIDownload); |
|
42 do_check_false(dl.targetFile.exists()); |
|
43 runNextTest(); |
|
44 }, |
|
45 |
|
46 observe: function (aSubject, aTopic, aData) { |
|
47 switch(aTopic) { |
|
48 case "dl-start" : |
|
49 // cancel, pause, or resume the download |
|
50 // depending on parameters in this.set |
|
51 let dl = aSubject.QueryInterface(Ci.nsIDownload); |
|
52 |
|
53 if (this.set.doPause) { |
|
54 downloadUtils.downloadManager.pauseDownload(dl.id); |
|
55 } |
|
56 |
|
57 if (this.set.doResume) { |
|
58 downloadUtils.downloadManager.resumeDownload(dl.id); |
|
59 } |
|
60 |
|
61 downloadUtils.downloadManager.cancelDownload(dl.id); |
|
62 break; |
|
63 case "dl-cancel" : |
|
64 this.onCancel(aSubject, aTopic, aData); |
|
65 break; |
|
66 case "dl-fail" : |
|
67 do_throw("Download failed"); |
|
68 break; |
|
69 case "dl-done" : |
|
70 do_throw("Download finished"); |
|
71 break; |
|
72 } |
|
73 }, |
|
74 |
|
75 QueryInterface: XPCOMUtils.generateQI([Ci.nsIObserver, |
|
76 Ci.nsISupportsWeakReference]) |
|
77 } |
|
78 |
|
79 // loads the uri given in tests[currentTest] |
|
80 // finishes tests if there are no more test files listed |
|
81 function runNextTest() |
|
82 { |
|
83 if (currentTest == tests.length) { |
|
84 httpserver.stop(do_test_finished); |
|
85 return; |
|
86 } |
|
87 |
|
88 let set = DownloadListener.set = tests[currentTest]; |
|
89 currentTest++; |
|
90 |
|
91 let channel = NetUtil.newChannel("http://localhost:" + |
|
92 httpserver.identity.primaryPort + |
|
93 set.serverPath); |
|
94 let uriloader = Cc["@mozilla.org/uriloader;1"].getService(Ci.nsIURILoader); |
|
95 uriloader.openURI(channel, Ci.nsIURILoader.IS_CONTENT_PREFERRED, |
|
96 new WindowContext()); |
|
97 } |
|
98 |
|
99 // sends the responses for the files. sends the same content twice if we resume |
|
100 // the download |
|
101 function getResponse(aSet) { |
|
102 return function(aMetadata, aResponse) { |
|
103 aResponse.setHeader("Content-Type", "text/plain", false); |
|
104 if (aMetadata.hasHeader("Range")) { |
|
105 var matches = aMetadata.getHeader("Range").match(/^\s*bytes=(\d+)?-(\d+)?\s*$/); |
|
106 aResponse.setStatusLine(aMetadata.httpVersion, 206, "Partial Content"); |
|
107 aResponse.bodyOutputStream.write(aSet.data, aSet.data.length); |
|
108 return; |
|
109 } |
|
110 aResponse.setHeader("Accept-Ranges", "bytes", false); |
|
111 aResponse.setHeader("Content-Disposition", "attachment; filename=test.txt;", false); |
|
112 aResponse.bodyOutputStream.write(aSet.data, aSet.data.length); |
|
113 } |
|
114 } |
|
115 |
|
116 // files to be downloaded. For these tests, files will be cancelled either: |
|
117 // 1.) during the download |
|
118 // 2.) while they are paused |
|
119 // 3.) after they have been resumed |
|
120 let tests = [ |
|
121 { serverPath: "/test1.html", data: "Test data 1" }, |
|
122 { serverPath: "/test2.html", data: "Test data 2", doPause: true }, |
|
123 { serverPath: "/test3.html", data: "Test data 3", doPause: true, doResume: true}, |
|
124 ]; |
|
125 |
|
126 function run_test() { |
|
127 if (oldDownloadManagerDisabled()) { |
|
128 return; |
|
129 } |
|
130 |
|
131 // setup a download listener to run tests during and after the download |
|
132 DownloadListener.init(); |
|
133 Services.prefs.setBoolPref("browser.download.manager.showWhenStarting", false); |
|
134 |
|
135 httpserver = new HttpServer(); |
|
136 httpserver.start(-1); |
|
137 do_test_pending(); |
|
138 |
|
139 // setup files to be download, each with the same suggested filename |
|
140 // from the server, but with different contents |
|
141 for(let i = 0; i < tests.length; i++) { |
|
142 let set = tests[i]; |
|
143 httpserver.registerPathHandler(set.serverPath, getResponse(set)); |
|
144 } |
|
145 |
|
146 runNextTest(); // start downloading the first file |
|
147 } |