Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

Remove E10S abstraction layer.

  • Loading branch information...
commit 55fccbc04ecb6746163e2481d647ced986519c52 1 parent 6a1a82e
Irakli Gozalishvili Gozala authored
46 packages/api-utils/lib/channel.js
... ... @@ -1,46 +0,0 @@
1   -/* This Source Code Form is subject to the terms of the Mozilla Public
2   - * License, v. 2.0. If a copy of the MPL was not distributed with this
3   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4   -
5   -const { jetpackID } = require('@packaging');
6   -const { when } = require('./unload');
7   -
8   -// TODO: Create a bug report and remove this workaround once it's fixed.
9   -// Only function needs defined in the context of the message manager window
10   -// can be registered via `addMessageListener`.
11   -function listener(callee) {
12   - return function listener() { return callee.apply(this, arguments); };
13   -}
14   -function messageListener(scope, callee) {
15   - return scope ? scope.eval('(' + listener + ')')(callee) : callee
16   -}
17   -
18   -exports.channel = function channel(scope, messageManager, address, raw) {
19   - address = jetpackID + ':' + address
20   - return {
21   - input: function input(next, stop) {
22   - let listener = messageListener(scope, function onMessage(message) {
23   - if (false === next(raw ? message : message.json) && listener) {
24   - messageManager.removeMessageListener(address, listener);
25   - listener = null;
26   - }
27   - });
28   - messageManager.addMessageListener(address, listener);
29   -
30   - // Bug 724433: do not leak `listener` on addon disabling
31   - when(function () {
32   - if (listener) {
33   - messageManager.removeMessageListener(address, listener);
34   - listener = null;
35   - }
36   - });
37   - },
38   - output: function output(data) {
39   - messageManager.sendAsyncMessage(address, data);
40   - },
41   - sync: !messageManager.sendSyncMessage ? null : function sync(data) {
42   - messageManager.sendSyncMessage(address, data);
43   - }
44   - };
45   -};
46   -
45 packages/api-utils/lib/cuddlefish.js
@@ -227,9 +227,7 @@ const Loader = {
227 227 return module.exports;
228 228 },
229 229
230   - // process.process() will eventually cause a call to main() to be evaluated
231   - // in the addon's context. This function loads and executes the addon's
232   - // entry point module.
  230 + // This function loads and executes the addon's entry point module.
233 231 main: function main(id, path) {
234 232 try {
235 233 let uri = this.uriPrefix + path;
@@ -252,47 +250,6 @@ const Loader = {
252 250 throw error;
253 251 }
254 252 },
255   -
256   - // This is the main entry-point: bootstrap.js calls this when the add-on is
257   - // installed. The order of calls is a bit confusing, but here's what
258   - // happens (in temporal order):
259   - // * process.spawn creates a new XUL 'browser' element which will house the
260   - // main addon code. When e10s is active, this uses a real separate OS
261   - // process. When e10s is disabled, this element lives in the one original
262   - // process. Either way, its API is the same.
263   - // * Grab the channel named "require!" and attach a handler which will load
264   - // modules (in the chrome process) when requested to by the addon
265   - // process. This handler uses Loader.require to import the module, then
266   - // calls the module's .initialize() function to connect a new channel.
267   - // The remote caller winds up with a channel reference, which they can
268   - // use to send messages to the newly loaded module. This is for e10s.
269   - // * After the channel handler is attached, process.process() (invoked by
270   - // process.spawn()) will use loadScript() to evaluate code in the
271   - // 'browser' element (which is where the main addon code starts running),
272   - // to do the following:
273   - // * create a Loader, initialized with the same manifest and
274   - // harness-options.json that we've got
275   - // * invoke it's main() method, with the name and path of the addon's
276   - // entry module (which comes from linker via harness-options.js, and is
277   - // usually main.js). That executes main(), above.
278   - // * main() loads the addon's main.js, which executes all top-level
279   - // forms. If the module defines an "exports.main=" function, we invoke
280   - // that too. This is where the addon finally gets to run.
281   - spawn: function spawn(id, path) {
282   - let loader = this;
283   - let process = this.require('api-utils/process');
284   - process.spawn(id, path)(function(addon) {
285   - // Listen to `require!` channel's input messages from the add-on process
286   - // and load modules being required.
287   - addon.channel('require!').input(function({ requirer: { path }, id }) {
288   - try {
289   - Loader.require.call(loader, path, id).initialize(addon.channel(id));
290   - } catch (error) {
291   - this.globals.console.exception(error);
292   - }
293   - });
294   - });
295   - },
296 253 unload: function unload(reason, callback) {
297 254 this.require('api-utils/unload').send(reason, callback);
298 255 }
20 packages/api-utils/lib/env!.js
... ... @@ -1,20 +0,0 @@
1   -/* vim:set ts=2 sw=2 sts=2 expandtab */
2   -/* This Source Code Form is subject to the terms of the Mozilla Public
3   - * License, v. 2.0. If a copy of the MPL was not distributed with this
4   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5   -
6   -const { messageManager } = require("chrome");
7   -const { channel } = require("./channel");
8   -
9   -module.exports = function load(module) {
10   - return {
11   - require: function require(id) {
12   - // Load required module on the chrome process.
13   - channel(messageManager, messageManager, 'require!').sync({
14   - requirer: module,
15   - id: id
16   - });
17   - return channel(messageManager, messageManager, id);
18   - }
19   - };
20   -};
203 packages/api-utils/lib/message-manager.js
... ... @@ -1,203 +0,0 @@
1   -/* This Source Code Form is subject to the terms of the Mozilla Public
2   - * License, v. 2.0. If a copy of the MPL was not distributed with this
3   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4   -
5   -"use strict";
6   -
7   -const BAD_LISTENER = "The event listener must be a function.";
8   -
9   -const { Cc, Ci, Cu, CC } = require("chrome");
10   -const { setTimeout } = require("./timer");
11   -
12   -const { ns } = require("./namespace");
13   -
14   -const { curry, invoke } = require("./functional");
15   -
16   -const Sandbox = require("./sandbox");
17   -
18   -// JSON.stringify is buggy with cross-sandbox values,
19   -// it may return "{}" on functions. Use a replacer to match them correctly.
20   -const jsonFixer = function (k, v) typeof v === "function" ? undefined : v;
21   -
22   -/**
23   - * Defers invoking the function until the current call stack has cleared.
24   - *
25   - * @param {Function} fn
26   - * The function to defer.
27   - *
28   - * @returns {Function}
29   - * The deferred function
30   - */
31   -const defer = function(fn) function() {
32   - setTimeout(invoke, 0, fn, arguments, this)
33   -};
34   -
35   -/**
36   - * Adds a message listener.
37   - * This listener will receive messages sent from the remote frame.
38   - *
39   - * @param {String} name
40   - * The name of the message for which to add a listener.
41   - * @param {Function} listener
42   - * The listener function called when the message is received.
43   - */
44   -function addMessageListener(name, listener) {
45   - if (typeof listener !== "function")
46   - throw new Error(BAD_LISTENER);
47   -
48   - let listeners = frame(this).listeners;
49   -
50   - if (name in listeners) {
51   - if (~listeners[name].indexOf(listener))
52   - return;
53   - } else {
54   - listeners[name] = [];
55   - }
56   -
57   - listeners[name].push(listener);
58   -}
59   -
60   -/**
61   - * Removes a message listener previously added by calling addMessageListener.
62   - *
63   - * @param {String} name
64   - * The name of the message for which to remove a listener.
65   - * @param {Function} listener
66   - * The listener function has to be removed.
67   - */
68   -function removeMessageListener(name, listener) {
69   - if (typeof listener !== "function")
70   - throw new Error(BAD_LISTENER);
71   -
72   - let listeners = frame(this).listeners;
73   -
74   - if (!(name in listeners))
75   - return;
76   -
77   - let index = listeners[name].indexOf(listener);
78   -
79   - if (~index) {
80   - listeners[name].splice(index, 1);
81   - }
82   -}
83   -
84   -/**
85   - * Sends a message to the listeners.
86   - *
87   - * @param {Boolean} sync
88   - * Indicates if the call is synchronous or asynchronous
89   - * @param {String} name
90   - * The name of the message to send to the listeners.
91   - * @param {Object} [data=null]
92   - * A JSON object containing data to be delivered to the listeners.
93   - *
94   - * @returns {Array|undefined}
95   - * An array with the return values of the listeners if `sync` is `true`,
96   - * otherwise `undefined`.
97   - */
98   -function sendMessage(sync, name, data) {
99   - typeof data === "undefined" && (data = null);
100   -
101   - let listeners = frame(frame(this).receiver).listeners;
102   -
103   - let responses = [];
104   -
105   - let returnValue = sync ? responses : undefined;
106   -
107   - if (!(name in listeners))
108   - return returnValue;
109   -
110   - let json = JSON.parse(JSON.stringify(data, jsonFixer));
111   -
112   - for each(let listener in listeners[name]) {
113   - try {
114   - let response = listener.call(null, {
115   - sync : sync,
116   - name : name,
117   - json : json,
118   - target : null
119   - });
120   -
121   - if (sync) {
122   - if (typeof response === "undefined")
123   - responses.push(response);
124   - else
125   - responses.push(JSON.parse(JSON.stringify(response, jsonFixer)));
126   - }
127   -
128   - } catch (e) {
129   - console.exception(e);
130   - }
131   - }
132   - return returnValue;
133   -};
134   -
135   -let sendSyncMessage = curry(sendMessage, true);
136   -let sendAsyncMessage = curry(defer(sendMessage), false);
137   -
138   -let frame = ns({receiver: null, listeners: null});
139   -
140   -/**
141   - * The MessageManager object emulates the Message Manager API, without creating
142   - * new processes. It useful in mono process context, like Fennec.
143   - *
144   - * @see
145   - * https://developer.mozilla.org/en/The_message_manager
146   - */
147   -function MessageManager() {
148   -
149   - let sandbox = Sandbox.sandbox(null, { wantXrays : false });
150   -
151   - Object.defineProperties(sandbox, {
152   - addMessageListener: {value: addMessageListener.bind(sandbox)},
153   -
154   - removeMessageListener: { value: removeMessageListener.bind(sandbox)},
155   -
156   - sendAsyncMessage: {value: sendAsyncMessage.bind(sandbox)},
157   -
158   - sendSyncMessage: { value: sendSyncMessage.bind(sandbox) }
159   - });
160   -
161   - frame(this).receiver = sandbox;
162   - frame(sandbox).receiver = this;
163   -
164   - frame(this).listeners = {};
165   - frame(sandbox).listeners = {};
166   -}
167   -
168   -MessageManager.prototype = {
169   - constructor: MessageManager,
170   -
171   - addMessageListener : addMessageListener,
172   -
173   - removeMessageListener : removeMessageListener,
174   -
175   - sendAsyncMessage : sendAsyncMessage,
176   -
177   - /**
178   - * Loads a script into the remote frame.
179   - *
180   - * @param {String} uri
181   - * The URL of the script to load into the frame; this must be an absolute
182   - * local URL, but data: URLs are supported.
183   - * @param {Boolean} allowDelayedLoad
184   - * Not used.
185   - */
186   - loadFrameScript: function loadFrameScript(uri, async) {
187   - if (arguments.length < loadFrameScript.length)
188   - throw new Error("Not enough arguments");
189   -
190   - let sandbox = frame(this).receiver;
191   -
192   - try {
193   - Sandbox.load(sandbox, uri);
194   - } catch (e) {
195   - console.exception(e)
196   - }
197   - }
198   -}
199   -
200   -Object.freeze(MessageManager);
201   -Object.freeze(MessageManager.prototype);
202   -
203   -exports.MessageManager = MessageManager;
76 packages/api-utils/lib/process.js
... ... @@ -1,76 +0,0 @@
1   -/* This Source Code Form is subject to the terms of the Mozilla Public
2   - * License, v. 2.0. If a copy of the MPL was not distributed with this
3   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4   -
5   -"use strict";
6   -
7   -const { Cc, Ci } = require("chrome");
8   -const { createRemoteBrowser } = require("api-utils/window-utils");
9   -const { channel } = require("./channel");
10   -const packaging = require('@packaging');
11   -const { when } = require('./unload');
12   -const { MessageManager } = require('./message-manager');
13   -
14   -const addonService = '@mozilla.org/addon/service;1' in Cc ?
15   - Cc['@mozilla.org/addon/service;1'].getService(Ci.nsIAddonService) : null
16   -
17   -const ENABLE_E10S = packaging.enable_e10s;
18   -
19   -const isFennec = require("./xul-app").is("Fennec");
20   -
21   -function loadScript(target, uri, sync) {
22   - return 'loadScript' in target ? target.loadScript(uri, sync)
23   - : target.loadFrameScript(uri, sync)
24   -}
25   -
26   -function process(target, id, path, scope) {
27   - // Please note that even though `loadScript`, is executed before channel is
28   - // returned, users still are able to subscribe for messages before any message
29   - // will be sent. That's because `loadScript` queues script execution on the
30   - // other process, which means they will execute async (on the next turn of
31   - // event loop), while the channel for messages is returned immediately (in
32   - // the same turn of event loop).
33   -
34   - let load = loadScript.bind(null, target);
35   -
36   - load(packaging.uriPrefix + packaging.loader, false);
37   - load('data:,' + encodeURIComponent(
38   - 'let loader = Loader.new(' + JSON.stringify(packaging) + ');\n' +
39   - 'loader.main("' + id + '", "' + path + '");'), false);
40   -
41   - when(function (reason) {
42   - // Please note that it's important to unload remote loader
43   - // synchronously (using synchronous frame script), to make sure that we
44   - // don't stop during unload.
45   - // Bug 724433: Take care to nullify all globals set by `cuddlefish.js`
46   - // otherwise, we will leak any still defined global.
47   - // `dump` is set in Loader.new method, `dump = globals.dump;`
48   - load('data:,loader.unload("' + reason + '");' +
49   - 'loader = null; Loader = null; dump = null;', true);
50   - });
51   -
52   - return {
53   - channel: channel.bind(null, scope, target),
54   - loadScript: load
55   - };
56   -}
57   -
58   -exports.spawn = function spawn(id, path) {
59   - return function promise(deliver) {
60   - // If `nsIAddonService` is available we use it to create an add-on process,
61   - // otherwise we fallback to the remote browser's message manager.
62   - if (ENABLE_E10S && addonService) {
63   - console.log('!!!!!!!!!!!!!!!!!!!! Using addon process !!!!!!!!!!!!!!!!!!');
64   - deliver(process(addonService.createAddon(), id, path));
65   - } else if (isFennec) {
66   - deliver(process(new MessageManager(), id, path));
67   - } else {
68   - createRemoteBrowser(ENABLE_E10S)(function(browser) {
69   - let messageManager = browser.QueryInterface(Ci.nsIFrameLoaderOwner).
70   - frameLoader.messageManager
71   - let window = browser.ownerDocument.defaultView;
72   - deliver(process(messageManager, id, path, window));
73   - });
74   - }
75   - };
76   -};
85 packages/api-utils/lib/window-utils.js
@@ -5,8 +5,8 @@
5 5 "use strict";
6 6
7 7 const { Cc, Ci } = require("chrome");
8   -const { EventEmitter } = require('./events'),
9   - { Trait } = require('./traits');
  8 +const { EventEmitter } = require('./events');
  9 +const { Trait } = require('./traits');
10 10 const { when } = require('./unload');
11 11 const { getInnerId, getOuterId } = require('./window-utils');
12 12 const errors = require("./errors");
@@ -15,10 +15,6 @@ const windowWatcher = Cc["@mozilla.org/embedcomp/window-watcher;1"].
15 15 getService(Ci.nsIWindowWatcher);
16 16 const appShellService = Cc["@mozilla.org/appshell/appShellService;1"].
17 17 getService(Ci.nsIAppShellService);
18   -const observers = require('api-utils/observer-service');
19   -
20   -
21   -const XUL = 'http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul';
22 18
23 19 /**
24 20 * An iterator for XUL windows currently in the application.
@@ -196,82 +192,7 @@ exports.isBrowser = isBrowser;
196 192
197 193 exports.hiddenWindow = appShellService.hiddenDOMWindow;
198 194
199   -function createHiddenXULFrame() {
200   - return function promise(deliver) {
201   - let window = appShellService.hiddenDOMWindow;
202   -
203   - // Ensuring waiting for hidden window end of loading
204   - // (The hidden window is still loading on windows/thunderbird)
205   - if (window.document.readyState != "complete") {
206   - window.addEventListener("load", function onload() {
207   - window.removeEventListener("load", onload, false);
208   - // We recurse with same arguments, when the window is ready
209   - promise(deliver);
210   - }, false);
211   - return;
212   - }
213   -
214   - let document = window.document;
215   - let isXMLDoc = (document.contentType == "application/xhtml+xml" ||
216   - document.contentType == "application/vnd.mozilla.xul+xml")
217   -
218   - if (isXMLDoc) {
219   - deliver(window)
220   - }
221   - else {
222   - let frame = document.createElement('iframe');
223   - // This is ugly but we need window for XUL document in order to create
224   - // browser elements.
225   -
226   - // See bug 725323: hiddenWindow URL is different on each mozilla product
227   - let prefs = Cc["@mozilla.org/preferences-service;1"].
228   - getService(Ci.nsIPrefBranch);
229   - let hiddenWindowURL = prefs.getCharPref("browser.hiddenWindowChromeURL", "");
230   -
231   - frame.src = hiddenWindowURL;
232   - frame.setAttribute('src', hiddenWindowURL);
233   - frame.addEventListener('DOMContentLoaded', function onLoad(event) {
234   - frame.removeEventListener('DOMContentLoaded', onLoad, false);
235   - deliver(frame.contentWindow);
236   - }, false);
237   - document.documentElement.appendChild(frame);
238   - }
239   - }
240   -};
241   -exports.createHiddenXULFrame = createHiddenXULFrame;
242   -
243   -function createRemoteBrowser(remote) {
244   - return function promise(deliver) {
245   - createHiddenXULFrame()(function(hiddenWindow) {
246   - let document = hiddenWindow.document;
247   - let browser = document.createElementNS(XUL, "browser");
248   - // Remote="true" enable everything here:
249   - // http://mxr.mozilla.org/mozilla-central/source/content/base/src/nsFrameLoader.cpp#1347
250   - if (remote !== false)
251   - browser.setAttribute("remote","true");
252   - // Type="content" is mandatory to enable stuff here:
253   - // http://mxr.mozilla.org/mozilla-central/source/content/base/src/nsFrameLoader.cpp#1776
254   - browser.setAttribute("type","content");
255   - // We remove XBL binding to avoid execution of code that is not going to work
256   - // because browser has no docShell attribute in remote mode (for example)
257   - browser.setAttribute("style","-moz-binding: none;");
258   - // Flex it in order to be visible (optional, for debug purpose)
259   - browser.setAttribute("flex", "1");
260   - document.documentElement.appendChild(browser);
261   -
262   - // Bug 724433: do not leak this <browser> DOM node
263   - when(function () {
264   - document.documentElement.removeChild(browser);
265   - });
266   -
267   - // Return browser
268   - deliver(browser);
269   - });
270   - };
271   -};
272   -exports.createRemoteBrowser = createRemoteBrowser;
273   -
274   -require("./unload").when(
  195 +when(
275 196 function() {
276 197 gDocsToClose.slice().forEach(
277 198 function(doc) { doc.defaultView.close(); });
600 packages/api-utils/tests/test-message-manager.js
... ... @@ -1,600 +0,0 @@
1   -/* This Source Code Form is subject to the terms of the Mozilla Public
2   - * License, v. 2.0. If a copy of the MPL was not distributed with this
3   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4   -
5   -"use strict";
6   -
7   -const { Loader } = require('./helpers');
8   -
9   -function createMessageManager() {
10   - let loader = Loader(module);
11   - let { MessageManager } = loader.require("api-utils/message-manager");
12   - let frame = loader.sandbox("api-utils/message-manager").frame;
13   -
14   - return [new MessageManager, frame];
15   -}
16   -
17   -
18   -exports["test MessageManager addMessageListener"] =
19   - function(assert) {
20   - let [mm, frame] = createMessageManager();
21   - let remoteFrame = frame(mm).receiver;
22   -
23   - let listeners = frame(mm).listeners;
24   - let remoteListeners = frame(remoteFrame).listeners;
25   -
26   - let topic = "message-topic";
27   -
28   - let listener = function () {};
29   -
30   - assert.equal(topic in listeners, false,
31   - "No listeners for MessageManager");
32   - assert.equal(topic in remoteListeners, false,
33   - "No listeners for Remote Frame");
34   -
35   - mm.addMessageListener(topic, listener);
36   -
37   - assert.deepEqual(listeners[topic], [listener],
38   - "Listener is added properly");
39   - assert.equal(topic in remoteListeners, false,
40   - "No listeners for Remote Frame");
41   - }
42   -
43   -
44   -exports["test MessageManager addMessageListener with duplicates"] =
45   - function(assert) {
46   - let [mm, frame] = createMessageManager();
47   - let topic = "message-topic";
48   - let listeners = frame(mm).listeners;
49   -
50   - let listener = function () {};
51   -
52   - mm.addMessageListener(topic, listener);
53   - mm.addMessageListener(topic, listener);
54   - mm.addMessageListener(topic, listener);
55   -
56   - assert.deepEqual(listeners[topic], [listener],
57   - "Same listener is added only once");
58   - }
59   -
60   -
61   -exports["test MessageManager addMessageListener exceptions"] =
62   - function(assert) {
63   - const BAD_LISTENER = "The event listener must be a function.";
64   -
65   - let [mm, frame] = createMessageManager();
66   - let listeners = frame(mm).listeners;
67   - let topic = "message-topic";
68   -
69   - assert.throws(
70   - function() mm.addMessageListener(),
71   - BAD_LISTENER
72   - );
73   -
74   - assert.throws(
75   - function() mm.addMessageListener(topic),
76   - BAD_LISTENER
77   - );
78   -
79   - assert.throws(
80   - function() mm.addMessageListener(topic, "something-else"),
81   - BAD_LISTENER
82   - );
83   - }
84   -
85   -exports["test MessageManager removeMessageListener"] =
86   - function(assert) {
87   - let [mm, frame] = createMessageManager();
88   - let topic = "message-topic";
89   - let listeners = frame(mm).listeners;
90   -
91   - let listenerA = function () {};
92   - let listenerB = function () {};
93   - let listenerC = function () {};
94   -
95   - mm.removeMessageListener(topic, listenerA);
96   -
97   - assert.deepEqual(listeners, {},
98   - "No listeners yet");
99   -
100   - mm.addMessageListener(topic, listenerA);
101   - mm.addMessageListener(topic, listenerB);
102   - mm.addMessageListener(topic, listenerC);
103   -
104   - mm.removeMessageListener(topic, listenerB);
105   -
106   - assert.deepEqual(listeners[topic], [listenerA, listenerC],
107   - "Listener is removed properly");
108   - }
109   -
110   -
111   -exports["test MessageManager loadFrameScript with data URL"] =
112   - function(assert) {
113   - let [mm, frame] = createMessageManager();
114   -
115   - let remoteFrame = frame(mm).receiver;
116   -
117   - assert.equal("TEST_VALUE" in remoteFrame, false,
118   - "TEST_VALUE is not defined in Remote Frame");
119   -
120   - mm.loadFrameScript("data:, const TEST_VALUE = 77;", true);
121   -
122   - assert.equal(remoteFrame.TEST_VALUE, 77,
123   - "TEST_VALUE is properly defined in Remote Frame");
124   - }
125   -
126   -
127   -exports["test MessageManager loadFrameScript with a File"] =
128   - function(assert) {
129   - let [mm, frame] = createMessageManager();
130   -
131   - let remoteFrame = frame(mm).receiver;
132   -
133   - assert.equal("TEST_VALUE" in remoteFrame, false,
134   - "TEST_VALUE is not defined in Remote Frame");
135   -
136   - mm.loadFrameScript(require("self").data.url("test-message-manager.js"), true);
137   -
138   - assert.equal(remoteFrame.TEST_VALUE, 11,
139   - "TEST_VALUE is properly defined in Remote Frame");
140   - }
141   -
142   -exports["test MessageManager loadFrameScript exception"] =
143   - function(assert) {
144   - let [mm, frame] = createMessageManager();
145   -
146   - let remoteFrame = frame(mm).receiver;
147   -
148   -
149   - assert.throws(
150   - function() mm.loadFrameScript("data:, const TEST_VALUE = 77;"),
151   - "Not enough arguments"
152   - );
153   -
154   - }
155   -
156   -exports["test Remote Frame addMessageListener"] =
157   - function(assert) {
158   - let [mm, frame] = createMessageManager();
159   - let remoteFrame = frame(mm).receiver;
160   -
161   - let listeners = frame(remoteFrame).listeners;
162   - let managerListeners = frame(mm).listeners;
163   -
164   - let topic = "message-topic";
165   -
166   - let listener = function () {};
167   -
168   - assert.equal(topic in listeners, false,
169   - "No listeners for Remote Frame");
170   - assert.equal(topic in managerListeners, false,
171   - "No listeners for MessageManager");
172   -
173   - remoteFrame.addMessageListener(topic, listener);
174   -
175   - assert.deepEqual(listeners[topic], [listener],
176   - "Listener is added properly");
177   - assert.equal(topic in managerListeners, false,
178   - "No listeners for MessageManager");
179   - }
180   -
181   -
182   -exports["test Remote Frame addMessageListener with duplicates"] =
183   - function(assert) {
184   - let [mm, frame] = createMessageManager();
185   -
186   - let remoteFrame = frame(mm).receiver;
187   - let listeners = frame(remoteFrame).listeners;
188   - let topic = "message-topic";
189   -
190   - let listener = function () {};
191   -
192   - assert.equal(topic in listeners, false,
193   - "No listeners in Remote Frame");
194   -
195   - remoteFrame.addMessageListener(topic, listener);
196   - remoteFrame.addMessageListener(topic, listener);
197   - remoteFrame.addMessageListener(topic, listener);
198   -
199   - assert.deepEqual(listeners[topic], [listener],
200   - "Listener is added properly");
201   - }
202   -
203   -
204   -exports["test Remote Frame addMessageListener exceptions"] =
205   - function(assert) {
206   - const BAD_LISTENER = "The event listener must be a function.";
207   -
208   - let [mm, frame] = createMessageManager();
209   - let remoteFrame = frame(mm).receiver;
210   - let listeners = frame(remoteFrame).listeners;
211   - let topic = "message-topic";
212   -
213   - assert.throws(
214   - function() mm.addMessageListener(),
215   - BAD_LISTENER
216   - );
217   -
218   - assert.throws(
219   - function() mm.addMessageListener(topic),
220   - BAD_LISTENER
221   - );
222   -
223   - assert.throws(
224   - function() mm.addMessageListener(topic, "something-else"),
225   - BAD_LISTENER
226   - );
227   - }
228   -
229   -
230   -exports["test Remote Frame removeMessageListener"] =
231   - function(assert) {
232   - let [mm, frame] = createMessageManager();
233   -
234   - let remoteFrame = frame(mm).receiver;
235   - let listeners = frame(remoteFrame).listeners;
236   -
237   - let topic = "message-topic";
238   -
239   - let listenerA = function () {};
240   - let listenerB = function () {};
241   - let listenerC = function () {};
242   -
243   - remoteFrame.removeMessageListener(topic, listenerA);
244   -
245   - assert.deepEqual(listeners, {},
246   - "No listeners yet");
247   -
248   - remoteFrame.addMessageListener(topic, listenerA);
249   - remoteFrame.addMessageListener(topic, listenerB);
250   - remoteFrame.addMessageListener(topic, listenerC);
251   -
252   - remoteFrame.removeMessageListener(topic, listenerB);
253   -
254   - assert.deepEqual(listeners[topic], [listenerA, listenerC],
255   - "Listener is removed properly");
256   - }
257   -
258   -
259   -exports["test MessageManager sendAsyncMessage"] =
260   - function(assert, done) {
261   - let [mm, frame] = createMessageManager();
262   -
263   - let remoteFrame = frame(mm).receiver;
264   - let calls = 0;
265   -
266   - let topic = "message-topic";
267   -
268   - let listener = function(data) {
269   - calls++;
270   -
271   - assert.deepEqual(data, {
272   - sync : false,
273   - name : topic,
274   - json : {foo : "bar"},
275   - target : null
276   - }, "Data received as expected");
277   -
278   - assert.equal(calls, 1,
279   - "Listener called once");
280   -
281   - done();
282   - }
283   -
284   - remoteFrame.addMessageListener(topic, listener);
285   -
286   - let response = mm.sendAsyncMessage(topic, {foo : "bar"});
287   -
288   - assert.strictEqual(response, undefined,
289   - "No response for async messages");
290   -
291   - assert.equal(calls, 0,
292   - "Listener not called yet");
293   - }
294   -
295   -exports["test MessageManager sendAsyncMessage without listeners"] =
296   - function(assert) {
297   - let [mm, frame] = createMessageManager();
298   -
299   - let remoteFrame = frame(mm).receiver;
300   -
301   - let topic = "message-topic";
302   -
303   - let response = mm.sendAsyncMessage(topic, {foo : "bar"});
304   -
305   - assert.strictEqual(response, undefined,
306   - "No response for async messages");
307   - }
308   -
309   -
310   -exports["test MessageManager sendAsyncMessage without arguments"] =
311   - function(assert, done) {
312   - let [mm, frame] = createMessageManager();
313   -
314   - let remoteFrame = frame(mm).receiver;
315   - let calls = 0;
316   -
317   - let topic = "message-topic";
318   -
319   - let listener = function(data) {
320   - calls++;
321   -
322   - assert.deepEqual(data, {
323   - sync : false,
324   - name : topic,
325   - json : null,
326   - target : null
327   - }, "Data received as expected");
328   -
329   - assert.equal(calls, 1,
330   - "Listener called once");
331   -
332   - done();
333   - }
334   -
335   - remoteFrame.addMessageListener(topic, listener);
336   -
337   - mm.sendAsyncMessage();
338   -
339   - mm.sendAsyncMessage(topic);
340   -
341   - assert.equal(calls, 0,
342   - "Listener not called yet");
343   - }
344   -
345   -
346   -exports["test Remote Frame sendAsyncMessage"] =
347   - function(assert, done) {
348   - let [mm, frame] = createMessageManager();
349   -
350   - let remoteFrame = frame(mm).receiver;
351   - let calls = 0;
352   -
353   - let topic = "message-topic";
354   -
355   - let listener = function(data) {
356   - calls++;
357   -
358   - assert.deepEqual(data, {
359   - sync : false,
360   - name : topic,
361   - json : {foo : "bar"},
362   - target : null
363   - }, "Data received as expected");
364   -
365   - assert.equal(calls, 1,
366   - "Listener called once");
367   -
368   - done();
369   - }
370   -
371   - mm.addMessageListener(topic, listener);
372   -
373   - let response = remoteFrame.sendAsyncMessage(topic, {foo : "bar"});
374   -
375   - assert.strictEqual(response, undefined,
376   - "No response for async messages");
377   -
378   - assert.equal(calls, 0,
379   - "Listener not called yet");
380   - }
381   -
382   -
383   -exports["test Remote Frame sendAsyncMessage without arguments"] =
384   - function(assert, done) {
385   - let [mm, frame] = createMessageManager();
386   -
387   - let remoteFrame = frame(mm).receiver;
388   - let calls = 0;
389   -
390   - let topic = "message-topic";
391   -
392   - let listener = function(data) {
393   - calls++;
394   -
395   - assert.deepEqual(data, {
396   - sync : false,
397   - name : topic,
398   - json : null,
399   - target : null
400   - }, "Data received as expected");
401   -
402   - assert.equal(calls, 1,
403   - "Listener called once");
404   -
405   - done();
406   - }
407   -
408   - mm.addMessageListener(topic, listener);
409   -
410   - remoteFrame.sendAsyncMessage();
411   -
412   - remoteFrame.sendAsyncMessage(topic);
413   -
414   - assert.equal(calls, 0,
415   - "Listener not called yet");
416   - }
417   -
418   -exports["test Remote Frame sendAsyncMessage without listeners"] =
419   - function(assert) {
420   - let [mm, frame] = createMessageManager();
421   -
422   - let remoteFrame = frame(mm).receiver;
423   -
424   - let topic = "message-topic";
425   -
426   - let response = remoteFrame.sendAsyncMessage(topic, {foo : "bar"});
427   -
428   - assert.strictEqual(response, undefined,
429   - "No response for async messages");
430   - }
431   -
432   -exports["test Remote Frame sendSyncMessage"] =
433   - function(assert) {
434   - let [mm, frame] = createMessageManager();
435   -
436   - let remoteFrame = frame(mm).receiver;
437   -
438   - let topic = "message-topic";
439   -
440   - let expectedData = {
441   - sync : true,
442   - name : topic,
443   - json : {foo : "bar"},
444   - target : null
445   - }
446   -
447   - let listenerA = function(data) {
448   - assert.deepEqual(data, expectedData,
449   - "Data received as expected");
450   -
451   - return "my value";
452   - }
453   -
454   - let listenerB = function(data) {
455   - assert.deepEqual(data, expectedData,
456   - "Data received as expected");
457   -
458   - return {complex : "object", method : function() "not allowed"};
459   - }
460   -
461   - let listenerC = function(data) {
462   - assert.deepEqual(data, expectedData,
463   - "Data received as expected");
464   - }
465   -
466   - mm.addMessageListener(topic, listenerA);
467   - mm.addMessageListener(topic, listenerB);
468   - mm.addMessageListener(topic, listenerC);
469   -
470   - let response = remoteFrame.sendSyncMessage(topic, {foo : "bar"});
471   -
472   - assert.deepEqual(response, ["my value", {complex : "object"}, undefined],
473   - "Response from sync messages as expected");
474   - }
475   -
476   -exports["test Remote Frame sendSyncMessage without arguments"] =
477   - function(assert) {
478   - let [mm, frame] = createMessageManager();
479   -
480   - let remoteFrame = frame(mm).receiver;
481   -
482   - let topic = "message-topic";
483   -
484   - let expectedData = {
485   - sync : true,
486   - name : topic,
487   - json : null,
488   - target : null
489   - }
490   -
491   - let listener = function(data) {
492   - assert.deepEqual(data, expectedData,
493   - "Data received as expected");
494   - }
495   -
496   - mm.addMessageListener(topic, listener);
497   -
498   - let response = remoteFrame.sendSyncMessage();
499   -
500   - assert.deepEqual(response, [],
501   - "Empty response as expected");
502   -
503   - let response = remoteFrame.sendSyncMessage(topic);
504   -
505   - assert.deepEqual(response, [undefined],
506   - "Response from sync messages as expected");
507   - }
508   -
509   -exports["test Remote Frame sendSyncMessage without listeners"] =
510   - function(assert) {
511   - let [mm, frame] = createMessageManager();
512   -
513   - let remoteFrame = frame(mm).receiver;
514   - let obj = {foo : "bar"};
515   -
516   - let topic = "message-topic";
517   -
518   - let response = remoteFrame.sendSyncMessage(topic, obj);
519   -
520   - assert.deepEqual(response, [],
521   - "Response from sync messages as expected");
522   - }
523   -
524   -
525   -exports["test Message Manager / Remote Frame async pipeline"] =
526   - function(assert, done) {
527   - let [mm] = createMessageManager();
528   -
529   - let expectedMessages = ["alpha:remote", "alpha", "omega:remote", "omega"];
530   -
531   - mm.addMessageListener("handshake", function (data) {
532   - let messages = data.json.concat("alpha");
533   -
534   - mm.sendAsyncMessage("shutdown", messages);
535   - });
536   -
537   - mm.addMessageListener("shutdown", function (data) {
538   - let messages = data.json.concat("omega");
539   -
540   - assert.deepEqual(messages, expectedMessages,
541   - "messages delivered in the expected order");
542   -
543   - done();
544   - });
545   -
546   - mm.loadFrameScript(
547   - "data:, \
548   - addMessageListener('handshake', function (data) {\
549   - let messages = data.json.concat('alpha:remote');\
550   - sendAsyncMessage('handshake', messages);\
551   - });\
552   - addMessageListener('shutdown', function (data) {\
553   - let messages = data.json.concat('omega:remote');\
554   - sendAsyncMessage('shutdown', messages);\
555   - });\
556   - ", true);
557   -
558   - mm.sendAsyncMessage("handshake", []);
559   - }
560   -
561   -
562   -exports["test Message Manager / Remote Frame async / sync pipeline"] =
563   - function(assert, done) {
564   - let [mm] = createMessageManager();
565   -
566   - let expectedMessages = ["alpha:remote", "alpha", "omega:remote", "omega"];
567   -
568   - mm.addMessageListener("handshake",
569   - function (data) data.json.concat("alpha")
570   - );
571   -
572   - mm.addMessageListener("shutdown",
573   - function (data) data.json.concat("omega")
574   - );
575   -
576   - mm.addMessageListener("verify", function (data) {
577   -
578   - assert.deepEqual(data.json, expectedMessages,
579   - "messages delivered in the expected order");
580   -
581   - done();
582   - });
583   -
584   - mm.loadFrameScript(
585   - "data:, \
586   - addMessageListener('handshake', function (data) {\
587   - let messages = data.json.concat('alpha:remote');\
588   - \
589   - messages = sendSyncMessage('handshake', messages)[0];\
590   - messages.push('omega:remote');\
591   - messages = sendSyncMessage('shutdown', messages)[0];\
592   - \
593   - sendSyncMessage('verify', messages);\
594   - });\
595   - ", true);
596   -
597   - mm.sendAsyncMessage("handshake", []);
598   - }
599   -
600   -require("test").run(exports);
36 packages/api-utils/tests/test-process.js
... ... @@ -1,36 +0,0 @@
1   -/* This Source Code Form is subject to the terms of the Mozilla Public
2   - * License, v. 2.0. If a copy of the MPL was not distributed with this
3   - * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4   -
5   -"use strict";
6   -