| // Copyright 2015 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| /** @fileoverview Suite of tests for site-list. */ |
| |
| /** |
| * An example pref with 2 blocked location items and 2 allowed. This pref |
| * is also used for the All Sites category and therefore needs values for |
| * all types, even though some might be blank. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsGeolocation; |
| |
| /** |
| * An example of prefs controlledBy policy. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsControlled; |
| |
| /** |
| * An example pref with mixed schemes (present and absent). |
| * @type {SiteSettingsPref} |
| */ |
| let prefsMixedSchemes; |
| |
| /** |
| * An example pref with exceptions with origins and patterns from |
| * different providers. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsMixedProvider; |
| |
| /** |
| * An example pref with with and without embeddingOrigin. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsMixedEmbeddingOrigin; |
| |
| /** |
| * An example pref with multiple categories and multiple allow/block |
| * state. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsVarious; |
| |
| /** |
| * An example pref with 1 allowed location item. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsOneEnabled; |
| |
| /** |
| * An example pref with 1 blocked location item. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsOneDisabled; |
| |
| /** |
| * An example Cookies pref with 1 in each of the three categories. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsSessionOnly; |
| |
| /** |
| * An example Cookies pref with mixed incognito and regular settings. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsIncognito; |
| |
| /** |
| * An example Javascript pref with a chrome-extension:// scheme. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsChromeExtension; |
| |
| /** |
| * An example Javascript pref for android_sms notification setting. |
| * @type {SiteSettingsPref} |
| */ |
| let prefsAndroidSms; |
| |
| /** |
| * Creates all the test |SiteSettingsPref|s that are needed for the tests in |
| * this file. They are populated after test setup in order to access the |
| * |settings| constants required. |
| */ |
| function populateTestExceptions() { |
| prefsGeolocation = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [ |
| test_util.createRawSiteException('https://bar-allow.com:443'), |
| test_util.createRawSiteException('https://foo-allow.com:443'), |
| test_util.createRawSiteException('https://bar-block.com:443', { |
| setting: settings.ContentSetting.BLOCK, |
| }), |
| test_util.createRawSiteException('https://foo-block.com:443', { |
| setting: settings.ContentSetting.BLOCK, |
| }) |
| ]), |
| ]); |
| |
| prefsControlled = test_util.createSiteSettingsPrefs( |
| [], [test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.PLUGINS, |
| [test_util.createRawSiteException('http://foo-block.com', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.BLOCK, |
| source: settings.SiteSettingSource.POLICY, |
| })])]); |
| |
| prefsMixedSchemes = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [ |
| test_util.createRawSiteException('https://foo-allow.com', { |
| source: settings.SiteSettingSource.POLICY, |
| }), |
| test_util.createRawSiteException('bar-allow.com'), |
| ]), |
| ]); |
| |
| prefsMixedProvider = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [ |
| test_util.createRawSiteException('https://[*.]foo.com', { |
| setting: settings.ContentSetting.BLOCK, |
| source: settings.SiteSettingSource.POLICY, |
| }), |
| test_util.createRawSiteException('https://bar.foo.com', { |
| setting: settings.ContentSetting.BLOCK, |
| source: settings.SiteSettingSource.POLICY, |
| }), |
| test_util.createRawSiteException('https://[*.]foo.com', { |
| setting: settings.ContentSetting.BLOCK, |
| source: settings.SiteSettingSource.POLICY, |
| }) |
| ]), |
| ]); |
| |
| prefsMixedEmbeddingOrigin = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.IMAGES, |
| [ |
| test_util.createRawSiteException('https://foo.com', { |
| embeddingOrigin: 'https://example.com', |
| }), |
| test_util.createRawSiteException('https://bar.com', { |
| embeddingOrigin: '', |
| }) |
| ]), |
| ]); |
| |
| prefsVarious = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [ |
| test_util.createRawSiteException('https://foo.com', { |
| embeddingOrigin: '', |
| }), |
| test_util.createRawSiteException('https://bar.com', { |
| embeddingOrigin: '', |
| }) |
| ]), |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.NOTIFICATIONS, |
| [ |
| test_util.createRawSiteException('https://google.com', { |
| embeddingOrigin: '', |
| }), |
| test_util.createRawSiteException('https://bar.com', { |
| embeddingOrigin: '', |
| }), |
| test_util.createRawSiteException('https://foo.com', { |
| embeddingOrigin: '', |
| }) |
| ]), |
| ]); |
| |
| prefsOneEnabled = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [test_util.createRawSiteException('https://foo-allow.com:443', { |
| embeddingOrigin: '', |
| })]), |
| ]); |
| |
| prefsOneDisabled = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| [test_util.createRawSiteException('https://foo-block.com:443', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.BLOCK, |
| })]), |
| ]); |
| |
| prefsSessionOnly = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.COOKIES, |
| [ |
| test_util.createRawSiteException('http://foo-block.com', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.BLOCK, |
| }), |
| test_util.createRawSiteException('http://foo-allow.com', { |
| embeddingOrigin: '', |
| }), |
| test_util.createRawSiteException('http://foo-session.com', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.SESSION_ONLY, |
| }) |
| ]), |
| ]); |
| |
| prefsIncognito = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.COOKIES, |
| [ |
| // foo.com is blocked for regular sessions. |
| test_util.createRawSiteException('http://foo.com', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.BLOCK, |
| }), |
| // bar.com is an allowed incognito item. |
| test_util.createRawSiteException('http://bar.com', { |
| embeddingOrigin: '', |
| incognito: true, |
| }), |
| // foo.com is allowed in incognito (overridden). |
| test_util.createRawSiteException('http://foo.com', { |
| embeddingOrigin: '', |
| incognito: true, |
| }) |
| ]), |
| ]); |
| |
| prefsChromeExtension = test_util.createSiteSettingsPrefs([], [ |
| test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.JAVASCRIPT, |
| [test_util.createRawSiteException( |
| 'chrome-extension://cfhgfbfpcbnnbibfphagcjmgjfjmojfa/', { |
| embeddingOrigin: '', |
| setting: settings.ContentSetting.BLOCK, |
| })]), |
| ]); |
| |
| prefsGeolocationEmpty = test_util.createSiteSettingsPrefs([], []); |
| |
| prefsAndroidSms = test_util.createSiteSettingsPrefs( |
| [], [test_util.createContentSettingTypeToValuePair( |
| settings.ContentSettingsTypes.NOTIFICATIONS, [ |
| // android sms setting. |
| test_util.createRawSiteException( |
| multidevice.TEST_ANDROID_SMS_ORIGIN), |
| // Non android sms setting that should be handled as usual. |
| test_util.createRawSiteException('http://bar.com') |
| ])]); |
| } |
| |
| suite('SiteList', function() { |
| /** |
| * A site list element created before each test. |
| * @type {SiteList} |
| */ |
| let testElement; |
| |
| /** |
| * The mock proxy object to use during test. |
| * @type {TestSiteSettingsPrefsBrowserProxy} |
| */ |
| let browserProxy = null; |
| |
| /** |
| * Mock MultiDeviceBrowserProxy to use during test. |
| * @type {TestMultideviceBrowserProxy} |
| */ |
| let multiDeviceBrowserProxy = null; |
| |
| suiteSetup(function() { |
| CrSettingsPrefs.setInitialized(); |
| }); |
| |
| suiteTeardown(function() { |
| CrSettingsPrefs.resetForTesting(); |
| }); |
| |
| // Initialize a site-list before each test. |
| setup(function() { |
| populateTestExceptions(); |
| |
| browserProxy = new TestSiteSettingsPrefsBrowserProxy(); |
| settings.SiteSettingsPrefsBrowserProxyImpl.instance_ = browserProxy; |
| PolymerTest.clearBody(); |
| testElement = document.createElement('site-list'); |
| document.body.appendChild(testElement); |
| |
| if (cr.isChromeOS) { |
| multiDeviceBrowserProxy = new multidevice.TestMultideviceBrowserProxy(); |
| settings.MultiDeviceBrowserProxyImpl.instance_ = multiDeviceBrowserProxy; |
| } |
| }); |
| |
| teardown(function() { |
| closeActionMenu(); |
| // The code being tested changes the Route. Reset so that state is not |
| // leaked across tests. |
| settings.resetRouteForTesting(); |
| |
| if (cr.isChromeOS) { |
| // Reset multidevice enabled flag. |
| loadTimeData.overrideValues({ |
| multideviceAllowedByPolicy: false |
| }); |
| } |
| }); |
| |
| /** |
| * Opens the action menu for a particular element in the list. |
| * @param {number} index The index of the child element (which site) to |
| * open the action menu for. |
| */ |
| function openActionMenu(index) { |
| const actionMenuButton = |
| testElement.$.listContainer.querySelectorAll('site-list-entry')[index] |
| .$.actionMenuButton; |
| actionMenuButton.click(); |
| Polymer.dom.flush(); |
| } |
| |
| /** Closes the action menu. */ |
| function closeActionMenu() { |
| const menu = testElement.$$('cr-action-menu'); |
| if (menu.open) |
| menu.close(); |
| } |
| |
| /** |
| * Asserts the menu looks as expected. |
| * @param {Array<string>} items The items expected to show in the menu. |
| */ |
| function assertMenu(items) { |
| const menu = testElement.$$('cr-action-menu'); |
| assertTrue(!!menu); |
| const menuItems = menu.querySelectorAll('button:not([hidden])'); |
| assertEquals(items.length, menuItems.length); |
| for (let i = 0; i < items.length; i++) |
| assertEquals(items[i], menuItems[i].textContent.trim()); |
| } |
| |
| /** |
| * @param {HTMLElement} listContainer Node with the exceptions listed. |
| * @return {boolean} Whether the entry is incognito only. |
| */ |
| function hasAnIncognito(listContainer) { |
| return listContainer.querySelector('iron-list') |
| .items.some(item => item.incognito); |
| } |
| |
| /** |
| * Configures the test element for a particular category. |
| * @param {settings.ContentSettingsTypes} category The category to set up. |
| * @param {settings.ContentSetting} subtype Type of list to use. |
| * @param {Array<dictionary>} prefs The prefs to use. |
| */ |
| function setUpCategory(category, subtype, prefs) { |
| browserProxy.setPrefs(prefs); |
| testElement.categorySubtype = subtype; |
| // Some route is needed, but the actual route doesn't matter. |
| testElement.currentRoute = { |
| page: 'dummy', |
| section: 'privacy', |
| subpage: ['site-settings', 'site-settings-category-location'], |
| }; |
| testElement.category = category; |
| } |
| |
| test('read-only attribute', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsVarious); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| // Flush to be sure list container is populated. |
| Polymer.dom.flush(); |
| const dotsMenu = testElement.$$('site-list-entry') |
| .$$('#actionMenuButtonContainer'); |
| assertFalse(dotsMenu.hidden); |
| testElement.setAttribute('read-only-list', true); |
| Polymer.dom.flush(); |
| assertTrue(dotsMenu.hidden); |
| testElement.removeAttribute('read-only-list'); |
| Polymer.dom.flush(); |
| assertFalse(dotsMenu.hidden); |
| }); |
| }); |
| |
| if (cr.isChromeOS) { |
| test('update androidSmsInfo', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.NOTIFICATIONS, |
| settings.ContentSetting.ALLOW, prefsAndroidSms); |
| assertEquals( |
| 0, multiDeviceBrowserProxy.getCallCount('getAndroidSmsInfo')); |
| |
| loadTimeData.overrideValues({multideviceAllowedByPolicy: true}); |
| setUpCategory( |
| settings.ContentSettingsTypes.NOTIFICATIONS, |
| settings.ContentSetting.ALLOW, prefsAndroidSms); |
| // Assert 2 calls since the observer observes 2 properties. |
| assertEquals( |
| 2, multiDeviceBrowserProxy.getCallCount('getAndroidSmsInfo')); |
| |
| return multiDeviceBrowserProxy.whenCalled('getAndroidSmsInfo') |
| .then(() => browserProxy.whenCalled('getExceptionList')) |
| .then((contentType) => { |
| assertEquals( |
| settings.ContentSettingsTypes.NOTIFICATIONS, contentType); |
| assertEquals(2, testElement.sites.length); |
| |
| assertEquals( |
| prefsAndroidSms.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| assertTrue(testElement.sites[0].showAndroidSmsNote); |
| |
| assertEquals( |
| prefsAndroidSms.exceptions[contentType][1].origin, |
| testElement.sites[1].origin); |
| assertEquals(undefined, testElement.sites[1].showAndroidSmsNote); |
| |
| browserProxy.resetResolver('getExceptionList'); |
| multiDeviceBrowserProxy.setFeatureEnabledState( |
| settings.MultiDeviceFeature.MESSAGES, false); |
| return browserProxy.whenCalled('getExceptionList'); |
| }) |
| .then((contentType) => { |
| assertEquals( |
| settings.ContentSettingsTypes.NOTIFICATIONS, contentType); |
| assertEquals(2, testElement.sites.length); |
| |
| assertEquals( |
| prefsAndroidSms.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| assertEquals(undefined, testElement.sites[0].showAndroidSmsNote); |
| |
| assertEquals( |
| prefsAndroidSms.exceptions[contentType][1].origin, |
| testElement.sites[1].origin); |
| assertEquals(undefined, testElement.sites[1].showAndroidSmsNote); |
| }); |
| }); |
| } |
| |
| test('getExceptionList API used', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocationEmpty); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| assertEquals(settings.ContentSettingsTypes.GEOLOCATION, contentType); |
| }); |
| }); |
| |
| test('Empty list', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocationEmpty); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| assertEquals(settings.ContentSettingsTypes.GEOLOCATION, contentType); |
| |
| assertEquals(0, testElement.sites.length); |
| |
| assertEquals( |
| settings.ContentSetting.ALLOW, testElement.categorySubtype); |
| |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('initial ALLOW state is correct', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| assertEquals(settings.ContentSettingsTypes.GEOLOCATION, contentType); |
| |
| assertEquals(2, testElement.sites.length); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][1].origin, |
| testElement.sites[1].origin); |
| assertEquals( |
| settings.ContentSetting.ALLOW, testElement.categorySubtype); |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| assertMenu(['Block', 'Edit', 'Remove'], testElement); |
| |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('action menu closes when list changes', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocation); |
| const actionMenu = testElement.$$('cr-action-menu'); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| assertTrue(actionMenu.open); |
| |
| browserProxy.resetResolver('getExceptionList'); |
| // Simulate a change in the underlying model. |
| cr.webUIListenerCallback( |
| 'contentSettingSitePermissionChanged', |
| settings.ContentSettingsTypes.GEOLOCATION); |
| return browserProxy.whenCalled('getExceptionList'); |
| }) |
| .then(function() { |
| // Check that the action menu was closed. |
| assertFalse(actionMenu.open); |
| }); |
| }); |
| |
| test('exceptions are not reordered in non-ALL_SITES', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.BLOCK, prefsMixedProvider); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| assertEquals(settings.ContentSettingsTypes.GEOLOCATION, contentType); |
| assertEquals(3, testElement.sites.length); |
| for (let i = 0; i < testElement.sites.length; ++i) { |
| assertEquals( |
| prefsMixedProvider.exceptions[contentType][i].origin, |
| testElement.sites[i].origin); |
| assertEquals( |
| kControlledByLookup[prefsMixedProvider |
| .exceptions[contentType][i] |
| .source] || |
| chrome.settingsPrivate.ControlledBy.PRIMARY_USER, |
| testElement.sites[i].controlledBy); |
| } |
| }); |
| }); |
| |
| test('initial BLOCK state is correct', function() { |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| const categorySubtype = settings.ContentSetting.BLOCK; |
| setUpCategory(contentType, categorySubtype, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertEquals(categorySubtype, testElement.categorySubtype); |
| |
| assertEquals(2, testElement.sites.length); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][2].origin, |
| testElement.sites[0].origin); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][3].origin, |
| testElement.sites[1].origin); |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| assertMenu(['Allow', 'Edit', 'Remove'], testElement); |
| |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('initial SESSION ONLY state is correct', function() { |
| const contentType = settings.ContentSettingsTypes.COOKIES; |
| const categorySubtype = settings.ContentSetting.SESSION_ONLY; |
| setUpCategory(contentType, categorySubtype, prefsSessionOnly); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertEquals(categorySubtype, testElement.categorySubtype); |
| |
| assertEquals(1, testElement.sites.length); |
| assertEquals( |
| prefsSessionOnly.exceptions[contentType][2].origin, |
| testElement.sites[0].origin); |
| |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| assertMenu(['Allow', 'Block', 'Edit', 'Remove'], testElement); |
| |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('update lists for incognito', function() { |
| const contentType = settings.ContentSettingsTypes.PLUGINS; |
| const categorySubtype = settings.ContentSetting.BLOCK; |
| setUpCategory(contentType, categorySubtype, prefsControlled); |
| const list = testElement.$.listContainer; |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| Polymer.dom.flush(); |
| assertEquals(1, list.querySelector('iron-list').items.length); |
| assertFalse(hasAnIncognito(list)); |
| browserProxy.resetResolver('getExceptionList'); |
| browserProxy.setIncognito(true); |
| return browserProxy.whenCalled('getExceptionList'); |
| }) |
| .then(function() { |
| Polymer.dom.flush(); |
| assertEquals(2, list.querySelector('iron-list').items.length); |
| assertTrue(hasAnIncognito(list)); |
| assertTrue(Array.from(list.querySelectorAll('site-list-entry')) |
| .some( |
| entry => entry.$.siteDescription.textContent == |
| 'Current incognito session')); |
| browserProxy.resetResolver('getExceptionList'); |
| browserProxy.setIncognito(false); |
| return browserProxy.whenCalled('getExceptionList'); |
| }) |
| .then(function() { |
| Polymer.dom.flush(); |
| assertEquals(1, list.querySelector('iron-list').items.length); |
| assertFalse(hasAnIncognito(list)); |
| browserProxy.resetResolver('getExceptionList'); |
| browserProxy.setIncognito(true); |
| return browserProxy.whenCalled('getExceptionList'); |
| }) |
| .then(function() { |
| Polymer.dom.flush(); |
| assertEquals(2, list.querySelector('iron-list').items.length); |
| assertTrue(hasAnIncognito(list)); |
| }); |
| }); |
| |
| test('initial INCOGNITO BLOCK state is correct', function() { |
| const contentType = settings.ContentSettingsTypes.COOKIES; |
| const categorySubtype = settings.ContentSetting.BLOCK; |
| setUpCategory(contentType, categorySubtype, prefsIncognito); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertEquals(categorySubtype, testElement.categorySubtype); |
| |
| assertEquals(1, testElement.sites.length); |
| assertEquals( |
| prefsIncognito.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| // 'Clear on exit' is visible as this is not an incognito item. |
| assertMenu(['Allow', 'Clear on exit', 'Edit', 'Remove'], testElement); |
| |
| // Select 'Remove' from menu. |
| const remove = testElement.$.reset; |
| assertTrue(!!remove); |
| remove.click(); |
| return browserProxy.whenCalled('resetCategoryPermissionForPattern'); |
| }) |
| .then(function(args) { |
| assertEquals('http://foo.com', args[0]); |
| assertEquals('', args[1]); |
| assertEquals(contentType, args[2]); |
| assertFalse(args[3]); // Incognito. |
| }); |
| }); |
| |
| test('initial INCOGNITO ALLOW state is correct', function() { |
| const contentType = settings.ContentSettingsTypes.COOKIES; |
| const categorySubtype = settings.ContentSetting.ALLOW; |
| setUpCategory(contentType, categorySubtype, prefsIncognito); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertEquals(categorySubtype, testElement.categorySubtype); |
| |
| assertEquals(2, testElement.sites.length); |
| assertEquals( |
| prefsIncognito.exceptions[contentType][1].origin, |
| testElement.sites[0].origin); |
| assertEquals( |
| prefsIncognito.exceptions[contentType][2].origin, |
| testElement.sites[1].origin); |
| |
| Polymer.dom.flush(); // Populates action menu. |
| openActionMenu(0); |
| // 'Clear on exit' is hidden for incognito items. |
| assertMenu(['Block', 'Edit', 'Remove'], testElement); |
| closeActionMenu(); |
| |
| // Select 'Remove' from menu on 'foo.com'. |
| openActionMenu(1); |
| const remove = testElement.$.reset; |
| assertTrue(!!remove); |
| remove.click(); |
| return browserProxy.whenCalled('resetCategoryPermissionForPattern'); |
| }) |
| .then(function(args) { |
| assertEquals('http://foo.com', args[0]); |
| assertEquals('', args[1]); |
| assertEquals(contentType, args[2]); |
| assertTrue(args[3]); // Incognito. |
| }); |
| }); |
| |
| test('reset button works for read-only content types', function() { |
| testElement.readOnlyList = true; |
| Polymer.dom.flush(); |
| |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| const categorySubtype = settings.ContentSetting.ALLOW; |
| setUpCategory(contentType, categorySubtype, prefsOneEnabled); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertEquals(categorySubtype, testElement.categorySubtype); |
| |
| assertEquals(1, testElement.sites.length); |
| assertEquals( |
| prefsOneEnabled.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| |
| Polymer.dom.flush(); |
| |
| const item = testElement.$$('site-list-entry'); |
| |
| // Assert action button is hidden. |
| const dots = item.$.actionMenuButtonContainer; |
| assertTrue(!!dots); |
| assertTrue(dots.hidden); |
| |
| // Assert reset button is visible. |
| const resetButton = item.$.resetSiteContainer; |
| assertTrue(!!resetButton); |
| assertFalse(resetButton.hidden); |
| |
| resetButton.querySelector('button').click(); |
| return browserProxy.whenCalled('resetCategoryPermissionForPattern'); |
| }) |
| .then(function(args) { |
| assertEquals('https://foo-allow.com:443', args[0]); |
| assertEquals('', args[1]); |
| assertEquals(contentType, args[2]); |
| }); |
| }); |
| |
| test('edit action menu opens edit exception dialog', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.COOKIES, |
| settings.ContentSetting.SESSION_ONLY, prefsSessionOnly); |
| |
| return browserProxy.whenCalled('getExceptionList').then(function() { |
| Polymer.dom.flush(); // Populates action menu. |
| |
| openActionMenu(0); |
| assertMenu(['Allow', 'Block', 'Edit', 'Remove'], testElement); |
| const menu = testElement.$$('cr-action-menu'); |
| assertTrue(menu.open); |
| const edit = testElement.$.edit; |
| assertTrue(!!edit); |
| edit.click(); |
| Polymer.dom.flush(); |
| assertFalse(menu.open); |
| |
| assertTrue(!!testElement.$$('settings-edit-exception-dialog')); |
| }); |
| }); |
| |
| test('edit dialog closes when incognito status changes', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.COOKIES, settings.ContentSetting.BLOCK, |
| prefsSessionOnly); |
| |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function() { |
| Polymer.dom.flush(); // Populates action menu. |
| |
| openActionMenu(0); |
| testElement.$.edit.click(); |
| Polymer.dom.flush(); |
| |
| const dialog = testElement.$$('settings-edit-exception-dialog'); |
| assertTrue(!!dialog); |
| const closeEventPromise = test_util.eventToPromise('close', dialog); |
| browserProxy.setIncognito(true); |
| return closeEventPromise; |
| }) |
| .then(() => { |
| assertFalse(!!testElement.$$('settings-edit-exception-dialog')); |
| }); |
| }); |
| |
| test('list items shown and clickable when data is present', function() { |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.ALLOW, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| |
| // Required for firstItem to be found below. |
| Polymer.dom.flush(); |
| |
| // Validate that the sites gets populated from pre-canned prefs. |
| assertEquals(2, testElement.sites.length); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][0].origin, |
| testElement.sites[0].origin); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][1].origin, |
| testElement.sites[1].origin); |
| assertFalse(!!testElement.selectedOrigin); |
| |
| // Validate that the sites are shown in UI and can be selected. |
| const clickable = testElement.$$('site-list-entry').$$('.middle'); |
| assertTrue(!!clickable); |
| clickable.click(); |
| assertEquals( |
| prefsGeolocation.exceptions[contentType][0].origin, |
| settings.getQueryParameters().get('site')); |
| }); |
| }); |
| |
| test('Block list open when Allow list is empty', function() { |
| // Prefs: One item in Block list, nothing in Allow list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.BLOCK, prefsOneDisabled); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| return test_util.waitForRender(testElement); |
| }) |
| .then(function() { |
| assertFalse(testElement.$.category.hidden); |
| assertNotEquals(0, testElement.$.listContainer.offsetHeight); |
| }); |
| }); |
| |
| test('Block list open when Allow list is not empty', function() { |
| // Prefs: Items in both Block and Allow list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.BLOCK, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| return test_util.waitForRender(testElement); |
| }) |
| .then(function() { |
| assertFalse(testElement.$.category.hidden); |
| assertNotEquals(0, testElement.$.listContainer.offsetHeight); |
| }); |
| }); |
| |
| test('Allow list is always open (Block list empty)', function() { |
| // Prefs: One item in Allow list, nothing in Block list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.ALLOW, prefsOneEnabled); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| return test_util.waitForRender(testElement); |
| }) |
| .then(function() { |
| assertFalse(testElement.$.category.hidden); |
| assertNotEquals(0, testElement.$.listContainer.offsetHeight); |
| }); |
| }); |
| |
| test('Allow list is always open (Block list non-empty)', function() { |
| // Prefs: Items in both Block and Allow list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.ALLOW, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| return test_util.waitForRender(testElement); |
| }) |
| .then(function() { |
| assertFalse(testElement.$.category.hidden); |
| assertNotEquals(0, testElement.$.listContainer.offsetHeight); |
| }); |
| }); |
| |
| test('Block list not hidden when empty', function() { |
| // Prefs: One item in Allow list, nothing in Block list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.BLOCK, prefsOneEnabled); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('Allow list not hidden when empty', function() { |
| // Prefs: One item in Block list, nothing in Allow list. |
| const contentType = settings.ContentSettingsTypes.GEOLOCATION; |
| setUpCategory(contentType, settings.ContentSetting.ALLOW, prefsOneDisabled); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(actualContentType) { |
| assertEquals(contentType, actualContentType); |
| assertFalse(testElement.$.category.hidden); |
| }); |
| }); |
| |
| test('Mixed embeddingOrigin', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.IMAGES, settings.ContentSetting.ALLOW, |
| prefsMixedEmbeddingOrigin); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| // Required for firstItem to be found below. |
| Polymer.dom.flush(); |
| // Validate that embeddingOrigin sites cannot be edited. |
| const entries = testElement.root.querySelectorAll('site-list-entry'); |
| const firstItem = entries[0]; |
| assertTrue(firstItem.$.actionMenuButtonContainer.hidden); |
| assertFalse(firstItem.$.resetSiteContainer.hidden); |
| // Validate that non-embeddingOrigin sites can be edited. |
| const secondItem = entries[1]; |
| assertFalse(secondItem.$.actionMenuButtonContainer.hidden); |
| assertTrue(secondItem.$.resetSiteContainer.hidden); |
| }); |
| }); |
| |
| test('Mixed schemes (present and absent)', function() { |
| // Prefs: One item with scheme and one without. |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsMixedSchemes); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| // No further checks needed. If this fails, it will hang the test. |
| }); |
| }); |
| |
| test('Select menu item', function() { |
| // Test for error: "Cannot read property 'origin' of undefined". |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| Polymer.dom.flush(); |
| openActionMenu(0); |
| const allow = testElement.$.allow; |
| assertTrue(!!allow); |
| allow.click(); |
| return browserProxy.whenCalled('setCategoryPermissionForPattern'); |
| }); |
| }); |
| |
| test('Chrome Extension scheme', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.JAVASCRIPT, settings.ContentSetting.BLOCK, |
| prefsChromeExtension); |
| return browserProxy.whenCalled('getExceptionList') |
| .then(function(contentType) { |
| Polymer.dom.flush(); |
| openActionMenu(0); |
| assertMenu(['Allow', 'Edit', 'Remove'], testElement); |
| |
| const allow = testElement.$.allow; |
| assertTrue(!!allow); |
| allow.click(); |
| return browserProxy.whenCalled('setCategoryPermissionForPattern'); |
| }) |
| .then(function(args) { |
| assertEquals( |
| 'chrome-extension://cfhgfbfpcbnnbibfphagcjmgjfjmojfa/', args[0]); |
| assertEquals('', args[1]); |
| assertEquals(settings.ContentSettingsTypes.JAVASCRIPT, args[2]); |
| assertEquals(settings.ContentSetting.ALLOW, args[3]); |
| }); |
| }); |
| |
| test('show-tooltip event fires on entry shows common tooltip', function() { |
| setUpCategory( |
| settings.ContentSettingsTypes.GEOLOCATION, |
| settings.ContentSetting.ALLOW, prefsGeolocation); |
| return browserProxy.whenCalled('getExceptionList').then(() => { |
| Polymer.dom.flush(); |
| const entry = |
| testElement.$.listContainer.querySelector('site-list-entry'); |
| const tooltip = testElement.$.tooltip; |
| |
| const testsParams = [ |
| ['a', testElement, new MouseEvent('mouseleave')], |
| ['b', testElement, new MouseEvent('tap')], |
| ['c', testElement, new Event('blur')], |
| ['d', tooltip, new MouseEvent('mouseenter')], |
| ]; |
| testsParams.forEach(params => { |
| const text = params[0]; |
| const eventTarget = params[1]; |
| const event = params[2]; |
| entry.fire('show-tooltip', {target: testElement, text}); |
| assertTrue(tooltip._showing); |
| assertEquals(text, tooltip.innerHTML.trim()); |
| eventTarget.dispatchEvent(event); |
| assertFalse(tooltip._showing); |
| }); |
| }); |
| }); |
| }); |
| |
| suite('EditExceptionDialog', function() { |
| /** @type {SettingsEditExceptionDialogElement} */ let dialog; |
| |
| /** |
| * The dialog tests don't call |getExceptionList| so the exception needs to |
| * be processed as a |SiteException|. |
| * @type {SiteException} |
| */ |
| let cookieException; |
| |
| setup(function() { |
| cookieException = { |
| category: settings.ContentSettingsTypes.COOKIES, |
| embeddingOrigin: 'http://foo.com', |
| incognito: false, |
| setting: settings.ContentSetting.BLOCK, |
| enforcement: '', |
| controlledBy: 'USER_POLICY', |
| }; |
| |
| browserProxy = new TestSiteSettingsPrefsBrowserProxy(); |
| settings.SiteSettingsPrefsBrowserProxyImpl.instance_ = browserProxy; |
| PolymerTest.clearBody(); |
| dialog = document.createElement('settings-edit-exception-dialog'); |
| dialog.model = cookieException; |
| document.body.appendChild(dialog); |
| }); |
| |
| teardown(function() { |
| dialog.remove(); |
| }); |
| |
| test('invalid input', function() { |
| const input = dialog.$$('cr-input'); |
| assertTrue(!!input); |
| assertFalse(input.invalid); |
| |
| const actionButton = dialog.$.actionButton; |
| assertTrue(!!actionButton); |
| assertFalse(actionButton.disabled); |
| |
| // Simulate user input of whitespace only text. |
| input.value = ' '; |
| input.fire('input'); |
| Polymer.dom.flush(); |
| assertTrue(actionButton.disabled); |
| assertTrue(input.invalid); |
| |
| // Simulate user input of invalid text. |
| browserProxy.setIsPatternValidForType(false); |
| const expectedPattern = '*'; |
| input.value = expectedPattern; |
| input.fire('input'); |
| |
| return browserProxy.whenCalled('isPatternValidForType') |
| .then(function(pattern, category) { |
| assertEquals(expectedPattern, pattern); |
| assertTrue(actionButton.disabled); |
| assertTrue(input.invalid); |
| }); |
| }); |
| |
| test('action button calls proxy', function() { |
| const input = dialog.$$('cr-input'); |
| assertTrue(!!input); |
| // Simulate user edit. |
| const newValue = input.value + ':1234'; |
| input.value = newValue; |
| |
| const actionButton = dialog.$.actionButton; |
| assertTrue(!!actionButton); |
| assertFalse(actionButton.disabled); |
| |
| actionButton.click(); |
| return browserProxy.whenCalled('resetCategoryPermissionForPattern') |
| .then(function(args) { |
| assertEquals(cookieException.origin, args[0]); |
| assertEquals(cookieException.embeddingOrigin, args[1]); |
| assertEquals(settings.ContentSettingsTypes.COOKIES, args[2]); |
| assertEquals(cookieException.incognito, args[3]); |
| |
| return browserProxy.whenCalled('setCategoryPermissionForPattern'); |
| }) |
| .then(function(args) { |
| assertEquals(newValue, args[0]); |
| assertEquals(newValue, args[1]); |
| assertEquals(settings.ContentSettingsTypes.COOKIES, args[2]); |
| assertEquals(cookieException.setting, args[3]); |
| assertEquals(cookieException.incognito, args[4]); |
| |
| assertFalse(dialog.$.dialog.open); |
| }); |
| }); |
| }); |
| |
| suite('AddExceptionDialog', function() { |
| /** @type {AddSiteDialogElement} */ let dialog; |
| |
| setup(function() { |
| populateTestExceptions(); |
| |
| browserProxy = new TestSiteSettingsPrefsBrowserProxy(); |
| settings.SiteSettingsPrefsBrowserProxyImpl.instance_ = browserProxy; |
| PolymerTest.clearBody(); |
| dialog = document.createElement('add-site-dialog'); |
| dialog.category = settings.ContentSettingsTypes.GEOLOCATION; |
| dialog.contentSetting = settings.ContentSetting.ALLOW; |
| dialog.hasIncognito = false; |
| document.body.appendChild(dialog); |
| }); |
| |
| teardown(function() { |
| dialog.remove(); |
| }); |
| |
| test('incognito', function() { |
| dialog.set('hasIncognito', true); |
| Polymer.dom.flush(); |
| assertFalse(dialog.$.incognito.checked); |
| dialog.$.incognito.checked = true; |
| // Changing the incognito status will reset the checkbox. |
| dialog.set('hasIncognito', false); |
| Polymer.dom.flush(); |
| assertFalse(dialog.$.incognito.checked); |
| }); |
| |
| test('invalid input', function() { |
| // Initially the action button should be disabled, but the error warning |
| // should not be shown for an empty input. |
| const input = dialog.$$('cr-input'); |
| assertTrue(!!input); |
| assertFalse(input.invalid); |
| |
| const actionButton = dialog.$.add; |
| assertTrue(!!actionButton); |
| assertTrue(actionButton.disabled); |
| |
| // Simulate user input of invalid text. |
| browserProxy.setIsPatternValidForType(false); |
| const expectedPattern = 'foobarbaz'; |
| input.value = expectedPattern; |
| input.fire('input'); |
| |
| return browserProxy.whenCalled('isPatternValidForType') |
| .then(function(pattern) { |
| assertEquals(expectedPattern, pattern); |
| assertTrue(actionButton.disabled); |
| assertTrue(input.invalid); |
| }); |
| }); |
| }); |