summaryrefslogtreecommitdiffstats
path: root/services/fxaccounts/tests/xpcshell/test_device.js
diff options
context:
space:
mode:
Diffstat (limited to 'services/fxaccounts/tests/xpcshell/test_device.js')
-rw-r--r--services/fxaccounts/tests/xpcshell/test_device.js127
1 files changed, 127 insertions, 0 deletions
diff --git a/services/fxaccounts/tests/xpcshell/test_device.js b/services/fxaccounts/tests/xpcshell/test_device.js
new file mode 100644
index 0000000000..a7793fd856
--- /dev/null
+++ b/services/fxaccounts/tests/xpcshell/test_device.js
@@ -0,0 +1,127 @@
+/* Any copyright is dedicated to the Public Domain.
+ * http://creativecommons.org/publicdomain/zero/1.0/ */
+
+"use strict";
+
+const { getFxAccountsSingleton } = ChromeUtils.importESModule(
+ "resource://gre/modules/FxAccounts.sys.mjs"
+);
+const fxAccounts = getFxAccountsSingleton();
+
+const { ON_NEW_DEVICE_ID, PREF_ACCOUNT_ROOT } = ChromeUtils.import(
+ "resource://gre/modules/FxAccountsCommon.js"
+);
+
+function promiseObserved(topic) {
+ return new Promise(res => {
+ Services.obs.addObserver(res, topic);
+ });
+}
+
+_("Misc tests for FxAccounts.device");
+
+fxAccounts.device._checkRemoteCommandsUpdateNeeded = async () => false;
+
+add_test(function test_default_device_name() {
+ // Note that head_helpers overrides getDefaultLocalName - this test is
+ // really just to ensure the actual implementation is sane - we can't
+ // really check the value it uses is correct.
+ // We are just hoping to avoid a repeat of bug 1369285.
+ let def = fxAccounts.device.getDefaultLocalName(); // make sure it doesn't throw.
+ _("default value is " + def);
+ ok(!!def.length);
+
+ // This is obviously tied to the implementation, but we want early warning
+ // if any of these things fail.
+ // We really want one of these 2 to provide a value.
+ let hostname = Services.sysinfo.get("device") || Services.dns.myHostName;
+ _("hostname is " + hostname);
+ ok(!!hostname.length);
+ // the hostname should be in the default.
+ ok(def.includes(hostname));
+ // We expect the following to work as a fallback to the above.
+ let fallback = Cc["@mozilla.org/network/protocol;1?name=http"].getService(
+ Ci.nsIHttpProtocolHandler
+ ).oscpu;
+ _("UA fallback is " + fallback);
+ ok(!!fallback.length);
+ // the fallback should not be in the default
+ ok(!def.includes(fallback));
+
+ run_next_test();
+});
+
+add_test(function test_migration() {
+ Services.prefs.clearUserPref("identity.fxaccounts.account.device.name");
+ Services.prefs.setStringPref("services.sync.client.name", "my client name");
+ // calling getLocalName() should move the name to the new pref and reset the old.
+ equal(fxAccounts.device.getLocalName(), "my client name");
+ equal(
+ Services.prefs.getStringPref("identity.fxaccounts.account.device.name"),
+ "my client name"
+ );
+ ok(!Services.prefs.prefHasUserValue("services.sync.client.name"));
+ run_next_test();
+});
+
+add_test(function test_migration_set_before_get() {
+ Services.prefs.setStringPref("services.sync.client.name", "old client name");
+ fxAccounts.device.setLocalName("new client name");
+ equal(fxAccounts.device.getLocalName(), "new client name");
+ run_next_test();
+});
+
+add_task(async function test_reset() {
+ // We don't test the client name specifically here because the client name
+ // is set as part of signing the user in via the attempt to register the
+ // device.
+ const testPref = PREF_ACCOUNT_ROOT + "test-pref";
+ Services.prefs.setStringPref(testPref, "whatever");
+ let credentials = {
+ email: "foo@example.com",
+ uid: "1234@lcip.org",
+ sessionToken: "dead",
+ verified: true,
+ ...MOCK_ACCOUNT_KEYS,
+ };
+ // FxA will try to register its device record in the background after signin.
+ const registerDevice = sinon
+ .stub(fxAccounts._internal.fxAccountsClient, "registerDevice")
+ .callsFake(async () => {
+ return { id: "foo" };
+ });
+ await fxAccounts._internal.setSignedInUser(credentials);
+ // wait for device registration to complete.
+ await promiseObserved(ON_NEW_DEVICE_ID);
+ ok(!Services.prefs.prefHasUserValue(testPref));
+ // signing the user out should reset the name pref.
+ const namePref = PREF_ACCOUNT_ROOT + "device.name";
+ ok(Services.prefs.prefHasUserValue(namePref));
+ await fxAccounts.signOut(/* localOnly = */ true);
+ ok(!Services.prefs.prefHasUserValue(namePref));
+ registerDevice.restore();
+});
+
+add_task(async function test_name_sanitization() {
+ fxAccounts.device.setLocalName("emoji is valid \u2665");
+ Assert.equal(fxAccounts.device.getLocalName(), "emoji is valid \u2665");
+
+ let invalid = "x\uFFFD\n\r\t" + "x".repeat(255);
+ let sanitized = "x\uFFFD\uFFFD\uFFFD\uFFFD" + "x".repeat(250); // 255 total.
+
+ // If the pref already has the invalid value we still get the valid one back.
+ Services.prefs.setStringPref(
+ "identity.fxaccounts.account.device.name",
+ invalid
+ );
+ Assert.equal(fxAccounts.device.getLocalName(), sanitized);
+
+ // But if we explicitly set it to an invalid name, the sanitized value ends
+ // up in the pref.
+ fxAccounts.device.setLocalName(invalid);
+ Assert.equal(fxAccounts.device.getLocalName(), sanitized);
+ Assert.equal(
+ Services.prefs.getStringPref("identity.fxaccounts.account.device.name"),
+ sanitized
+ );
+});