Source code

Revision control

Copy as Markdown

Other Tools

Test Info:

"use strict";
const { ExtensionProcessScript } = ChromeUtils.importESModule(
"resource://gre/modules/ExtensionProcessScript.sys.mjs"
);
let experimentAPIs = {
userinputtest: {
schema: "schema.json",
parent: {
scopes: ["addon_parent"],
script: "parent.js",
paths: [["userinputtest"]],
},
child: {
scopes: ["addon_child"],
script: "child.js",
paths: [["userinputtest", "child"]],
},
},
};
let experimentFiles = {
"schema.json": JSON.stringify([
{
namespace: "userinputtest",
functions: [
{
name: "test",
type: "function",
async: true,
requireUserInput: true,
parameters: [],
},
{
name: "child",
type: "function",
async: true,
requireUserInput: true,
parameters: [],
},
],
},
]),
/* globals ExtensionAPI */
"parent.js": () => {
this.userinputtest = class extends ExtensionAPI {
getAPI() {
return {
userinputtest: {
test() {},
},
};
}
};
},
"child.js": () => {
this.userinputtest = class extends ExtensionAPI {
getAPI() {
return {
userinputtest: {
child() {},
},
};
}
};
},
};
// Set the "handlingUserInput" flag for the given extension's background page.
// Returns an RAIIHelper that should be destruct()ed eventually.
function setHandlingUserInput(extension) {
let extensionChild = ExtensionProcessScript.getExtensionChild(extension.id);
let bgwin = null;
for (let view of extensionChild.views) {
if (view.viewType == "background") {
bgwin = view.contentWindow;
break;
}
}
notEqual(bgwin, null, "Found background window for the test extension");
let winutils = bgwin.windowUtils;
return winutils.setHandlingUserInput(true);
}
// Test that the schema requireUserInput flag works correctly for
// proxied api implementations.
add_task(async function test_proxy() {
let extension = ExtensionTestUtils.loadExtension({
isPrivileged: true,
background() {
browser.test.onMessage.addListener(async () => {
try {
await browser.userinputtest.test();
browser.test.sendMessage("result", null);
} catch (err) {
browser.test.sendMessage("result", err.message);
}
});
},
manifest: {
permissions: ["experiments.userinputtest"],
experiment_apis: experimentAPIs,
},
files: experimentFiles,
});
await extension.startup();
extension.sendMessage("test");
let result = await extension.awaitMessage("result");
ok(
/test may only be called from a user input handler/.test(result),
`function failed when not called from a user input handler: ${result}`
);
let handle = setHandlingUserInput(extension);
extension.sendMessage("test");
result = await extension.awaitMessage("result");
equal(
result,
null,
"function succeeded when called from a user input handler"
);
handle.destruct();
await extension.unload();
});
// Test that the schema requireUserInput flag works correctly for
// non-proxied api implementations.
add_task(async function test_local() {
let extension = ExtensionTestUtils.loadExtension({
isPrivileged: true,
background() {
browser.test.onMessage.addListener(async () => {
try {
await browser.userinputtest.child();
browser.test.sendMessage("result", null);
} catch (err) {
browser.test.sendMessage("result", err.message);
}
});
},
manifest: {
experiment_apis: experimentAPIs,
},
files: experimentFiles,
});
await extension.startup();
extension.sendMessage("test");
let result = await extension.awaitMessage("result");
ok(
/child may only be called from a user input handler/.test(result),
`function failed when not called from a user input handler: ${result}`
);
let handle = setHandlingUserInput(extension);
extension.sendMessage("test");
result = await extension.awaitMessage("result");
equal(
result,
null,
"function succeeded when called from a user input handler"
);
handle.destruct();
await extension.unload();
});