summaryrefslogtreecommitdiffstats
path: root/toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js
diff options
context:
space:
mode:
Diffstat (limited to 'toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js')
-rw-r--r--toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js173
1 files changed, 173 insertions, 0 deletions
diff --git a/toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js b/toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js
new file mode 100644
index 0000000000..986dc74bc5
--- /dev/null
+++ b/toolkit/components/extensions/test/xpcshell/test_ext_schemas_interactive.js
@@ -0,0 +1,173 @@
+"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(context) {
+ return {
+ userinputtest: {
+ test() {},
+ },
+ };
+ }
+ };
+ },
+
+ "child.js": () => {
+ this.userinputtest = class extends ExtensionAPI {
+ getAPI(context) {
+ 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();
+});