dom/downloads/src/DownloadsAPI.jsm

Sat, 03 Jan 2015 20:18:00 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Sat, 03 Jan 2015 20:18:00 +0100
branch
TOR_BUG_3246
changeset 7
129ffea94266
permissions
-rw-r--r--

Conditionally enable double key logic according to:
private browsing mode or privacy.thirdparty.isolate preference and
implement in GetCookieStringCommon and FindCookie where it counts...
With some reservations of how to convince FindCookie users to test
condition and pass a nullptr when disabling double key logic.

michael@0 1 /* This Source Code Form is subject to the terms of the Mozilla Public
michael@0 2 * License, v. 2.0. If a copy of the MPL was not distributed with this
michael@0 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
michael@0 4
michael@0 5 "use strict";
michael@0 6
michael@0 7 const Cc = Components.classes;
michael@0 8 const Ci = Components.interfaces;
michael@0 9 const Cu = Components.utils;
michael@0 10
michael@0 11 this.EXPORTED_SYMBOLS = [];
michael@0 12
michael@0 13 Cu.import("resource://gre/modules/XPCOMUtils.jsm");
michael@0 14 Cu.import("resource://gre/modules/Downloads.jsm");
michael@0 15 Cu.import("resource://gre/modules/Task.jsm");
michael@0 16
michael@0 17 XPCOMUtils.defineLazyServiceGetter(this, "ppmm",
michael@0 18 "@mozilla.org/parentprocessmessagemanager;1",
michael@0 19 "nsIMessageBroadcaster");
michael@0 20
michael@0 21 function debug(aStr) {
michael@0 22 #ifdef MOZ_DEBUG
michael@0 23 dump("-*- DownloadsAPI.jsm : " + aStr + "\n");
michael@0 24 #endif
michael@0 25 }
michael@0 26
michael@0 27 function sendPromiseMessage(aMm, aMessageName, aData, aError) {
michael@0 28 debug("sendPromiseMessage " + aMessageName);
michael@0 29 let msg = {
michael@0 30 id: aData.id,
michael@0 31 promiseId: aData.promiseId
michael@0 32 };
michael@0 33
michael@0 34 if (aError) {
michael@0 35 msg.error = aError;
michael@0 36 }
michael@0 37
michael@0 38 aMm.sendAsyncMessage(aMessageName, msg);
michael@0 39 }
michael@0 40
michael@0 41 let DownloadsAPI = {
michael@0 42 init: function() {
michael@0 43 debug("init");
michael@0 44
michael@0 45 this._ids = new WeakMap(); // Maps toolkit download objects to ids.
michael@0 46 this._index = {}; // Maps ids to downloads.
michael@0 47
michael@0 48 ["Downloads:GetList",
michael@0 49 "Downloads:ClearAllDone",
michael@0 50 "Downloads:Remove",
michael@0 51 "Downloads:Pause",
michael@0 52 "Downloads:Resume"].forEach((msgName) => {
michael@0 53 ppmm.addMessageListener(msgName, this);
michael@0 54 });
michael@0 55
michael@0 56 let self = this;
michael@0 57 Task.spawn(function () {
michael@0 58 let list = yield Downloads.getList(Downloads.ALL);
michael@0 59 yield list.addView(self);
michael@0 60
michael@0 61 debug("view added to download list.");
michael@0 62 }).then(null, Components.utils.reportError);
michael@0 63
michael@0 64 this._currentId = 0;
michael@0 65 },
michael@0 66
michael@0 67 /**
michael@0 68 * Returns a unique id for each download, hashing the url and the path.
michael@0 69 */
michael@0 70 downloadId: function(aDownload) {
michael@0 71 let id = this._ids.get(aDownload, null);
michael@0 72 if (!id) {
michael@0 73 id = "download-" + this._currentId++;
michael@0 74 this._ids.set(aDownload, id);
michael@0 75 this._index[id] = aDownload;
michael@0 76 }
michael@0 77 return id;
michael@0 78 },
michael@0 79
michael@0 80 getDownloadById: function(aId) {
michael@0 81 return this._index[aId];
michael@0 82 },
michael@0 83
michael@0 84 /**
michael@0 85 * Converts a download object into a plain json object that we'll
michael@0 86 * send to the DOM side.
michael@0 87 */
michael@0 88 jsonDownload: function(aDownload) {
michael@0 89 let res = {
michael@0 90 totalBytes: aDownload.totalBytes,
michael@0 91 currentBytes: aDownload.currentBytes,
michael@0 92 url: aDownload.source.url,
michael@0 93 path: aDownload.target.path,
michael@0 94 contentType: aDownload.contentType,
michael@0 95 startTime: aDownload.startTime.getTime()
michael@0 96 };
michael@0 97
michael@0 98 if (aDownload.error) {
michael@0 99 res.error = aDownload.error;
michael@0 100 }
michael@0 101
michael@0 102 res.id = this.downloadId(aDownload);
michael@0 103
michael@0 104 // The state of the download. Can be any of "downloading", "stopped",
michael@0 105 // "succeeded", finalized".
michael@0 106
michael@0 107 // Default to "stopped"
michael@0 108 res.state = "stopped";
michael@0 109 if (!aDownload.stopped &&
michael@0 110 !aDownload.canceled &&
michael@0 111 !aDownload.succeeded &&
michael@0 112 !aDownload.DownloadError) {
michael@0 113 res.state = "downloading";
michael@0 114 } else if (aDownload.succeeded) {
michael@0 115 res.state = "succeeded";
michael@0 116 }
michael@0 117 return res;
michael@0 118 },
michael@0 119
michael@0 120 /**
michael@0 121 * download view methods.
michael@0 122 */
michael@0 123 onDownloadAdded: function(aDownload) {
michael@0 124 let download = this.jsonDownload(aDownload);
michael@0 125 debug("onDownloadAdded " + uneval(download));
michael@0 126 ppmm.broadcastAsyncMessage("Downloads:Added", download);
michael@0 127 },
michael@0 128
michael@0 129 onDownloadRemoved: function(aDownload) {
michael@0 130 let download = this.jsonDownload(aDownload);
michael@0 131 download.state = "finalized";
michael@0 132 debug("onDownloadRemoved " + uneval(download));
michael@0 133 ppmm.broadcastAsyncMessage("Downloads:Removed", download);
michael@0 134 this._index[this._ids.get(aDownload)] = null;
michael@0 135 this._ids.delete(aDownload);
michael@0 136 },
michael@0 137
michael@0 138 onDownloadChanged: function(aDownload) {
michael@0 139 let download = this.jsonDownload(aDownload);
michael@0 140 debug("onDownloadChanged " + uneval(download));
michael@0 141 ppmm.broadcastAsyncMessage("Downloads:Changed", download);
michael@0 142 },
michael@0 143
michael@0 144 receiveMessage: function(aMessage) {
michael@0 145 if (!aMessage.target.assertPermission("downloads")) {
michael@0 146 debug("No 'downloads' permission!");
michael@0 147 return;
michael@0 148 }
michael@0 149
michael@0 150 debug("message: " + aMessage.name);
michael@0 151
michael@0 152 switch (aMessage.name) {
michael@0 153 case "Downloads:GetList":
michael@0 154 this.getList(aMessage.data, aMessage.target);
michael@0 155 break;
michael@0 156 case "Downloads:ClearAllDone":
michael@0 157 this.clearAllDone(aMessage.data, aMessage.target);
michael@0 158 break;
michael@0 159 case "Downloads:Remove":
michael@0 160 this.remove(aMessage.data, aMessage.target);
michael@0 161 break;
michael@0 162 case "Downloads:Pause":
michael@0 163 this.pause(aMessage.data, aMessage.target);
michael@0 164 break;
michael@0 165 case "Downloads:Resume":
michael@0 166 this.resume(aMessage.data, aMessage.target);
michael@0 167 break;
michael@0 168 default:
michael@0 169 debug("Invalid message: " + aMessage.name);
michael@0 170 }
michael@0 171 },
michael@0 172
michael@0 173 getList: function(aData, aMm) {
michael@0 174 debug("getList called!");
michael@0 175 let self = this;
michael@0 176 Task.spawn(function () {
michael@0 177 let list = yield Downloads.getList(Downloads.ALL);
michael@0 178 let downloads = yield list.getAll();
michael@0 179 let res = [];
michael@0 180 downloads.forEach((aDownload) => {
michael@0 181 res.push(self.jsonDownload(aDownload));
michael@0 182 });
michael@0 183 aMm.sendAsyncMessage("Downloads:GetList:Return", res);
michael@0 184 }).then(null, Components.utils.reportError);
michael@0 185 },
michael@0 186
michael@0 187 clearAllDone: function(aData, aMm) {
michael@0 188 debug("clearAllDone called!");
michael@0 189 let self = this;
michael@0 190 Task.spawn(function () {
michael@0 191 let list = yield Downloads.getList(Downloads.ALL);
michael@0 192 yield list.removeFinished();
michael@0 193 list = yield Downloads.getList(Downloads.ALL);
michael@0 194 let downloads = yield list.getAll();
michael@0 195 let res = [];
michael@0 196 downloads.forEach((aDownload) => {
michael@0 197 res.push(self.jsonDownload(aDownload));
michael@0 198 });
michael@0 199 aMm.sendAsyncMessage("Downloads:ClearAllDone:Return", res);
michael@0 200 }).then(null, Components.utils.reportError);
michael@0 201 },
michael@0 202
michael@0 203 remove: function(aData, aMm) {
michael@0 204 debug("remove id " + aData.id);
michael@0 205 let download = this.getDownloadById(aData.id);
michael@0 206 if (!download) {
michael@0 207 sendPromiseMessage(aMm, "Downloads:Remove:Return",
michael@0 208 aData, "NoSuchDownload");
michael@0 209 return;
michael@0 210 }
michael@0 211
michael@0 212 Task.spawn(function() {
michael@0 213 yield download.finalize(true);
michael@0 214 let list = yield Downloads.getList(Downloads.ALL);
michael@0 215 yield list.remove(download);
michael@0 216 }).then(
michael@0 217 function() {
michael@0 218 sendPromiseMessage(aMm, "Downloads:Remove:Return", aData);
michael@0 219 },
michael@0 220 function() {
michael@0 221 sendPromiseMessage(aMm, "Downloads:Remove:Return",
michael@0 222 aData, "RemoveError");
michael@0 223 }
michael@0 224 );
michael@0 225 },
michael@0 226
michael@0 227 pause: function(aData, aMm) {
michael@0 228 debug("pause id " + aData.id);
michael@0 229 let download = this.getDownloadById(aData.id);
michael@0 230 if (!download) {
michael@0 231 sendPromiseMessage(aMm, "Downloads:Pause:Return",
michael@0 232 aData, "NoSuchDownload");
michael@0 233 return;
michael@0 234 }
michael@0 235
michael@0 236 download.cancel().then(
michael@0 237 function() {
michael@0 238 sendPromiseMessage(aMm, "Downloads:Pause:Return", aData);
michael@0 239 },
michael@0 240 function() {
michael@0 241 sendPromiseMessage(aMm, "Downloads:Pause:Return",
michael@0 242 aData, "PauseError");
michael@0 243 }
michael@0 244 );
michael@0 245 },
michael@0 246
michael@0 247 resume: function(aData, aMm) {
michael@0 248 debug("resume id " + aData.id);
michael@0 249 let download = this.getDownloadById(aData.id);
michael@0 250 if (!download) {
michael@0 251 sendPromiseMessage(aMm, "Downloads:Resume:Return",
michael@0 252 aData, "NoSuchDownload");
michael@0 253 return;
michael@0 254 }
michael@0 255
michael@0 256 download.start().then(
michael@0 257 function() {
michael@0 258 sendPromiseMessage(aMm, "Downloads:Resume:Return", aData);
michael@0 259 },
michael@0 260 function() {
michael@0 261 sendPromiseMessage(aMm, "Downloads:Resume:Return",
michael@0 262 aData, "ResumeError");
michael@0 263 }
michael@0 264 );
michael@0 265 }
michael@0 266 };
michael@0 267
michael@0 268 DownloadsAPI.init();

mercurial