--- a/browser/components/preferences/in-content/tests/browser.ini
+++ b/browser/components/preferences/in-content/tests/browser.ini
@@ -36,16 +36,17 @@ skip-if = !updater
[browser_engines.js]
support-files =
browser_bug1184989_prevent_scrolling_when_preferences_flipped.xul
[browser_change_app_handler.js]
skip-if = os != "win" || (os == "win" && os_version == "6.1")
# This test tests the windows-specific app selection dialog, so can't run on non-Windows.
# Skip the test on Window 7, see the detail at Bug 1381706.
[browser_checkspelling.js]
+[browser_clearSiteData.js]
[browser_connection.js]
[browser_connection_bug388287.js]
[browser_cookies_exceptions.js]
[browser_defaultbrowser_alwayscheck.js]
[browser_healthreport.js]
skip-if = true || !healthreport # Bug 1185403 for the "true"
[browser_homepages_filter_aboutpreferences.js]
[browser_extension_controlled.js]
copy from browser/components/preferences/in-content/tests/browser_siteData.js
copy to browser/components/preferences/in-content/tests/browser_clearSiteData.js
--- a/browser/components/preferences/in-content/tests/browser_siteData.js
+++ b/browser/components/preferences/in-content/tests/browser_clearSiteData.js
@@ -1,64 +1,25 @@
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
-const { classes: Cc, interfaces: Ci, utils: Cu, results: Cr } = Components;
+ChromeUtils.import("resource:///modules/SitePermissions.jsm");
-ChromeUtils.import("resource://gre/modules/XPCOMUtils.jsm");
-/* global sinon */
-Services.scriptloader.loadSubScript("resource://testing-common/sinon-2.3.2.js");
+const { SiteDataManager } = ChromeUtils.import("resource:///modules/SiteDataManager.jsm", {});
+const { DownloadUtils } = ChromeUtils.import("resource://gre/modules/DownloadUtils.jsm", {});
const TEST_QUOTA_USAGE_HOST = "example.com";
const TEST_QUOTA_USAGE_ORIGIN = "https://" + TEST_QUOTA_USAGE_HOST;
const TEST_QUOTA_USAGE_URL = TEST_QUOTA_USAGE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/site_data_test.html";
const TEST_OFFLINE_HOST = "example.org";
const TEST_OFFLINE_ORIGIN = "https://" + TEST_OFFLINE_HOST;
const TEST_OFFLINE_URL = TEST_OFFLINE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/offline/offline.html";
const TEST_SERVICE_WORKER_URL = TEST_OFFLINE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/service_worker_test.html";
-const REMOVE_DIALOG_URL = "chrome://browser/content/preferences/siteDataRemoveSelected.xul";
-
-const { NetUtil } = ChromeUtils.import("resource://gre/modules/NetUtil.jsm", {});
-const { DownloadUtils } = ChromeUtils.import("resource://gre/modules/DownloadUtils.jsm", {});
-const { SiteDataManager } = ChromeUtils.import("resource:///modules/SiteDataManager.jsm", {});
-const { OfflineAppCacheHelper } = ChromeUtils.import("resource:///modules/offlineAppCache.jsm", {});
-
-XPCOMUtils.defineLazyServiceGetter(this, "serviceWorkerManager", "@mozilla.org/serviceworkers/manager;1", "nsIServiceWorkerManager");
-
-const mockOfflineAppCacheHelper = {
- clear: null,
-
- originalClear: null,
-
- register() {
- this.originalClear = OfflineAppCacheHelper.clear;
- this.clear = sinon.spy();
- OfflineAppCacheHelper.clear = this.clear;
- },
-
- unregister() {
- OfflineAppCacheHelper.clear = this.originalClear;
- }
-};
-
-function getPersistentStoragePermStatus(origin) {
- let uri = NetUtil.newURI(origin);
- let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
- return Services.perms.testExactPermissionFromPrincipal(principal, "persistent-storage");
-}
-
-function getQuotaUsage(origin) {
- return new Promise(resolve => {
- let uri = NetUtil.newURI(origin);
- let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
- Services.qms.getUsageForPrincipal(principal, request => resolve(request.result.usage));
- });
-}
// XXX: The intermittent bug 1331851
// The implementation of nsICacheStorageConsumptionObserver must be passed as weak referenced,
// so we must hold this observer here well. If we didn't, there would be a chance that
// in Linux debug test run the observer was released before the operation at gecko was completed
// (may be because of a relatively quicker GC cycle or a relatively slower operation).
// As a result of that, we would never get the cache usage we want so the test would fail from timeout.
const cacheUsageGetter = {
@@ -79,264 +40,166 @@ const cacheUsageGetter = {
cacheUsageGetter._resolve(usage);
},
QueryInterface: XPCOMUtils.generateQI([
Components.interfaces.nsICacheStorageConsumptionObserver,
Components.interfaces.nsISupportsWeakReference
]),
};
-function promiseCookiesCleared() {
- return TestUtils.topicObserved("cookie-changed", (subj, data) => {
- return data === "cleared";
- });
-}
-
-async function loadServiceWorkerTestPage(url) {
- let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, url);
- await BrowserTestUtils.waitForCondition(() => {
- return ContentTask.spawn(tab.linkedBrowser, {}, () =>
- content.document.body.getAttribute("data-test-service-worker-registered") === "true");
- }, `Fail to load service worker test ${url}`);
- await BrowserTestUtils.removeTab(tab);
-}
+async function testClearData(clearSiteData, clearCache) {
+ let quotaURI = Services.io.newURI(TEST_QUOTA_USAGE_ORIGIN);
+ SitePermissions.set(quotaURI, "persistent-storage", SitePermissions.ALLOW);
-function promiseServiceWorkerRegisteredFor(url) {
- return BrowserTestUtils.waitForCondition(() => {
- try {
- let principal = Services.scriptSecurityManager.createCodebasePrincipalFromOrigin(url);
- let sw = serviceWorkerManager.getRegistrationByPrincipal(principal, principal.URI.spec);
- if (sw) {
- ok(true, `Found the service worker registered for ${url}`);
- return true;
- }
- } catch (e) {}
- return false;
- }, `Should register service worker for ${url}`);
-}
-
-function promiseServiceWorkersCleared() {
- return BrowserTestUtils.waitForCondition(() => {
- let serviceWorkers = serviceWorkerManager.getAllRegistrations();
- if (serviceWorkers.length == 0) {
- ok(true, "Cleared all service workers");
- return true;
- }
- return false;
- }, "Should clear all service workers");
-}
-
-registerCleanupFunction(function() {
- delete window.sinon;
- mockOfflineAppCacheHelper.unregister();
-});
-
-// Test listing site using quota usage or site using appcache
-add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
-
- // Open a test site which would save into appcache
+ // Open a test site which saves into appcache.
await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_OFFLINE_URL);
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
- // Open a test site which would save into quota manager
- await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- await waitForEvent(gBrowser.selectedBrowser.contentWindowAsCPOW, "test-indexedDB-done");
+ // Fill indexedDB with test data.
+ // Don't wait for the page to load, to register the content event handler as quickly as possible.
+ // If this test goes intermittent, we might have to tell the page to wait longer before
+ // firing the event.
+ BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL, false);
+ await BrowserTestUtils.waitForContentEvent(
+ gBrowser.selectedBrowser, "test-indexedDB-done", false, null, true);
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
- let updatedPromise = promiseSiteDataManagerSitesUpdated();
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- await updatedPromise;
- await openSiteDataSettingsDialog();
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- let dialog = content.gSubDialog._topDialog;
- let dialogFrame = dialog._frame;
- let frameDoc = dialogFrame.contentDocument;
-
- let siteItems = frameDoc.getElementsByTagName("richlistitem");
- is(siteItems.length, 2, "Should list sites using quota usage or appcache");
-
- let appcacheSite = frameDoc.querySelector(`richlistitem[host="${TEST_OFFLINE_HOST}"]`);
- ok(appcacheSite, "Should list site using appcache");
-
- let qoutaUsageSite = frameDoc.querySelector(`richlistitem[host="${TEST_QUOTA_USAGE_HOST}"]`);
- ok(qoutaUsageSite, "Should list site using quota usage");
-
- // Always remember to clean up
- OfflineAppCacheHelper.clear();
- await new Promise(resolve => {
- let principal = Services.scriptSecurityManager
- .createCodebasePrincipalFromOrigin(TEST_QUOTA_USAGE_ORIGIN);
- let request = Services.qms.clearStoragesForPrincipal(principal, null, true);
- request.callback = resolve;
- });
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
-});
-
-// Test buttons are disabled and loading message shown while updating sites
-add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- let updatedPromise = promiseSiteDataManagerSitesUpdated();
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- await updatedPromise;
-
- let actual = null;
- let expected = null;
- let doc = gBrowser.selectedBrowser.contentDocument;
- let clearBtn = doc.getElementById("clearSiteDataButton");
- let settingsButton = doc.getElementById("siteDataSettings");
- let prefStrBundle = doc.getElementById("bundlePreferences");
- let totalSiteDataSizeLabel = doc.getElementById("totalSiteDataSize");
- is(clearBtn.disabled, false, "Should enable clear button after sites updated");
- is(settingsButton.disabled, false, "Should enable settings button after sites updated");
- await SiteDataManager.getTotalUsage()
- .then(usage => {
- actual = totalSiteDataSizeLabel.textContent;
- expected = prefStrBundle.getFormattedString(
- "totalSiteDataSize", DownloadUtils.convertByteUnits(usage));
- is(actual, expected, "Should show the right total site data size");
- });
-
- Services.obs.notifyObservers(null, "sitedatamanager:updating-sites");
- is(clearBtn.disabled, true, "Should disable clear button while updating sites");
- is(settingsButton.disabled, true, "Should disable settings button while updating sites");
- actual = totalSiteDataSizeLabel.textContent;
- expected = prefStrBundle.getString("loadingSiteDataSize");
- is(actual, expected, "Should show the loading message while updating");
-
- Services.obs.notifyObservers(null, "sitedatamanager:sites-updated");
- is(clearBtn.disabled, false, "Should enable clear button after sites updated");
- is(settingsButton.disabled, false, "Should enable settings button after sites updated");
- await SiteDataManager.getTotalUsage()
- .then(usage => {
- actual = totalSiteDataSizeLabel.textContent;
- expected = prefStrBundle.getFormattedString(
- "totalSiteDataSize", DownloadUtils.convertByteUnits(usage));
- is(actual, expected, "Should show the right total site data size");
- });
-
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
-});
-
-// Test the function of the "Clear All Data" button
-add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- addPersistentStoragePerm(TEST_QUOTA_USAGE_ORIGIN);
-
- await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- await waitForEvent(gBrowser.selectedBrowser.contentWindowAsCPOW, "test-indexedDB-done");
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
+ // Register some service workers.
+ await loadServiceWorkerTestPage(TEST_SERVICE_WORKER_URL);
+ await promiseServiceWorkerRegisteredFor(TEST_SERVICE_WORKER_URL);
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- // Test the initial states
+ // Test the initial states.
let cacheUsage = await cacheUsageGetter.get();
let quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
let totalUsage = await SiteDataManager.getTotalUsage();
Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
Assert.greater(totalUsage, 0, "The total usage should not be 0");
- // Test cancelling "Clear All Data"
- // Click "Clear All Data" button and then cancel
let doc = gBrowser.selectedBrowser.contentDocument;
- let cancelPromise = promiseAlertDialogOpen("cancel");
- let clearBtn = doc.getElementById("clearSiteDataButton");
- clearBtn.doCommand();
- await cancelPromise;
+ let clearSiteDataButton = doc.getElementById("clearSiteDataButton");
+
+ let dialogOpened = promiseLoadSubDialog("chrome://browser/content/preferences/clearSiteData.xul");
+ clearSiteDataButton.doCommand();
+ let dialogWin = await dialogOpened;
+
+ // Convert the usage numbers in the same way the UI does it to assert
+ // that they're displayed in the dialog.
+ let [convertedTotalUsage] = DownloadUtils.convertByteUnits(totalUsage);
+ // For cache we just assert that the right unit (KB, probably) is displayed,
+ // since we've had cache intermittently changing under our feet.
+ let [, convertedCacheUnit] = DownloadUtils.convertByteUnits(cacheUsage);
- // Test the items are not removed
- let status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
- is(status, Ci.nsIPermissionManager.ALLOW_ACTION, "Should not remove permission");
+ let clearSiteDataLabel = dialogWin.document.getElementById("clearSiteDataLabel");
+ let clearCacheLabel = dialogWin.document.getElementById("clearCacheLabel");
+ // The usage details are filled asynchronously, so we assert that they're present by
+ // waiting for them to be filled in.
+ await Promise.all([
+ TestUtils.waitForCondition(
+ () => clearSiteDataLabel.value && clearSiteDataLabel.value.includes(convertedTotalUsage), "Should show the quota usage"),
+ TestUtils.waitForCondition(
+ () => clearCacheLabel.value && clearCacheLabel.value.includes(convertedCacheUnit), "Should show the cache usage")
+ ]);
- cacheUsage = await cacheUsageGetter.get();
- quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
- totalUsage = await SiteDataManager.getTotalUsage();
- Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
- Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
- Assert.greater(totalUsage, 0, "The total usage should not be 0");
- // Test cancelling "Clear All Data" ends
+ // Check the boxes according to our test input.
+ let clearSiteDataCheckbox = dialogWin.document.getElementById("clearSiteData");
+ let clearCacheCheckbox = dialogWin.document.getElementById("clearCache");
+ clearSiteDataCheckbox.checked = clearSiteData;
+ clearCacheCheckbox.checked = clearCache;
+
+ // Some additional promises/assertions to wait for
+ // when deleting site data.
+ let acceptPromise;
+ let updatePromise;
+ let cookiesClearedPromise;
+ if (clearSiteData) {
+ acceptPromise = promiseAlertDialogOpen("accept");
+ updatePromise = promiseSiteDataManagerSitesUpdated();
+ cookiesClearedPromise = promiseCookiesCleared();
+ }
+
+ let dialogClosed = BrowserTestUtils.waitForEvent(dialogWin, "unload");
- // Test accepting "Clear All Data"
- // Click "Clear All Data" button and then accept
- let acceptPromise = promiseAlertDialogOpen("accept");
- let updatePromise = promiseSiteDataManagerSitesUpdated();
- let cookiesClearedPromise = promiseCookiesCleared();
+ let clearButton = dialogWin.document.getElementById("clearButton");
+ if (!clearSiteData && !clearCache) {
+ // Simulate user input on one of the checkboxes to trigger the event listener for
+ // disabling the clearButton.
+ clearCacheCheckbox.doCommand();
+ // Check that the clearButton gets disabled by unchecking both options.
+ await TestUtils.waitForCondition(() => clearButton.disabled, "Clear button should be disabled");
+ let cancelButton = dialogWin.document.getElementById("cancelButton");
+ // Cancel, since we can't delete anything.
+ cancelButton.click();
+ } else {
+ // Delete stuff!
+ clearButton.click();
+ }
- mockOfflineAppCacheHelper.register();
- clearBtn.doCommand();
- await acceptPromise;
- await updatePromise;
- mockOfflineAppCacheHelper.unregister();
+ // For site data we display an extra warning dialog, make sure
+ // to accept it.
+ if (clearSiteData) {
+ await acceptPromise;
+ }
+
+ await dialogClosed;
- // Test all the items are removed
- await cookiesClearedPromise;
+ if (clearCache) {
+ TestUtils.waitForCondition(async function() {
+ let usage = await cacheUsageGetter.get();
+ return usage == 0;
+ }, "The cache usage should be removed");
+ } else {
+ Assert.greater(await cacheUsageGetter.get(), 0, "The cache usage should not be 0");
+ }
- ok(mockOfflineAppCacheHelper.clear.calledOnce, "Should clear app cache");
-
- status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
- is(status, Ci.nsIPermissionManager.UNKNOWN_ACTION, "Should remove permission");
+ if (clearSiteData) {
+ await updatePromise;
+ await cookiesClearedPromise;
+ await promiseServiceWorkersCleared();
- cacheUsage = await cacheUsageGetter.get();
- quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
- totalUsage = await SiteDataManager.getTotalUsage();
- is(cacheUsage, 0, "The cache usage should be removed");
- is(quotaUsage, 0, "The quota usage should be removed");
- is(totalUsage, 0, "The total usage should be removed");
- // Test accepting "Clear All Data" ends
+ TestUtils.waitForCondition(async function() {
+ let usage = await SiteDataManager.getTotalUsage();
+ return usage == 0;
+ }, "The total usage should be removed");
+
+ // Check that the size label in about:preferences updates after we cleared data.
+ await ContentTask.spawn(gBrowser.selectedBrowser, null, async function() {
+ let sizeLabel = content.document.getElementById("totalSiteDataSize");
+
+ await ContentTaskUtils.waitForCondition(
+ () => sizeLabel.textContent.includes("0"), "Site data size label should have updated.");
+ });
+ } else {
+ quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
+ totalUsage = await SiteDataManager.getTotalUsage();
+ Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
+ Assert.greater(totalUsage, 0, "The total usage should not be 0");
+ }
+
+ let desiredPermissionState = clearSiteData ? SitePermissions.UNKNOWN : SitePermissions.ALLOW;
+ let permission = SitePermissions.get(quotaURI, "persistent-storage");
+ is(permission.state, desiredPermissionState, "Should have the correct permission state.");
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
+ await SiteDataManager.removeAll();
+}
+
+// Test opening the "Clear All Data" dialog and cancelling.
+add_task(async function() {
+ await testClearData(false, false);
});
-// Test clearing service wroker through the "Clear All" button
+// Test opening the "Clear All Data" dialog and removing all site data.
add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- // Register a test service
- await loadServiceWorkerTestPage(TEST_SERVICE_WORKER_URL);
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- // Test the initial states
- await promiseServiceWorkerRegisteredFor(TEST_SERVICE_WORKER_URL);
- // Click the "Clear All" button
- let doc = gBrowser.selectedBrowser.contentDocument;
- let clearBtn = doc.getElementById("clearSiteDataButton");
- let acceptPromise = promiseAlertDialogOpen("accept");
- let updatePromise = promiseSiteDataManagerSitesUpdated();
- clearBtn.doCommand();
- await acceptPromise;
- await updatePromise;
- await promiseServiceWorkersCleared();
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
+ await testClearData(true, false);
});
-// Test clearing service wroker through the settings panel
+// Test opening the "Clear All Data" dialog and removing all cache.
add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- // Register a test service worker
- await loadServiceWorkerTestPage(TEST_SERVICE_WORKER_URL);
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- // Test the initial states
- await promiseServiceWorkerRegisteredFor(TEST_SERVICE_WORKER_URL);
- // Open the Site Data Settings panel and remove the site
- await openSiteDataSettingsDialog();
- let acceptRemovePromise = promiseAlertDialogOpen("accept");
- let updatePromise = promiseSiteDataManagerSitesUpdated();
- ContentTask.spawn(gBrowser.selectedBrowser, { TEST_OFFLINE_HOST }, args => {
- let host = args.TEST_OFFLINE_HOST;
- let frameDoc = content.gSubDialog._topDialog._frame.contentDocument;
- let sitesList = frameDoc.getElementById("sitesList");
- let site = sitesList.querySelector(`richlistitem[host="${host}"]`);
- if (site) {
- let removeBtn = frameDoc.getElementById("removeSelected");
- let saveBtn = frameDoc.getElementById("save");
- site.click();
- removeBtn.doCommand();
- saveBtn.doCommand();
- } else {
- ok(false, `Should have one site of ${host}`);
- }
- });
- await acceptRemovePromise;
- await updatePromise;
- await promiseServiceWorkersCleared();
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
+ await testClearData(false, true);
});
+
+// Test opening the "Clear All Data" dialog and removing everything.
+add_task(async function() {
+ await testClearData(true, true);
+});
--- a/browser/components/preferences/in-content/tests/browser_siteData.js
+++ b/browser/components/preferences/in-content/tests/browser_siteData.js
@@ -1,151 +1,44 @@
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
-const { classes: Cc, interfaces: Ci, utils: Cu, results: Cr } = Components;
-
-ChromeUtils.import("resource://gre/modules/XPCOMUtils.jsm");
-/* global sinon */
-Services.scriptloader.loadSubScript("resource://testing-common/sinon-2.3.2.js");
-
const TEST_QUOTA_USAGE_HOST = "example.com";
const TEST_QUOTA_USAGE_ORIGIN = "https://" + TEST_QUOTA_USAGE_HOST;
const TEST_QUOTA_USAGE_URL = TEST_QUOTA_USAGE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/site_data_test.html";
const TEST_OFFLINE_HOST = "example.org";
const TEST_OFFLINE_ORIGIN = "https://" + TEST_OFFLINE_HOST;
const TEST_OFFLINE_URL = TEST_OFFLINE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/offline/offline.html";
const TEST_SERVICE_WORKER_URL = TEST_OFFLINE_ORIGIN + "/browser/browser/components/preferences/in-content/tests/service_worker_test.html";
-const REMOVE_DIALOG_URL = "chrome://browser/content/preferences/siteDataRemoveSelected.xul";
const { NetUtil } = ChromeUtils.import("resource://gre/modules/NetUtil.jsm", {});
const { DownloadUtils } = ChromeUtils.import("resource://gre/modules/DownloadUtils.jsm", {});
const { SiteDataManager } = ChromeUtils.import("resource:///modules/SiteDataManager.jsm", {});
const { OfflineAppCacheHelper } = ChromeUtils.import("resource:///modules/offlineAppCache.jsm", {});
-XPCOMUtils.defineLazyServiceGetter(this, "serviceWorkerManager", "@mozilla.org/serviceworkers/manager;1", "nsIServiceWorkerManager");
-
-const mockOfflineAppCacheHelper = {
- clear: null,
-
- originalClear: null,
-
- register() {
- this.originalClear = OfflineAppCacheHelper.clear;
- this.clear = sinon.spy();
- OfflineAppCacheHelper.clear = this.clear;
- },
-
- unregister() {
- OfflineAppCacheHelper.clear = this.originalClear;
- }
-};
-
function getPersistentStoragePermStatus(origin) {
let uri = NetUtil.newURI(origin);
let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
return Services.perms.testExactPermissionFromPrincipal(principal, "persistent-storage");
}
-function getQuotaUsage(origin) {
- return new Promise(resolve => {
- let uri = NetUtil.newURI(origin);
- let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
- Services.qms.getUsageForPrincipal(principal, request => resolve(request.result.usage));
- });
-}
-
-// XXX: The intermittent bug 1331851
-// The implementation of nsICacheStorageConsumptionObserver must be passed as weak referenced,
-// so we must hold this observer here well. If we didn't, there would be a chance that
-// in Linux debug test run the observer was released before the operation at gecko was completed
-// (may be because of a relatively quicker GC cycle or a relatively slower operation).
-// As a result of that, we would never get the cache usage we want so the test would fail from timeout.
-const cacheUsageGetter = {
- _promise: null,
- _resolve: null,
- get() {
- if (!this._promise) {
- this._promise = new Promise(resolve => {
- this._resolve = resolve;
- Services.cache2.asyncGetDiskConsumption(this);
- });
- }
- return this._promise;
- },
- // nsICacheStorageConsumptionObserver implementations
- onNetworkCacheDiskConsumption(usage) {
- cacheUsageGetter._promise = null;
- cacheUsageGetter._resolve(usage);
- },
- QueryInterface: XPCOMUtils.generateQI([
- Components.interfaces.nsICacheStorageConsumptionObserver,
- Components.interfaces.nsISupportsWeakReference
- ]),
-};
-
-function promiseCookiesCleared() {
- return TestUtils.topicObserved("cookie-changed", (subj, data) => {
- return data === "cleared";
- });
-}
-
-async function loadServiceWorkerTestPage(url) {
- let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, url);
- await BrowserTestUtils.waitForCondition(() => {
- return ContentTask.spawn(tab.linkedBrowser, {}, () =>
- content.document.body.getAttribute("data-test-service-worker-registered") === "true");
- }, `Fail to load service worker test ${url}`);
- await BrowserTestUtils.removeTab(tab);
-}
-
-function promiseServiceWorkerRegisteredFor(url) {
- return BrowserTestUtils.waitForCondition(() => {
- try {
- let principal = Services.scriptSecurityManager.createCodebasePrincipalFromOrigin(url);
- let sw = serviceWorkerManager.getRegistrationByPrincipal(principal, principal.URI.spec);
- if (sw) {
- ok(true, `Found the service worker registered for ${url}`);
- return true;
- }
- } catch (e) {}
- return false;
- }, `Should register service worker for ${url}`);
-}
-
-function promiseServiceWorkersCleared() {
- return BrowserTestUtils.waitForCondition(() => {
- let serviceWorkers = serviceWorkerManager.getAllRegistrations();
- if (serviceWorkers.length == 0) {
- ok(true, "Cleared all service workers");
- return true;
- }
- return false;
- }, "Should clear all service workers");
-}
-
-registerCleanupFunction(function() {
- delete window.sinon;
- mockOfflineAppCacheHelper.unregister();
-});
-
// Test listing site using quota usage or site using appcache
add_task(async function() {
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
// Open a test site which would save into appcache
await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_OFFLINE_URL);
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
// Open a test site which would save into quota manager
- await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- await waitForEvent(gBrowser.selectedBrowser.contentWindowAsCPOW, "test-indexedDB-done");
+ BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
+ await BrowserTestUtils.waitForContentEvent(
+ gBrowser.selectedBrowser, "test-indexedDB-done", false, null, true);
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
let updatedPromise = promiseSiteDataManagerSitesUpdated();
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
await updatedPromise;
await openSiteDataSettingsDialog();
// eslint-disable-next-line mozilla/no-cpows-in-tests
let dialog = content.gSubDialog._topDialog;
@@ -212,107 +105,16 @@ add_task(async function() {
expected = prefStrBundle.getFormattedString(
"totalSiteDataSize", DownloadUtils.convertByteUnits(usage));
is(actual, expected, "Should show the right total site data size");
});
await BrowserTestUtils.removeTab(gBrowser.selectedTab);
});
-// Test the function of the "Clear All Data" button
-add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- addPersistentStoragePerm(TEST_QUOTA_USAGE_ORIGIN);
-
- await BrowserTestUtils.openNewForegroundTab(gBrowser, TEST_QUOTA_USAGE_URL);
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- await waitForEvent(gBrowser.selectedBrowser.contentWindowAsCPOW, "test-indexedDB-done");
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
-
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
-
- // Test the initial states
- let cacheUsage = await cacheUsageGetter.get();
- let quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
- let totalUsage = await SiteDataManager.getTotalUsage();
- Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
- Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
- Assert.greater(totalUsage, 0, "The total usage should not be 0");
-
- // Test cancelling "Clear All Data"
- // Click "Clear All Data" button and then cancel
- let doc = gBrowser.selectedBrowser.contentDocument;
- let cancelPromise = promiseAlertDialogOpen("cancel");
- let clearBtn = doc.getElementById("clearSiteDataButton");
- clearBtn.doCommand();
- await cancelPromise;
-
- // Test the items are not removed
- let status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
- is(status, Ci.nsIPermissionManager.ALLOW_ACTION, "Should not remove permission");
-
- cacheUsage = await cacheUsageGetter.get();
- quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
- totalUsage = await SiteDataManager.getTotalUsage();
- Assert.greater(cacheUsage, 0, "The cache usage should not be 0");
- Assert.greater(quotaUsage, 0, "The quota usage should not be 0");
- Assert.greater(totalUsage, 0, "The total usage should not be 0");
- // Test cancelling "Clear All Data" ends
-
- // Test accepting "Clear All Data"
- // Click "Clear All Data" button and then accept
- let acceptPromise = promiseAlertDialogOpen("accept");
- let updatePromise = promiseSiteDataManagerSitesUpdated();
- let cookiesClearedPromise = promiseCookiesCleared();
-
- mockOfflineAppCacheHelper.register();
- clearBtn.doCommand();
- await acceptPromise;
- await updatePromise;
- mockOfflineAppCacheHelper.unregister();
-
- // Test all the items are removed
- await cookiesClearedPromise;
-
- ok(mockOfflineAppCacheHelper.clear.calledOnce, "Should clear app cache");
-
- status = getPersistentStoragePermStatus(TEST_QUOTA_USAGE_ORIGIN);
- is(status, Ci.nsIPermissionManager.UNKNOWN_ACTION, "Should remove permission");
-
- cacheUsage = await cacheUsageGetter.get();
- quotaUsage = await getQuotaUsage(TEST_QUOTA_USAGE_ORIGIN);
- totalUsage = await SiteDataManager.getTotalUsage();
- is(cacheUsage, 0, "The cache usage should be removed");
- is(quotaUsage, 0, "The quota usage should be removed");
- is(totalUsage, 0, "The total usage should be removed");
- // Test accepting "Clear All Data" ends
-
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
-});
-
-// Test clearing service wroker through the "Clear All" button
-add_task(async function() {
- await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
- // Register a test service
- await loadServiceWorkerTestPage(TEST_SERVICE_WORKER_URL);
- await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
- // Test the initial states
- await promiseServiceWorkerRegisteredFor(TEST_SERVICE_WORKER_URL);
- // Click the "Clear All" button
- let doc = gBrowser.selectedBrowser.contentDocument;
- let clearBtn = doc.getElementById("clearSiteDataButton");
- let acceptPromise = promiseAlertDialogOpen("accept");
- let updatePromise = promiseSiteDataManagerSitesUpdated();
- clearBtn.doCommand();
- await acceptPromise;
- await updatePromise;
- await promiseServiceWorkersCleared();
- await BrowserTestUtils.removeTab(gBrowser.selectedTab);
-});
-
// Test clearing service wroker through the settings panel
add_task(async function() {
await SpecialPowers.pushPrefEnv({set: [["browser.storageManager.enabled", true]]});
// Register a test service worker
await loadServiceWorkerTestPage(TEST_SERVICE_WORKER_URL);
await openPreferencesViaOpenPreferencesAPI("privacy", { leaveOpen: true });
// Test the initial states
await promiseServiceWorkerRegisteredFor(TEST_SERVICE_WORKER_URL);
--- a/browser/components/preferences/in-content/tests/head.js
+++ b/browser/components/preferences/in-content/tests/head.js
@@ -1,13 +1,15 @@
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
ChromeUtils.import("resource://gre/modules/Promise.jsm", this);
+XPCOMUtils.defineLazyServiceGetter(this, "serviceWorkerManager", "@mozilla.org/serviceworkers/manager;1", "nsIServiceWorkerManager");
+
const kDefaultWait = 2000;
function is_hidden(aElement) {
var style = aElement.ownerGlobal.getComputedStyle(aElement);
if (style.display == "none")
return true;
if (style.visibility != "visible")
return true;
@@ -158,22 +160,16 @@ function promiseWindowDialogOpen(buttonA
});
});
}
function promiseAlertDialogOpen(buttonAction) {
return promiseWindowDialogOpen(buttonAction, "chrome://global/content/commonDialog.xul");
}
-function addPersistentStoragePerm(origin) {
- let uri = NetUtil.newURI(origin);
- let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
- Services.perms.addFromPrincipal(principal, "persistent-storage", Ci.nsIPermissionManager.ALLOW_ACTION);
-}
-
function promiseSiteDataManagerSitesUpdated() {
return TestUtils.topicObserved("sitedatamanager:sites-updated", () => true);
}
function openSiteDataSettingsDialog() {
let doc = gBrowser.selectedBrowser.contentDocument;
let settingsBtn = doc.getElementById("siteDataSettings");
let dialogOverlay = content.gSubDialog._preloadDialog._overlay;
@@ -254,8 +250,57 @@ const mockSiteDataManager = {
this.fakeSites = null;
},
unregister() {
this._SiteDataManager._qms = this._originalQMS;
this._SiteDataManager._removeQuotaUsage = this._originalRemoveQuotaUsage;
}
};
+
+function getQuotaUsage(origin) {
+ return new Promise(resolve => {
+ let uri = NetUtil.newURI(origin);
+ let principal = Services.scriptSecurityManager.createCodebasePrincipal(uri, {});
+ Services.qms.getUsageForPrincipal(principal, request => resolve(request.result.usage));
+ });
+}
+
+function promiseCookiesCleared() {
+ return TestUtils.topicObserved("cookie-changed", (subj, data) => {
+ return data === "cleared";
+ });
+}
+
+async function loadServiceWorkerTestPage(url) {
+ let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, url);
+ await BrowserTestUtils.waitForCondition(() => {
+ return ContentTask.spawn(tab.linkedBrowser, {}, () =>
+ content.document.body.getAttribute("data-test-service-worker-registered") === "true");
+ }, `Fail to load service worker test ${url}`);
+ await BrowserTestUtils.removeTab(tab);
+}
+
+function promiseServiceWorkersCleared() {
+ return BrowserTestUtils.waitForCondition(() => {
+ let serviceWorkers = serviceWorkerManager.getAllRegistrations();
+ if (serviceWorkers.length == 0) {
+ ok(true, "Cleared all service workers");
+ return true;
+ }
+ return false;
+ }, "Should clear all service workers");
+}
+
+function promiseServiceWorkerRegisteredFor(url) {
+ return BrowserTestUtils.waitForCondition(() => {
+ try {
+ let principal = Services.scriptSecurityManager.createCodebasePrincipalFromOrigin(url);
+ let sw = serviceWorkerManager.getRegistrationByPrincipal(principal, principal.URI.spec);
+ if (sw) {
+ ok(true, `Found the service worker registered for ${url}`);
+ return true;
+ }
+ } catch (e) {}
+ return false;
+ }, `Should register service worker for ${url}`);
+}
+
--- a/browser/components/preferences/in-content/tests/site_data_test.html
+++ b/browser/components/preferences/in-content/tests/site_data_test.html
@@ -16,14 +16,14 @@
request.onupgradeneeded = function(e) {
let db = e.target.result;
db.createObjectStore("TestStore", { keyPath: "id" });
};
request.onsuccess = function(e) {
let db = e.target.result;
let tx = db.transaction("TestStore", "readwrite");
let store = tx.objectStore("TestStore");
- tx.oncomplete = () => window.dispatchEvent(new Event("test-indexedDB-done"));
+ tx.oncomplete = () => document.dispatchEvent(new CustomEvent("test-indexedDB-done", {bubbles: true, cancelable: false}));
store.put({ id: "test_id", description: "Site Data Test"});
};
</script>
</body>
</html>