diff --git a/platform/chromium/vapi-client.js b/platform/chromium/vapi-client.js index 28eb05b62..d2a772fad 100644 --- a/platform/chromium/vapi-client.js +++ b/platform/chromium/vapi-client.js @@ -137,10 +137,10 @@ vAPI.messaging = { // Response to specific message previously sent if ( details.auxProcessId ) { - const listener = this.pending.get(details.auxProcessId); - if ( listener !== undefined ) { + const resolver = this.pending.get(details.auxProcessId); + if ( resolver !== undefined ) { this.pending.delete(details.auxProcessId); - listener(details.msg); + resolver(details.msg); return; } } @@ -222,10 +222,8 @@ vAPI.messaging = { if ( this.pending.size !== 0 ) { const pending = this.pending; this.pending = new Map(); - for ( const callback of pending.values() ) { - if ( typeof callback === 'function' ) { - callback(null); - } + for ( const resolver of pending.values() ) { + resolver(); } } }, @@ -264,7 +262,7 @@ vAPI.messaging = { return this.port !== null ? this.port : this.createPort(); }, - send: function(channelName, message, callback) { + send: function(channelName, msg) { // Too large a gap between the last request and the last response means // the main process is no longer reachable: memory leaks and bad // performance become a risk -- especially for long-lived, dynamic @@ -274,19 +272,14 @@ vAPI.messaging = { } const port = this.getPort(); if ( port === null ) { - if ( typeof callback === 'function' ) { callback(); } - return; + return Promise.resolve(); } - let auxProcessId; - if ( callback ) { - auxProcessId = this.auxProcessId++; - this.pending.set(auxProcessId, callback); - } - port.postMessage({ - channelName: channelName, - auxProcessId: auxProcessId, - msg: message + const auxProcessId = this.auxProcessId++; + const promise = new Promise(resolve => { + this.pending.set(auxProcessId, resolve); }); + port.postMessage({ channelName, auxProcessId, msg }); + return promise; }, connectTo: function(from, to, handler) { diff --git a/platform/chromium/vapi-usercss.real.js b/platform/chromium/vapi-usercss.real.js index e6683f2a6..8ec746f6d 100644 --- a/platform/chromium/vapi-usercss.real.js +++ b/platform/chromium/vapi-usercss.real.js @@ -38,8 +38,11 @@ vAPI.userStylesheet = { vAPI.messaging.send('vapi', { what: 'userCSS', add: Array.from(this.added), - remove: Array.from(this.removed) - }, callback); + remove: Array.from(this.removed), + }).then(( ) => { + if ( callback instanceof Function === false ) { return; } + callback(); + }); this.added.clear(); this.removed.clear(); }, diff --git a/src/js/1p-filters.js b/src/js/1p-filters.js index 045542970..8064f1ac0 100644 --- a/src/js/1p-filters.js +++ b/src/js/1p-filters.js @@ -29,14 +29,13 @@ /******************************************************************************/ -const messaging = vAPI.messaging; const cmEditor = new CodeMirror( document.getElementById('userFilters'), { autofocus: true, lineNumbers: true, lineWrapping: true, - styleActiveLine: true + styleActiveLine: true, } ); @@ -72,30 +71,31 @@ const userFiltersChanged = function(changed) { /******************************************************************************/ -const renderUserFilters = function(first) { - const onRead = function(details) { - if ( details.error ) { return; } - let content = details.content.trim(); - cachedUserFilters = content; - if ( content.length !== 0 ) { - content += '\n'; - } - cmEditor.setValue(content); - if ( first ) { - cmEditor.clearHistory(); - try { - const line = JSON.parse( - vAPI.localStorage.getItem('myFiltersCursorPosition') - ); - if ( typeof line === 'number' ) { - cmEditor.setCursor(line, 0); - } - } catch(ex) { +const renderUserFilters = async function(first) { + const details = await vAPI.messaging.send('dashboard', { + what: 'readUserFilters', + }); + if ( details instanceof Object === false || details.error ) { return; } + + let content = details.content.trim(); + cachedUserFilters = content; + if ( content.length !== 0 ) { + content += '\n'; + } + cmEditor.setValue(content); + if ( first ) { + cmEditor.clearHistory(); + try { + const line = JSON.parse( + vAPI.localStorage.getItem('myFiltersCursorPosition') + ); + if ( typeof line === 'number' ) { + cmEditor.setCursor(line, 0); } + } catch(ex) { } - userFiltersChanged(false); - }; - messaging.send('dashboard', { what: 'readUserFilters' }, onRead); + } + userFiltersChanged(false); }; /******************************************************************************/ @@ -170,20 +170,18 @@ const exportUserFiltersToFile = function() { /******************************************************************************/ -const applyChanges = function() { - messaging.send( - 'dashboard', - { - what: 'writeUserFilters', - content: cmEditor.getValue() - }, - details => { - if ( details.error ) { return; } - cachedUserFilters = details.content.trim(); - userFiltersChanged(false); - messaging.send('dashboard', { what: 'reloadAllFilters' }); - } - ); +const applyChanges = async function() { + const details = await vAPI.messaging.send('dashboard', { + what: 'writeUserFilters', + content: cmEditor.getValue(), + }); + if ( details instanceof Object === false || details.error ) { return; } + + cachedUserFilters = details.content.trim(); + userFiltersChanged(false); + vAPI.messaging.send('dashboard', { + what: 'reloadAllFilters', + }); }; const revertChanges = function() { @@ -223,7 +221,7 @@ self.hasUnsavedData = function() { uDom('#importUserFiltersFromFile').on('click', startImportFilePicker); uDom('#importFilePicker').on('change', handleImportFilePicker); uDom('#exportUserFiltersToFile').on('click', exportUserFiltersToFile); -uDom('#userFiltersApply').on('click', applyChanges); +uDom('#userFiltersApply').on('click', ( ) => { applyChanges(); }); uDom('#userFiltersRevert').on('click', revertChanges); renderUserFilters(true); diff --git a/src/js/3p-filters.js b/src/js/3p-filters.js index f34caaa65..5b3989620 100644 --- a/src/js/3p-filters.js +++ b/src/js/3p-filters.js @@ -306,7 +306,11 @@ const renderFilterLists = function(soft) { renderWidgets(); }; - messaging.send('dashboard', { what: 'getLists' }, onListsReceived); + messaging.send('dashboard', { + what: 'getLists', + }).then(details => { + onListsReceived(details); + }); }; /******************************************************************************/ @@ -402,7 +406,10 @@ const onPurgeClicked = function(ev) { const listKey = liEntry.attr('data-listkey'); if ( !listKey ) { return; } - messaging.send('dashboard', { what: 'purgeCache', assetKey: listKey }); + messaging.send('dashboard', { + what: 'purgeCache', + assetKey: listKey, + }); // If the cached version is purged, the installed version must be assumed // to be obsolete. @@ -419,17 +426,17 @@ const onPurgeClicked = function(ev) { /******************************************************************************/ -const selectFilterLists = function(callback) { +const selectFilterLists = async function() { // Cosmetic filtering switch messaging.send('dashboard', { what: 'userSettings', name: 'parseAllABPHideFilters', - value: document.getElementById('parseCosmeticFilters').checked + value: document.getElementById('parseCosmeticFilters').checked, }); messaging.send('dashboard', { what: 'userSettings', name: 'ignoreGenericCosmeticFilters', - value: document.getElementById('ignoreGenericCosmeticFilters').checked + value: document.getElementById('ignoreGenericCosmeticFilters').checked, }); // Filter lists to select @@ -454,67 +461,53 @@ const selectFilterLists = function(callback) { externalListsElem.value = ''; uDom.nodeFromId('importLists').checked = false; - messaging.send( - 'dashboard', - { - what: 'applyFilterListSelection', - toSelect: toSelect, - toImport: toImport, - toRemove: toRemove - }, - callback - ); + await messaging.send('dashboard', { + what: 'applyFilterListSelection', + toSelect: toSelect, + toImport: toImport, + toRemove: toRemove, + }); + filteringSettingsHash = hashFromCurrentFromSettings(); }; /******************************************************************************/ -const buttonApplyHandler = function() { +const buttonApplyHandler = async function() { uDom('#buttonApply').removeClass('enabled'); - selectFilterLists(( ) => { - messaging.send('dashboard', { what: 'reloadAllFilters' }); - }); renderWidgets(); + await selectFilterLists(); + messaging.send('dashboard', { what: 'reloadAllFilters' }); }; /******************************************************************************/ -const buttonUpdateHandler = function() { - selectFilterLists(( ) => { - document.body.classList.add('updating'); - messaging.send('dashboard', { what: 'forceUpdateAssets' }); - renderWidgets(); - }); +const buttonUpdateHandler = async function() { + await selectFilterLists(); + document.body.classList.add('updating'); renderWidgets(); + messaging.send('dashboard', { what: 'forceUpdateAssets' }); }; /******************************************************************************/ -const buttonPurgeAllHandler = function(ev) { +const buttonPurgeAllHandler = async function(hard) { uDom('#buttonPurgeAll').removeClass('enabled'); - messaging.send( - 'dashboard', - { - what: 'purgeAllCaches', - hard: ev.ctrlKey && ev.shiftKey - }, - ( ) => { - renderFilterLists(true); - } - ); + await messaging.send('dashboard', { + what: 'purgeAllCaches', + hard, + }); + renderFilterLists(true); }; /******************************************************************************/ const autoUpdateCheckboxChanged = function() { - messaging.send( - 'dashboard', - { - what: 'userSettings', - name: 'autoUpdate', - value: this.checked - } - ); + messaging.send('dashboard', { + what: 'userSettings', + name: 'autoUpdate', + value: this.checked, + }); }; /******************************************************************************/ @@ -675,9 +668,11 @@ self.hasUnsavedData = function() { uDom('#autoUpdate').on('change', autoUpdateCheckboxChanged); uDom('#parseCosmeticFilters').on('change', onFilteringSettingsChanged); uDom('#ignoreGenericCosmeticFilters').on('change', onFilteringSettingsChanged); -uDom('#buttonApply').on('click', buttonApplyHandler); -uDom('#buttonUpdate').on('click', buttonUpdateHandler); -uDom('#buttonPurgeAll').on('click', buttonPurgeAllHandler); +uDom('#buttonApply').on('click', ( ) => { buttonApplyHandler(); }); +uDom('#buttonUpdate').on('click', ( ) => { buttonUpdateHandler(); }); +uDom('#buttonPurgeAll').on('click', ev => { + buttonPurgeAllHandler(ev.ctrlKey && ev.shiftKey); +}); uDom('#lists').on('change', '.listEntry > input', onFilteringSettingsChanged); uDom('#lists').on('click', '.listEntry > a.remove', onRemoveExternalList); uDom('#lists').on('click', 'span.cache', onPurgeClicked); diff --git a/src/js/about.js b/src/js/about.js index 184a800a9..e4405c90a 100644 --- a/src/js/about.js +++ b/src/js/about.js @@ -1,7 +1,7 @@ /******************************************************************************* uBlock Origin - a browser extension to block requests. - Copyright (C) 2014-2016 Raymond Hill + Copyright (C) 2014-present Raymond Hill This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -25,12 +25,7 @@ /******************************************************************************/ -(( ) => { - - vAPI.messaging.send('dashboard', { what: 'getAppData' }, appData => { - uDom('#aboutNameVer').text(appData.name + ' v' + appData.version); - }); - +(async ( ) => { document.querySelector( '[href="logger-ui.html"]' ).addEventListener( @@ -38,4 +33,8 @@ self.uBlockDashboard.openOrSelectPage ); + const appData = await vAPI.messaging.send('dashboard', { + what: 'getAppData', + }); + uDom('#aboutNameVer').text(appData.name + ' v' + appData.version); })(); diff --git a/src/js/advanced-settings.js b/src/js/advanced-settings.js index 53c209c58..ce92f3b1b 100644 --- a/src/js/advanced-settings.js +++ b/src/js/advanced-settings.js @@ -25,12 +25,11 @@ /******************************************************************************/ -(function() { +(( ) => { // >>>> Start of private namespace /******************************************************************************/ -const messaging = vAPI.messaging; const noopFunc = function(){}; let beforeHash = ''; @@ -57,18 +56,19 @@ const hashFromAdvancedSettings = function(raw) { // This is to give a visual hint that the content of user blacklist has changed. -const advancedSettingsChanged = (function () { - let timer = null; +const advancedSettingsChanged = (( ) => { + let timer; const handler = ( ) => { - timer = null; - let changed = hashFromAdvancedSettings(cmEditor.getValue()) !== beforeHash; + timer = undefined; + const changed = + hashFromAdvancedSettings(cmEditor.getValue()) !== beforeHash; uDom.nodeFromId('advancedSettingsApply').disabled = !changed; CodeMirror.commands.save = changed ? applyChanges : noopFunc; }; return function() { - if ( timer !== null ) { clearTimeout(timer); } + if ( timer !== undefined ) { clearTimeout(timer); } timer = vAPI.setTimeout(handler, 100); }; })(); @@ -77,42 +77,40 @@ cmEditor.on('changes', advancedSettingsChanged); /******************************************************************************/ -const renderAdvancedSettings = function(first) { - const onRead = function(raw) { - beforeHash = hashFromAdvancedSettings(raw); - let pretty = [], - whitespaces = ' ', - lines = raw.split('\n'), - max = 0; - for ( let line of lines ) { - let pos = line.indexOf(' '); - if ( pos > max ) { max = pos; } - } - for ( let line of lines ) { - let pos = line.indexOf(' '); - pretty.push(whitespaces.slice(0, max - pos) + line); - } - cmEditor.setValue(pretty.join('\n') + '\n'); - if ( first ) { - cmEditor.clearHistory(); - } - advancedSettingsChanged(); - cmEditor.focus(); - }; - messaging.send('dashboard', { what: 'readHiddenSettings' }, onRead); +const renderAdvancedSettings = async function(first) { + const raw = await vAPI.messaging.send('dashboard', { + what: 'readHiddenSettings', + }); + + beforeHash = hashFromAdvancedSettings(raw); + let pretty = [], + whitespaces = ' ', + lines = raw.split('\n'), + max = 0; + for ( let line of lines ) { + let pos = line.indexOf(' '); + if ( pos > max ) { max = pos; } + } + for ( let line of lines ) { + let pos = line.indexOf(' '); + pretty.push(whitespaces.slice(0, max - pos) + line); + } + cmEditor.setValue(pretty.join('\n') + '\n'); + if ( first ) { + cmEditor.clearHistory(); + } + advancedSettingsChanged(); + cmEditor.focus(); }; /******************************************************************************/ -const applyChanges = function() { - messaging.send( - 'dashboard', - { - what: 'writeHiddenSettings', - content: cmEditor.getValue() - }, - renderAdvancedSettings - ); +const applyChanges = async function() { + await vAPI.messaging.send('dashboard', { + what: 'writeHiddenSettings', + content: cmEditor.getValue(), + }); + renderAdvancedSettings(); }; /******************************************************************************/ @@ -121,10 +119,9 @@ uDom.nodeFromId('advancedSettings').addEventListener( 'input', advancedSettingsChanged ); -uDom.nodeFromId('advancedSettingsApply').addEventListener( - 'click', - applyChanges -); +uDom.nodeFromId('advancedSettingsApply').addEventListener('click', ( ) => { + applyChanges(); +}); renderAdvancedSettings(true); diff --git a/src/js/asset-viewer.js b/src/js/asset-viewer.js index eeeb9fc3d..8ea3eb5a5 100644 --- a/src/js/asset-viewer.js +++ b/src/js/asset-viewer.js @@ -25,27 +25,11 @@ /******************************************************************************/ -(( ) => { +(async ( ) => { const params = new URL(document.location).searchParams; const assetKey = params.get('url'); if ( assetKey === null ) { return; } - vAPI.messaging.send( - 'default', - { - what : 'getAssetContent', - url: assetKey, - }, - details => { - cmEditor.setValue(details && details.content || ''); - if ( details.sourceURL ) { - const a = document.querySelector('.cm-search-widget .sourceURL'); - a.setAttribute('href', details.sourceURL); - a.setAttribute('title', details.sourceURL); - } - } - ); - const cmEditor = new CodeMirror( document.getElementById('content'), { @@ -58,4 +42,15 @@ ); uBlockDashboard.patchCodeMirrorEditor(cmEditor); + + const details = await vAPI.messaging.send('default', { + what : 'getAssetContent', + url: assetKey, + }); + cmEditor.setValue(details && details.content || ''); + if ( details.sourceURL ) { + const a = document.querySelector('.cm-search-widget .sourceURL'); + a.setAttribute('href', details.sourceURL); + a.setAttribute('title', details.sourceURL); + } })(); diff --git a/src/js/cloud-ui.js b/src/js/cloud-ui.js index c5c404219..25a613b90 100644 --- a/src/js/cloud-ui.js +++ b/src/js/cloud-ui.js @@ -21,11 +21,11 @@ /* global uDom */ +'use strict'; + /******************************************************************************/ -(function() { - -'use strict'; +(( ) => { /******************************************************************************/ @@ -39,31 +39,27 @@ self.cloud = { /******************************************************************************/ -var widget = uDom.nodeFromId('cloudWidget'); -if ( widget === null ) { - return; -} +const widget = uDom.nodeFromId('cloudWidget'); +if ( widget === null ) { return; } self.cloud.datakey = widget.getAttribute('data-cloud-entry') || ''; -if ( self.cloud.datakey === '' ) { - return; -} - -var messaging = vAPI.messaging; +if ( self.cloud.datakey === '' ) { return; } /******************************************************************************/ -var onCloudDataReceived = function(entry) { - if ( entry instanceof Object === false ) { - return; - } +const fetchCloudData = async function() { + const entry = await vAPI.messaging.send('cloudWidget', { + what: 'cloudPull', + datakey: self.cloud.datakey, + }); + if ( entry instanceof Object === false ) { return; } self.cloud.data = entry.data; uDom.nodeFromId('cloudPull').removeAttribute('disabled'); uDom.nodeFromId('cloudPullAndMerge').removeAttribute('disabled'); - var timeOptions = { + const timeOptions = { weekday: 'short', year: 'numeric', month: 'short', @@ -74,7 +70,7 @@ var onCloudDataReceived = function(entry) { timeZoneName: 'short' }; - var time = new Date(entry.tstamp); + const time = new Date(entry.tstamp); widget.querySelector('#cloudInfo').textContent = entry.source + '\n' + time.toLocaleString('fullwide', timeOptions); @@ -82,40 +78,21 @@ var onCloudDataReceived = function(entry) { /******************************************************************************/ -var fetchCloudData = function() { - messaging.send( - 'cloudWidget', - { - what: 'cloudPull', - datakey: self.cloud.datakey - }, - onCloudDataReceived - ); -}; +const pushData = async function() { + if ( typeof self.cloud.onPush !== 'function' ) { return; } -/******************************************************************************/ - -var pushData = function() { - if ( typeof self.cloud.onPush !== 'function' ) { - return; - } - messaging.send( - 'cloudWidget', - { - what: 'cloudPush', - datakey: self.cloud.datakey, - data: self.cloud.onPush() - }, - function(error) { - var failed = typeof error === 'string'; - document.getElementById('cloudPush') - .classList - .toggle('error', failed); - document.querySelector('#cloudError') - .textContent = failed ? error : ''; - fetchCloudData(); - } - ); + const error = await vAPI.messaging.send('cloudWidget', { + what: 'cloudPush', + datakey: self.cloud.datakey, + data: self.cloud.onPush(), + }); + const failed = typeof error === 'string'; + document.getElementById('cloudPush') + .classList + .toggle('error', failed); + document.querySelector('#cloudError') + .textContent = failed ? error : ''; + fetchCloudData(); }; /******************************************************************************/ @@ -155,46 +132,34 @@ var closeOptions = function(ev) { /******************************************************************************/ -var submitOptions = function() { - var onOptions = function(options) { - if ( options instanceof Object === false ) { - return; - } - self.cloud.options = options; - }; - - messaging.send( - 'cloudWidget', - { - what: 'cloudSetOptions', - options: { - deviceName: uDom.nodeFromId('cloudDeviceName').value - } - }, - onOptions - ); +const submitOptions = async function() { uDom.nodeFromId('cloudOptions').classList.remove('show'); + + const options = await vAPI.messaging.send('cloudWidget', { + what: 'cloudSetOptions', + options: { + deviceName: uDom.nodeFromId('cloudDeviceName').value + }, + }); + if ( options instanceof Object ) { + self.cloud.options = options; + } }; /******************************************************************************/ -var onInitialize = function(options) { - if ( typeof options !== 'object' || options === null ) { - return; - } - - if ( !options.enabled ) { - return; - } +const onInitialize = function(options) { + if ( options instanceof Object === false ) { return; } + if ( !options.enabled ) { return; } self.cloud.options = options; - var xhr = new XMLHttpRequest(); + const xhr = new XMLHttpRequest(); xhr.open('GET', 'cloud-ui.html', true); xhr.overrideMimeType('text/html;charset=utf-8'); xhr.responseType = 'text'; xhr.onload = function() { this.onload = null; - var parser = new DOMParser(), + const parser = new DOMParser(), parsed = parser.parseFromString(this.responseText, 'text/html'), fromParent = parsed.body; while ( fromParent.firstElementChild !== null ) { @@ -206,12 +171,12 @@ var onInitialize = function(options) { vAPI.i18n.render(widget); widget.classList.remove('hide'); - uDom('#cloudPush').on('click', pushData); + uDom('#cloudPush').on('click', ( ) => { pushData(); }); uDom('#cloudPull').on('click', pullData); uDom('#cloudPullAndMerge').on('click', pullAndMergeData); uDom('#cloudCog').on('click', openOptions); uDom('#cloudOptions').on('click', closeOptions); - uDom('#cloudOptionsSubmit').on('click', submitOptions); + uDom('#cloudOptionsSubmit').on('click', ( ) => { submitOptions(); }); // Patch 2018-01-05: Must not assume this XHR will always be faster // than messaging @@ -220,10 +185,12 @@ var onInitialize = function(options) { xhr.send(); }; -messaging.send('cloudWidget', { what: 'cloudGetOptions' }, onInitialize); +vAPI.messaging.send('cloudWidget', { + what: 'cloudGetOptions', +}).then(options => { + onInitialize(options); +}); /******************************************************************************/ -// https://www.youtube.com/watch?v=aQFp67VoiDA - })(); diff --git a/src/js/contentscript.js b/src/js/contentscript.js index a9dd15bb0..8aa6294c5 100644 --- a/src/js/contentscript.js +++ b/src/js/contentscript.js @@ -207,19 +207,15 @@ vAPI.SafeAnimationFrame.prototype = { let timer; const send = function() { - vAPI.messaging.send( - 'scriptlets', - { - what: 'securityPolicyViolation', - type: 'net', - docURL: document.location.href, - violations: Array.from(newEvents), - }, - response => { - if ( response === true ) { return; } - stop(); - } - ); + vAPI.messaging.send('scriptlets', { + what: 'securityPolicyViolation', + type: 'net', + docURL: document.location.href, + violations: Array.from(newEvents), + }).then(response => { + if ( response === true ) { return; } + stop(); + }); for ( const event of newEvents ) { allEvents.add(event); } @@ -230,7 +226,7 @@ vAPI.SafeAnimationFrame.prototype = { if ( timer !== undefined ) { return; } timer = self.requestIdleCallback( ( ) => { timer = undefined; send(); }, - { timeout: 2000 } + { timeout: 2063 } ); }; @@ -908,7 +904,8 @@ vAPI.domCollapser = (function() { // https://github.com/chrisaljoudi/uBlock/issues/174 // Do not remove fragment from src URL const onProcessed = function(response) { - if ( !response ) { // This happens if uBO is disabled or restarted. + // This happens if uBO is disabled or restarted. + if ( response instanceof Object === false ) { toCollapse.clear(); return; } @@ -964,29 +961,27 @@ vAPI.domCollapser = (function() { } if ( selectors.length !== 0 ) { - messaging.send( - 'contentscript', - { - what: 'cosmeticFiltersInjected', - type: 'net', - hostname: window.location.hostname, - selectors: selectors - } - ); + messaging.send('contentscript', { + what: 'cosmeticFiltersInjected', + type: 'net', + hostname: window.location.hostname, + selectors, + }); } }; const send = function() { processTimer = undefined; toCollapse.set(resquestIdGenerator, toProcess); - const msg = { + messaging.send('contentscript', { what: 'getCollapsibleBlockedRequests', id: resquestIdGenerator, frameURL: window.location.href, resources: toFilter, - hash: cachedBlockedSetHash - }; - messaging.send('contentscript', msg, onProcessed); + hash: cachedBlockedSetHash, + }).then(response => { + onProcessed(response); + }); toProcess = []; toFilter = []; resquestIdGenerator += 1; @@ -1256,18 +1251,16 @@ vAPI.domSurveyor = (function() { //console.info(`domSurveyor> Surveyed ${processed} nodes in ${(t1-t0).toFixed(2)} ms`); // Phase 2: Ask main process to lookup relevant cosmetic filters. if ( ids.length !== 0 || classes.length !== 0 ) { - messaging.send( - 'contentscript', - { - what: 'retrieveGenericCosmeticSelectors', - hostname: hostname, - ids: ids, - classes: classes, - exceptions: domFilterer.exceptions, - cost: surveyCost - }, - surveyPhase3 - ); + messaging.send('contentscript', { + what: 'retrieveGenericCosmeticSelectors', + hostname, + ids, + classes, + exceptions: domFilterer.exceptions, + cost: surveyCost, + }).then(response => { + surveyPhase3(response); + }); } else { surveyPhase3(null); } @@ -1408,10 +1401,9 @@ vAPI.bootstrap = (function() { if ( window.location === null ) { return; } if ( vAPI instanceof Object === false ) { return; } - vAPI.messaging.send( - 'contentscript', - { what: 'shouldRenderNoscriptTags' } - ); + vAPI.messaging.send('contentscript', { + what: 'shouldRenderNoscriptTags', + }); if ( vAPI.domWatcher instanceof Object ) { vAPI.domWatcher.start(); @@ -1437,15 +1429,12 @@ vAPI.bootstrap = (function() { while ( elem !== null && elem.localName !== 'a' ) { elem = elem.parentElement; } - vAPI.messaging.send( - 'contentscript', - { - what: 'mouseClick', - x: ev.clientX, - y: ev.clientY, - url: elem !== null && ev.isTrusted !== false ? elem.href : '' - } - ); + vAPI.messaging.send('contentscript', { + what: 'mouseClick', + x: ev.clientX, + y: ev.clientY, + url: elem !== null && ev.isTrusted !== false ? elem.href : '', + }); }; document.addEventListener('mousedown', onMouseClick, true); @@ -1546,16 +1535,14 @@ vAPI.bootstrap = (function() { }; return function() { - vAPI.messaging.send( - 'contentscript', - { - what: 'retrieveContentScriptParameters', - url: window.location.href, - isRootFrame: window === window.top, - charset: document.characterSet, - }, - bootstrapPhase1 - ); + vAPI.messaging.send('contentscript', { + what: 'retrieveContentScriptParameters', + url: window.location.href, + isRootFrame: window === window.top, + charset: document.characterSet, + }).then(response => { + bootstrapPhase1(response); + }); }; })(); diff --git a/src/js/dashboard-common.js b/src/js/dashboard-common.js index d421bc413..02dae77b4 100644 --- a/src/js/dashboard-common.js +++ b/src/js/dashboard-common.js @@ -225,7 +225,10 @@ self.uBlockDashboard.openOrSelectPage = function(url, options = {}) { url = ev.target.getAttribute('href'); } const details = Object.assign({ url, select: true, index: -1 }, options); - vAPI.messaging.send('default', { what: 'gotoURL', details }); + vAPI.messaging.send('default', { + what: 'gotoURL', + details, + }); if ( ev ) { ev.preventDefault(); } diff --git a/src/js/dashboard.js b/src/js/dashboard.js index 6bea58e9c..b407c498c 100644 --- a/src/js/dashboard.js +++ b/src/js/dashboard.js @@ -115,7 +115,9 @@ const onTabClickHandler = function(ev) { }; // https://github.com/uBlockOrigin/uBlock-issues/issues/106 -vAPI.messaging.send('dashboard', { what: 'canUpdateShortcuts' }, response => { +vAPI.messaging.send('dashboard', { + what: 'canUpdateShortcuts', +}).then(response => { document.body.classList.toggle('canUpdateShortcuts', response === true); }); diff --git a/src/js/document-blocked.js b/src/js/document-blocked.js index 83581e013..4b9520901 100644 --- a/src/js/document-blocked.js +++ b/src/js/document-blocked.js @@ -41,44 +41,42 @@ let details = {}; /******************************************************************************/ -messaging.send( - 'documentBlocked', - { +(async ( ) => { + const response = await messaging.send('documentBlocked', { what: 'listsFromNetFilter', compiledFilter: details.fc, - rawFilter: details.fs - }, - response => { - if ( response instanceof Object === false ) { return; } + rawFilter: details.fs, + }); + if ( response instanceof Object === false ) { return; } - let lists; - for ( const rawFilter in response ) { - if ( response.hasOwnProperty(rawFilter) === false ) { continue; } + let lists; + for ( const rawFilter in response ) { + if ( response.hasOwnProperty(rawFilter) ) { lists = response[rawFilter]; break; } - - if ( Array.isArray(lists) === false || lists.length === 0 ) { return; } - - const parent = uDom.nodeFromSelector('#whyex > span:nth-of-type(2)'); - for ( const list of lists ) { - const elem = document.querySelector('#templates .filterList') - .cloneNode(true); - const source = elem.querySelector('.filterListSource'); - source.href += encodeURIComponent(list.assetKey); - source.textContent = list.title; - if ( - typeof list.supportURL === 'string' && - list.supportURL !== '' - ) { - elem.querySelector('.filterListSupport') - .setAttribute('href', list.supportURL); - } - parent.appendChild(elem); - } - uDom.nodeFromId('whyex').style.removeProperty('display'); } -); + + if ( Array.isArray(lists) === false || lists.length === 0 ) { return; } + + const parent = uDom.nodeFromSelector('#whyex > span:nth-of-type(2)'); + for ( const list of lists ) { + const elem = document.querySelector('#templates .filterList') + .cloneNode(true); + const source = elem.querySelector('.filterListSource'); + source.href += encodeURIComponent(list.assetKey); + source.textContent = list.title; + if ( + typeof list.supportURL === 'string' && + list.supportURL !== '' + ) { + elem.querySelector('.filterListSupport') + .setAttribute('href', list.supportURL); + } + parent.appendChild(elem); + } + uDom.nodeFromId('whyex').style.removeProperty('display'); +})(); /******************************************************************************/ @@ -219,10 +217,9 @@ if ( window.history.length > 1 ) { uDom('#bye').on( 'click', ( ) => { - messaging.send( - 'documentBlocked', - { what: 'closeThisTab', } - ); + messaging.send('documentBlocked', { + what: 'closeThisTab', + }); } ); uDom('#back').css('display', 'none'); @@ -240,30 +237,24 @@ const proceedToURL = function() { window.location.replace(details.url); }; -const proceedTemporary = function() { - messaging.send( - 'documentBlocked', - { - what: 'temporarilyWhitelistDocument', - hostname: getTargetHostname() - }, - proceedToURL - ); +const proceedTemporary = async function() { + await messaging.send('documentBlocked', { + what: 'temporarilyWhitelistDocument', + hostname: getTargetHostname(), + }); + proceedToURL(); }; -const proceedPermanent = function() { - messaging.send( - 'documentBlocked', - { - what: 'toggleHostnameSwitch', - name: 'no-strict-blocking', - hostname: getTargetHostname(), - deep: true, - state: true, - persist: true - }, - proceedToURL - ); +const proceedPermanent = async function() { + await messaging.send('documentBlocked', { + what: 'toggleHostnameSwitch', + name: 'no-strict-blocking', + hostname: getTargetHostname(), + deep: true, + state: true, + persist: true, + }); + proceedToURL(); }; uDom('#proceedTemporary').attr('href', details.url).on('click', proceedTemporary); diff --git a/src/js/dyna-rules.js b/src/js/dyna-rules.js index 839a9b4da..85cf87fe2 100644 --- a/src/js/dyna-rules.js +++ b/src/js/dyna-rules.js @@ -29,8 +29,6 @@ /******************************************************************************/ -const messaging = vAPI.messaging; - const mergeView = new CodeMirror.MergeView( document.querySelector('.codeMirrorMergeContainer'), { @@ -105,7 +103,7 @@ let differ; const updateOverlay = (function() { let reFilter; - let mode = { + const mode = { token: function(stream) { if ( reFilter !== undefined ) { reFilter.lastIndex = stream.pos; @@ -190,8 +188,8 @@ const rulesToDoc = function(clearHistory) { /******************************************************************************/ const filterRules = function(key) { + const filter = uDom.nodeFromSelector('#ruleFilter input').value; let rules = unfilteredRules[key].rules; - let filter = uDom.nodeFromSelector('#ruleFilter input').value; if ( filter !== '' ) { rules = rules.slice(); let i = rules.length; @@ -235,17 +233,14 @@ const renderRules = (( ) => { /******************************************************************************/ -const applyDiff = function(permanent, toAdd, toRemove) { - messaging.send( - 'dashboard', - { - what: 'modifyRuleset', - permanent: permanent, - toAdd: toAdd, - toRemove: toRemove - }, - renderRules - ); +const applyDiff = async function(permanent, toAdd, toRemove) { + const details = await vAPI.messaging.send('dashboard', { + what: 'modifyRuleset', + permanent: permanent, + toAdd: toAdd, + toRemove: toRemove, + }); + renderRules(details); }; /******************************************************************************/ @@ -266,13 +261,13 @@ mergeView.options.revertChunk = function( } if ( typeof fromStart.ch !== 'number' ) { fromStart.ch = 0; } if ( fromEnd.ch !== 0 ) { fromEnd.line += 1; } - let toAdd = from.getRange( + const toAdd = from.getRange( { line: fromStart.line, ch: 0 }, { line: fromEnd.line, ch: 0 } ); if ( typeof toStart.ch !== 'number' ) { toStart.ch = 0; } if ( toEnd.ch !== 0 ) { toEnd.line += 1; } - let toRemove = to.getRange( + const toRemove = to.getRange( { line: toStart.line, ch: 0 }, { line: toEnd.line, ch: 0 } ); @@ -282,7 +277,7 @@ mergeView.options.revertChunk = function( /******************************************************************************/ function handleImportFilePicker() { - let fileReaderOnLoadHandler = function() { + const fileReaderOnLoadHandler = function() { if ( typeof this.result !== 'string' || this.result === '' ) { return; } // https://github.com/chrisaljoudi/uBlock/issues/757 // Support RequestPolicy rule syntax @@ -295,10 +290,10 @@ function handleImportFilePicker() { } applyDiff(false, result, ''); }; - let file = this.files[0]; + const file = this.files[0]; if ( file === undefined || file.name === '' ) { return; } if ( file.type.indexOf('text') !== 0 ) { return; } - let fr = new FileReader(); + const fr = new FileReader(); fr.onload = fileReaderOnLoadHandler; fr.readAsText(file); } @@ -306,7 +301,7 @@ function handleImportFilePicker() { /******************************************************************************/ const startImportFilePicker = function() { - let input = document.getElementById('importFilePicker'); + const input = document.getElementById('importFilePicker'); // Reset to empty string, this will ensure an change event is properly // triggered if the user pick a file, even if it is the same as the last // one picked. @@ -317,7 +312,7 @@ const startImportFilePicker = function() { /******************************************************************************/ function exportUserRulesToFile() { - let filename = vAPI.i18n('rulesDefaultFileName') + const filename = vAPI.i18n('rulesDefaultFileName') .replace('{{datetime}}', uBlockDashboard.dateNowToSensibleString()) .replace(/ +/g, '_'); vAPI.download({ @@ -339,7 +334,7 @@ const onFilterChanged = (function() { const process = function() { timer = undefined; if ( mergeView.editor().isClean(cleanEditToken) === false ) { return; } - let filter = uDom.nodeFromSelector('#ruleFilter input').value; + const filter = uDom.nodeFromSelector('#ruleFilter input').value; if ( filter === last ) { return; } last = filter; if ( overlay !== null ) { @@ -401,15 +396,15 @@ const onTextChanged = (( ) => { /******************************************************************************/ const revertAllHandler = function() { - let toAdd = [], toRemove = []; - let left = mergeView.leftOriginal(), - edit = mergeView.editor(); - for ( let chunk of mergeView.leftChunks() ) { - let addedLines = left.getRange( + const toAdd = [], toRemove = []; + const left = mergeView.leftOriginal(); + const edit = mergeView.editor(); + for ( const chunk of mergeView.leftChunks() ) { + const addedLines = left.getRange( { line: chunk.origFrom, ch: 0 }, { line: chunk.origTo, ch: 0 } ); - let removedLines = edit.getRange( + const removedLines = edit.getRange( { line: chunk.editFrom, ch: 0 }, { line: chunk.editTo, ch: 0 } ); @@ -422,15 +417,15 @@ const revertAllHandler = function() { /******************************************************************************/ const commitAllHandler = function() { - let toAdd = [], toRemove = []; - let left = mergeView.leftOriginal(), - edit = mergeView.editor(); - for ( let chunk of mergeView.leftChunks() ) { - let addedLines = edit.getRange( + const toAdd = [], toRemove = []; + const left = mergeView.leftOriginal(); + const edit = mergeView.editor(); + for ( const chunk of mergeView.leftChunks() ) { + const addedLines = edit.getRange( { line: chunk.editFrom, ch: 0 }, { line: chunk.editTo, ch: 0 } ); - let removedLines = left.getRange( + const removedLines = left.getRange( { line: chunk.origFrom, ch: 0 }, { line: chunk.origTo, ch: 0 } ); @@ -443,16 +438,16 @@ const commitAllHandler = function() { /******************************************************************************/ const editSaveHandler = function() { - let editor = mergeView.editor(); - let editText = editor.getValue().trim(); + const editor = mergeView.editor(); + const editText = editor.getValue().trim(); if ( editText === cleanEditText ) { onTextChanged(true); return; } if ( differ === undefined ) { differ = new diff_match_patch(); } - let toAdd = [], toRemove = []; - let diffs = differ.diff_main(cleanEditText, editText); - for ( let diff of diffs ) { + const toAdd = [], toRemove = []; + const diffs = differ.diff_main(cleanEditText, editText); + for ( const diff of diffs ) { if ( diff[0] === 1 ) { toAdd.push(diff[1]); } else if ( diff[0] === -1 ) { @@ -485,7 +480,11 @@ self.hasUnsavedData = function() { /******************************************************************************/ -messaging.send('dashboard', { what: 'getRules' }, renderRules); +vAPI.messaging.send('dashboard', { + what: 'getRules', +}).then(details => { + renderRules(details); +}); // Handle user interaction uDom('#importButton').on('click', startImportFilePicker); diff --git a/src/js/logger-ui-inspector.js b/src/js/logger-ui-inspector.js index e61e07e40..d321496af 100644 --- a/src/js/logger-ui-inspector.js +++ b/src/js/logger-ui-inspector.js @@ -25,7 +25,7 @@ /******************************************************************************/ -(function() { +(( ) => { /******************************************************************************/ @@ -385,9 +385,15 @@ const startDialog = (function() { ev.stopPropagation(); if ( target.id === 'createCosmeticFilters' ) { - messaging.send('loggerUI', { what: 'createUserFilter', filters: textarea.value }); + messaging.send('loggerUI', { + what: 'createUserFilter', + filters: textarea.value, + }); // Force a reload for the new cosmetic filter(s) to take effect - messaging.send('loggerUI', { what: 'reloadTab', tabId: inspectedTabId }); + messaging.send('loggerUI', { + what: 'reloadTab', + tabId: inspectedTabId, + }); return stop(); } }; @@ -561,8 +567,8 @@ const injectInspector = function() { inspectedTabId = tabId; messaging.send('loggerUI', { what: 'scriptlet', - tabId: tabId, - scriptlet: 'dom-inspector' + tabId, + scriptlet: 'dom-inspector', }); }; diff --git a/src/js/logger-ui.js b/src/js/logger-ui.js index a69e21d0a..c65808e05 100644 --- a/src/js/logger-ui.js +++ b/src/js/logger-ui.js @@ -25,7 +25,7 @@ /******************************************************************************/ -(function() { +(( ) => { /******************************************************************************/ @@ -975,7 +975,7 @@ const onLogBufferRead = function(response) { const readLogBuffer = (( ) => { let timer; - const readLogBufferNow = function() { + const readLogBufferNow = async function() { if ( logger.ownerId === undefined ) { return; } const msg = { @@ -1002,11 +1002,11 @@ const readLogBuffer = (( ) => { msg.popupLoggerBoxChanged = true; } - vAPI.messaging.send('loggerUI', msg, response => { - timer = undefined; - onLogBufferRead(response); - readLogBufferLater(); - }); + const response = await vAPI.messaging.send('loggerUI', msg); + + timer = undefined; + onLogBufferRead(response); + readLogBufferLater(); }; const readLogBufferLater = function() { @@ -1078,7 +1078,7 @@ const reloadTab = function(ev) { messaging.send('loggerUI', { what: 'reloadTab', tabId: tabId, - bypassCache: ev && (ev.ctrlKey || ev.metaKey || ev.shiftKey) + bypassCache: ev && (ev.ctrlKey || ev.metaKey || ev.shiftKey), }); }; @@ -1144,17 +1144,14 @@ const reloadTab = function(ev) { } }; - const colorize = function() { - messaging.send( - 'loggerUI', - { - what: 'getURLFilteringData', - context: selectValue('select.dynamic.origin'), - urls: targetURLs, - type: uglyTypeFromSelector('dynamic') - }, - onColorsReady - ); + const colorize = async function() { + const response = await messaging.send('loggerUI', { + what: 'getURLFilteringData', + context: selectValue('select.dynamic.origin'), + urls: targetURLs, + type: uglyTypeFromSelector('dynamic'), + }); + onColorsReady(response); }; const parseStaticInputs = function() { @@ -1228,16 +1225,13 @@ const reloadTab = function(ev) { } createdStaticFilters[value] = true; if ( value !== '' ) { - messaging.send( - 'loggerUI', - { - what: 'createUserFilter', - autoComment: true, - filters: value, - origin: targetPageDomain, - pageDomain: targetPageDomain, - } - ); + messaging.send('loggerUI', { + what: 'createUserFilter', + autoComment: true, + filters: value, + origin: targetPageDomain, + pageDomain: targetPageDomain, + }); } updateWidgets(); ev.stopPropagation(); @@ -1246,16 +1240,14 @@ const reloadTab = function(ev) { // Save url filtering rule(s) if ( target.id === 'saveRules' ) { - messaging.send( - 'loggerUI', - { - what: 'saveURLFilteringRules', - context: selectValue('select.dynamic.origin'), - urls: targetURLs, - type: uglyTypeFromSelector('dynamic') - }, - colorize - ); + messaging.send('loggerUI', { + what: 'saveURLFilteringRules', + context: selectValue('select.dynamic.origin'), + urls: targetURLs, + type: uglyTypeFromSelector('dynamic'), + }).then(( ) => { + colorize(); + }); ev.stopPropagation(); return; } @@ -1264,100 +1256,86 @@ const reloadTab = function(ev) { // Remove url filtering rule if ( tcl.contains('action') ) { - messaging.send( - 'loggerUI', - { - what: 'setURLFilteringRule', - context: selectValue('select.dynamic.origin'), - url: target.getAttribute('data-url'), - type: uglyTypeFromSelector('dynamic'), - action: 0, - persist: persist - }, - colorize - ); + messaging.send('loggerUI', { + what: 'setURLFilteringRule', + context: selectValue('select.dynamic.origin'), + url: target.getAttribute('data-url'), + type: uglyTypeFromSelector('dynamic'), + action: 0, + persist: persist, + }).then(( ) => { + colorize(); + }); ev.stopPropagation(); return; } // add "allow" url filtering rule if ( tcl.contains('allow') ) { - messaging.send( - 'loggerUI', - { - what: 'setURLFilteringRule', - context: selectValue('select.dynamic.origin'), - url: target.parentNode.getAttribute('data-url'), - type: uglyTypeFromSelector('dynamic'), - action: 2, - persist: persist - }, - colorize - ); + messaging.send('loggerUI', { + what: 'setURLFilteringRule', + context: selectValue('select.dynamic.origin'), + url: target.parentNode.getAttribute('data-url'), + type: uglyTypeFromSelector('dynamic'), + action: 2, + persist: persist, + }).then(( ) => { + colorize(); + }); ev.stopPropagation(); return; } // add "block" url filtering rule if ( tcl.contains('noop') ) { - messaging.send( - 'loggerUI', - { - what: 'setURLFilteringRule', - context: selectValue('select.dynamic.origin'), - url: target.parentNode.getAttribute('data-url'), - type: uglyTypeFromSelector('dynamic'), - action: 3, - persist: persist - }, - colorize - ); + messaging.send('loggerUI', { + what: 'setURLFilteringRule', + context: selectValue('select.dynamic.origin'), + url: target.parentNode.getAttribute('data-url'), + type: uglyTypeFromSelector('dynamic'), + action: 3, + persist: persist, + }).then(( ) => { + colorize(); + }); ev.stopPropagation(); return; } // add "block" url filtering rule if ( tcl.contains('block') ) { - messaging.send( - 'loggerUI', - { - what: 'setURLFilteringRule', - context: selectValue('select.dynamic.origin'), - url: target.parentNode.getAttribute('data-url'), - type: uglyTypeFromSelector('dynamic'), - action: 1, - persist: persist - }, - colorize - ); + messaging.send('loggerUI', { + what: 'setURLFilteringRule', + context: selectValue('select.dynamic.origin'), + url: target.parentNode.getAttribute('data-url'), + type: uglyTypeFromSelector('dynamic'), + action: 1, + persist: persist, + }).then(( ) => { + colorize(); + }); ev.stopPropagation(); return; } // Force a reload of the tab if ( tcl.contains('reload') ) { - messaging.send( - 'loggerUI', - { - what: 'reloadTab', - tabId: targetTabId - } - ); + messaging.send('loggerUI', { + what: 'reloadTab', + tabId: targetTabId, + }); ev.stopPropagation(); return; } // Hightlight corresponding element in target web page if ( tcl.contains('picker') ) { - messaging.send( - 'loggerUI', - { - what: 'launchElementPicker', - tabId: targetTabId, - targetURL: 'img\t' + targetURLs[0], - select: true - } - ); + messaging.send('loggerUI', { + what: 'launchElementPicker', + tabId: targetTabId, + targetURL: 'img\t' + targetURLs[0], + select: true, + }); ev.stopPropagation(); return; } @@ -1450,7 +1428,7 @@ const reloadTab = function(ev) { return urls; }; - const fillSummaryPaneFilterList = function(rows) { + const fillSummaryPaneFilterList = async function(rows) { const rawFilter = targetRow.children[1].textContent; const compiledFilter = targetRow.getAttribute('data-filter'); @@ -1509,25 +1487,19 @@ const reloadTab = function(ev) { }; if ( targetRow.classList.contains('networkRealm') ) { - messaging.send( - 'loggerUI', - { - what: 'listsFromNetFilter', - compiledFilter: compiledFilter, - rawFilter: rawFilter - }, - handleResponse - ); + const response = await messaging.send('loggerUI', { + what: 'listsFromNetFilter', + compiledFilter: compiledFilter, + rawFilter: rawFilter, + }); + handleResponse(response); } else if ( targetRow.classList.contains('cosmeticRealm') ) { - messaging.send( - 'loggerUI', - { - what: 'listsFromCosmeticFilter', - url: targetRow.children[6].textContent, - rawFilter: rawFilter, - }, - handleResponse - ); + const response = await messaging.send('loggerUI', { + what: 'listsFromCosmeticFilter', + url: targetRow.children[6].textContent, + rawFilter: rawFilter, + }); + handleResponse(response); } }; @@ -1789,7 +1761,7 @@ const reloadTab = function(ev) { modalDialog.show(); }; - const toggleOn = function(ev) { + const toggleOn = async function(ev) { targetRow = ev.target.closest('.canDetails'); if ( targetRow === null ) { return; } ev.stopPropagation(); @@ -1800,24 +1772,21 @@ const reloadTab = function(ev) { targetFrameHostname = targetRow.getAttribute('data-dochn') || ''; // We need the root domain names for best user experience. - messaging.send( - 'loggerUI', - { - what: 'getDomainNames', - targets: [ - targetURLs[0], - targetPageHostname, - targetFrameHostname - ] - }, - fillDialog - ); + const domains = await messaging.send('loggerUI', { + what: 'getDomainNames', + targets: [ + targetURLs[0], + targetPageHostname, + targetFrameHostname + ], + }); + fillDialog(domains); }; uDom('#netInspector').on( 'click', '.canDetails > span:nth-of-type(2),.canDetails > span:nth-of-type(3),.canDetails > span:nth-of-type(5)', - toggleOn + ev => { toggleOn(ev); } ); })(); @@ -2766,10 +2735,10 @@ const grabView = function() { const releaseView = function() { if ( logger.ownerId === undefined ) { return; } - vAPI.messaging.send( - 'loggerUI', - { what: 'releaseView', ownerId: logger.ownerId } - ); + vAPI.messaging.send('loggerUI', { + what: 'releaseView', + ownerId: logger.ownerId, + }); logger.ownerId = undefined; }; diff --git a/src/js/messaging.js b/src/js/messaging.js index 3a4bd3b08..4b3f22277 100644 --- a/src/js/messaging.js +++ b/src/js/messaging.js @@ -362,11 +362,35 @@ const popupDataFromRequest = async function(request) { return popupDataFromTabId(tabId, tabTitle); }; +const getDOMStats = async function(tabId) { + const results = await vAPI.tabs.executeScript(tabId, { + allFrames: true, + file: '/js/scriptlets/dom-survey.js', + runAt: 'document_end', + }); + + let elementCount = 0; + let scriptCount = 0; + results.forEach(result => { + if ( result instanceof Object === false ) { return; } + elementCount += result.elementCount; + scriptCount += result.scriptCount; + }); + + return { elementCount, scriptCount }; +}; + const onMessage = function(request, sender, callback) { let pageStore; // Async switch ( request.what ) { + case 'getPopupLazyData': + getDOMStats(request.tabId).then(results => { + callback(results); + }); + return; + case 'getPopupData': popupDataFromRequest(request).then(popupData => { callback(popupData); @@ -381,19 +405,6 @@ const onMessage = function(request, sender, callback) { let response; switch ( request.what ) { - case 'getPopupLazyData': - pageStore = µb.pageStoreFromTabId(request.tabId); - if ( pageStore !== null ) { - pageStore.hiddenElementCount = 0; - pageStore.scriptCount = 0; - vAPI.tabs.executeScript(request.tabId, { - allFrames: true, - file: '/js/scriptlets/dom-survey.js', - runAt: 'document_end' - }); - } - break; - case 'hasPopupContentChanged': pageStore = µb.pageStoreFromTabId(request.tabId); var lastModified = pageStore ? pageStore.contentLastModified : 0; @@ -792,14 +803,13 @@ const µb = µBlock; const getLocalData = async function() { const data = Object.assign({}, µb.restoreBackupSettings); data.storageUsed = await µb.getBytesInUse(); + data.cloudStorageSupported = µb.cloudStorageSupported; + data.privacySettingsSupported = µb.privacySettingsSupported; return data; }; const backupUserData = async function() { - const [ userFilters, localData ] = await Promise.all([ - µb.loadUserFilters(), - getLocalData(), - ]); + const userFilters = await µb.loadUserFilters(); const userData = { timeStamp: Date.now(), @@ -823,6 +833,8 @@ const backupUserData = async function() { µb.restoreBackupSettings.lastBackupTime = Date.now(); vAPI.storage.set(µb.restoreBackupSettings); + const localData = await getLocalData(); + return { localData, userData }; }; @@ -1348,21 +1360,6 @@ vAPI.messaging.listen({ // >>>>> start of local scope const µb = µBlock; -const broadcastTimers = new Map(); - -const domSurveyFinalReport = function(tabId) { - broadcastTimers.delete(tabId + '-domSurveyReport'); - - const pageStore = µb.pageStoreFromTabId(tabId); - if ( pageStore === null ) { return; } - - vAPI.messaging.broadcast({ - what: 'domSurveyFinalReport', - tabId: tabId, - affectedElementCount: pageStore.hiddenElementCount, - scriptCount: pageStore.scriptCount, - }); -}; const logCosmeticFilters = function(tabId, details) { if ( µb.logger.enabled === false ) { return; } @@ -1488,24 +1485,6 @@ const onMessage = function(request, sender, callback) { response = µb.applyFilterListSelection(request); break; - case 'domSurveyTransientReport': - if ( pageStore !== null ) { - if ( request.filteredElementCount ) { - pageStore.hiddenElementCount += request.filteredElementCount; - } - if ( request.scriptCount ) { - pageStore.scriptCount += request.scriptCount; - } - const broadcastKey = `${tabId}-domSurveyReport`; - if ( broadcastTimers.has(broadcastKey) === false ) { - broadcastTimers.set(broadcastKey, vAPI.setTimeout( - ( ) => { domSurveyFinalReport(tabId); }, - 103 - )); - } - } - break; - case 'inlinescriptFound': if ( µb.logger.enabled && pageStore !== null ) { const fctxt = µb.filteringContext.duplicate(); diff --git a/src/js/pagestore.js b/src/js/pagestore.js index 64a94614e..4ddc73b60 100644 --- a/src/js/pagestore.js +++ b/src/js/pagestore.js @@ -257,9 +257,7 @@ const PageStore = class { this.logData = undefined; this.perLoadBlockedRequestCount = 0; this.perLoadAllowedRequestCount = 0; - this.hiddenElementCount = ''; // Empty string means "unknown" this.remoteFontCount = 0; - this.scriptCount = 0; this.popupBlockedCount = 0; this.largeMediaCount = 0; this.largeMediaTimer = null; diff --git a/src/js/popup.js b/src/js/popup.js index 6da054767..ea9c4da34 100644 --- a/src/js/popup.js +++ b/src/js/popup.js @@ -668,49 +668,36 @@ let renderOnce = function() { /******************************************************************************/ -const renderPopupLazy = function() { - messaging.send( - 'popupPanel', - { what: 'getPopupLazyData', tabId: popupData.tabId } - ); +const renderPopupLazy = async function() { + const result = await messaging.send('popupPanel', { + what: 'getPopupLazyData', + tabId: popupData.tabId, + }); + if ( result instanceof Object === false ) { return; } + + let count = result.elementCount || 0; + uDom.nodeFromSelector('#no-cosmetic-filtering > span.fa-icon-badge') + .textContent = count !== 0 + ? Math.min(count, 99).toLocaleString() + : ''; + count = result.scriptCount || 0; + uDom.nodeFromSelector('#no-scripting > span.fa-icon-badge') + .textContent = count !== 0 + ? Math.min(count, 99).toLocaleString() + : ''; }; -const onPopupMessage = function(data) { - if ( !data ) { return; } - if ( data.tabId !== popupData.tabId ) { return; } - - switch ( data.what ) { - case 'domSurveyFinalReport': - let count = data.affectedElementCount || ''; - uDom.nodeFromSelector('#no-cosmetic-filtering > span.fa-icon-badge') - .textContent = typeof count === 'number' - ? Math.min(count, 99).toLocaleString() - : count; - count = data.scriptCount || ''; - uDom.nodeFromSelector('#no-scripting > span.fa-icon-badge') - .textContent = typeof count === 'number' - ? Math.min(count, 99).toLocaleString() - : count; - break; - } -}; - -messaging.addChannelListener('popup', onPopupMessage); - /******************************************************************************/ const toggleNetFilteringSwitch = function(ev) { if ( !popupData || !popupData.pageURL ) { return; } - messaging.send( - 'popupPanel', - { - what: 'toggleNetFiltering', - url: popupData.pageURL, - scope: ev.ctrlKey || ev.metaKey ? 'page' : '', - state: !uDom('body').toggleClass('off').hasClass('off'), - tabId: popupData.tabId - } - ); + messaging.send('popupPanel', { + what: 'toggleNetFiltering', + url: popupData.pageURL, + scope: ev.ctrlKey || ev.metaKey ? 'page' : '', + state: !uDom('body').toggleClass('off').hasClass('off'), + tabId: popupData.tabId, + }); renderTooltips('#switch'); hashFromPopupData(); }; @@ -718,14 +705,11 @@ const toggleNetFilteringSwitch = function(ev) { /******************************************************************************/ const gotoZap = function() { - messaging.send( - 'popupPanel', - { - what: 'launchElementPicker', - tabId: popupData.tabId, - zap: true - } - ); + messaging.send('popupPanel', { + what: 'launchElementPicker', + tabId: popupData.tabId, + zap: true, + }); vAPI.closePopup(); }; @@ -733,13 +717,10 @@ const gotoZap = function() { /******************************************************************************/ const gotoPick = function() { - messaging.send( - 'popupPanel', - { - what: 'launchElementPicker', - tabId: popupData.tabId - } - ); + messaging.send('popupPanel', { + what: 'launchElementPicker', + tabId: popupData.tabId, + }); vAPI.closePopup(); }; @@ -759,18 +740,15 @@ const gotoURL = function(ev) { url += '+' + popupData.tabId; } - messaging.send( - 'popupPanel', - { - what: 'gotoURL', - details: { - url: url, - select: true, - index: -1, - shiftKey: ev.shiftKey - } - } - ); + messaging.send('popupPanel', { + what: 'gotoURL', + details: { + url: url, + select: true, + index: -1, + shiftKey: ev.shiftKey + }, + }); vAPI.closePopup(); }; @@ -780,14 +758,11 @@ const gotoURL = function(ev) { const toggleFirewallPane = function() { popupData.dfEnabled = !popupData.dfEnabled; - messaging.send( - 'popupPanel', - { - what: 'userSettings', - name: 'dynamicFilteringEnabled', - value: popupData.dfEnabled - } - ); + messaging.send('popupPanel', { + what: 'userSettings', + name: 'dynamicFilteringEnabled', + value: popupData.dfEnabled, + }); // https://github.com/chrisaljoudi/uBlock/issues/996 // Remember the last state of the firewall pane. This allows to @@ -817,7 +792,7 @@ const mouseleaveCellHandler = function() { /******************************************************************************/ -const setFirewallRule = function(src, des, type, action, persist) { +const setFirewallRule = async function(src, des, type, action, persist) { // This can happen on pages where uBlock does not work if ( typeof popupData.pageHostname !== 'string' || @@ -826,24 +801,20 @@ const setFirewallRule = function(src, des, type, action, persist) { return; } - messaging.send( - 'popupPanel', - { - what: 'toggleFirewallRule', - tabId: popupData.tabId, - pageHostname: popupData.pageHostname, - srcHostname: src, - desHostname: des, - requestType: type, - action: action, - persist: persist - }, - response => { - cachePopupData(response); - updateAllFirewallCells(); - hashFromPopupData(); - } - ); + const response = await messaging.send('popupPanel', { + what: 'toggleFirewallRule', + tabId: popupData.tabId, + pageHostname: popupData.pageHostname, + srcHostname: src, + desHostname: des, + requestType: type, + action: action, + persist: persist, + }); + + cachePopupData(response); + updateAllFirewallCells(); + hashFromPopupData(); }; /******************************************************************************/ @@ -889,15 +860,12 @@ const setFirewallRuleHandler = function(ev) { /******************************************************************************/ const reloadTab = function(ev) { - messaging.send( - 'popupPanel', - { - what: 'reloadTab', - tabId: popupData.tabId, - select: vAPI.webextFlavor.soup.has('mobile'), - bypassCache: ev.ctrlKey || ev.metaKey || ev.shiftKey - } - ); + messaging.send('popupPanel', { + what: 'reloadTab', + tabId: popupData.tabId, + select: vAPI.webextFlavor.soup.has('mobile'), + bypassCache: ev.ctrlKey || ev.metaKey || ev.shiftKey, + }); // Polling will take care of refreshing the popup content // https://github.com/chrisaljoudi/uBlock/issues/748 @@ -930,17 +898,14 @@ const toggleMinimize = function(ev) { // Useful to take snapshots of the whole list of domains -- example: // https://github.com/gorhill/uBlock/issues/736#issuecomment-178879944 if ( ev.shiftKey && ev.ctrlKey ) { - messaging.send( - 'popupPanel', - { - what: 'gotoURL', - details: { - url: 'popup.html?tabId=' + popupData.tabId + '&responsive=1', - select: true, - index: -1 - } - } - ); + messaging.send('popupPanel', { + what: 'gotoURL', + details: { + url: 'popup.html?tabId=' + popupData.tabId + '&responsive=1', + select: true, + index: -1 + }, + }); vAPI.closePopup(); return; } @@ -948,76 +913,62 @@ const toggleMinimize = function(ev) { popupData.firewallPaneMinimized = uDom.nodeFromId('firewallContainer').classList.toggle('minimized'); - messaging.send( - 'popupPanel', - { - what: 'userSettings', - name: 'firewallPaneMinimized', - value: popupData.firewallPaneMinimized - } - ); + messaging.send('popupPanel', { + what: 'userSettings', + name: 'firewallPaneMinimized', + value: popupData.firewallPaneMinimized, + }); positionRulesetTools(); }; /******************************************************************************/ const saveFirewallRules = function() { - messaging.send( - 'popupPanel', - { - what: 'saveFirewallRules', - srcHostname: popupData.pageHostname, - desHostnames: popupData.hostnameDict - } - ); + messaging.send('popupPanel', { + what: 'saveFirewallRules', + srcHostname: popupData.pageHostname, + desHostnames: popupData.hostnameDict, + }); uDom.nodeFromId('firewallContainer').classList.remove('dirty'); }; /******************************************************************************/ -const revertFirewallRules = function() { - messaging.send( - 'popupPanel', - { - what: 'revertFirewallRules', - srcHostname: popupData.pageHostname, - desHostnames: popupData.hostnameDict, - tabId: popupData.tabId - }, - response => { - cachePopupData(response); - updateAllFirewallCells(); - updateHnSwitches(); - hashFromPopupData(); - } - ); +const revertFirewallRules = async function() { uDom.nodeFromId('firewallContainer').classList.remove('dirty'); + const response = await messaging.send('popupPanel', { + what: 'revertFirewallRules', + srcHostname: popupData.pageHostname, + desHostnames: popupData.hostnameDict, + tabId: popupData.tabId, + }); + cachePopupData(response); + updateAllFirewallCells(); + updateHnSwitches(); + hashFromPopupData(); }; /******************************************************************************/ -const toggleHostnameSwitch = function(ev) { +const toggleHostnameSwitch = async function(ev) { const target = ev.currentTarget; const switchName = target.getAttribute('id'); if ( !switchName ) { return; } target.classList.toggle('on'); - messaging.send( - 'popupPanel', - { - what: 'toggleHostnameSwitch', - name: switchName, - hostname: popupData.pageHostname, - state: target.classList.contains('on'), - tabId: popupData.tabId, - persist: popupData.dfEnabled === false || ev.ctrlKey || ev.metaKey - }, - response => { - cachePopupData(response); - updateAllFirewallCells(); - hashFromPopupData(); - } - ); renderTooltips('#' + switchName); + + const response = await messaging.send('popupPanel', { + what: 'toggleHostnameSwitch', + name: switchName, + hostname: popupData.pageHostname, + state: target.classList.contains('on'), + tabId: popupData.tabId, + persist: popupData.dfEnabled === false || ev.ctrlKey || ev.metaKey, + }); + + cachePopupData(response); + updateAllFirewallCells(); + hashFromPopupData(); }; /******************************************************************************/ @@ -1040,20 +991,17 @@ const toggleHostnameSwitch = function(ev) { // on demand rather than forcing the main process to assume a client may need // it and thus having to push it all the time unconditionally. -const pollForContentChange = (function() { +const pollForContentChange = (( ) => { let pollTimer; - const pollCallback = function() { + const pollCallback = async function() { pollTimer = undefined; - messaging.send( - 'popupPanel', - { - what: 'hasPopupContentChanged', - tabId: popupData.tabId, - contentLastModified: popupData.contentLastModified - }, - queryCallback - ); + const response = await messaging.send('popupPanel', { + what: 'hasPopupContentChanged', + tabId: popupData.tabId, + contentLastModified: popupData.contentLastModified, + }); + queryCallback(response); }; const queryCallback = function(response) { @@ -1074,20 +1022,18 @@ const pollForContentChange = (function() { /******************************************************************************/ -const getPopupData = function(tabId) { - const onDataReceived = function(response) { - cachePopupData(response); - renderOnce(); - renderPopup(); - renderPopupLazy(); // low priority rendering - hashFromPopupData(true); - pollForContentChange(); - }; - messaging.send( - 'popupPanel', - { what: 'getPopupData', tabId: tabId }, - onDataReceived - ); +const getPopupData = async function(tabId) { + const response = await messaging.send('popupPanel', { + what: 'getPopupData', + tabId, + }); + + cachePopupData(response); + renderOnce(); + renderPopup(); + renderPopupLazy(); // low priority rendering + hashFromPopupData(true); + pollForContentChange(); }; /******************************************************************************/ @@ -1151,9 +1097,9 @@ uDom('#switch').on('click', toggleNetFilteringSwitch); uDom('#gotoZap').on('click', gotoZap); uDom('#gotoPick').on('click', gotoPick); uDom('h2').on('click', toggleFirewallPane); -uDom('.hnSwitch').on('click', toggleHostnameSwitch); +uDom('.hnSwitch').on('click', ev => { toggleHostnameSwitch(ev); }); uDom('#saveRules').on('click', saveFirewallRules); -uDom('#revertRules').on('click', revertFirewallRules); +uDom('#revertRules').on('click', ( ) => { revertFirewallRules(); }); uDom('[data-i18n="popupAnyRulePrompt"]').on('click', toggleMinimize); uDom('body').on('mouseenter', '[data-tip]', onShowTooltip) diff --git a/src/js/scriptlets/cosmetic-logger.js b/src/js/scriptlets/cosmetic-logger.js index 6be34fb5b..ab3a3f721 100644 --- a/src/js/scriptlets/cosmetic-logger.js +++ b/src/js/scriptlets/cosmetic-logger.js @@ -195,15 +195,12 @@ const processTimer = new vAPI.SafeAnimationFrame(( ) => { if ( toLog.length === 0 ) { return; } - vAPI.messaging.send( - 'scriptlets', - { - what: 'logCosmeticFilteringData', - frameURL: window.location.href, - frameHostname: window.location.hostname, - matchedSelectors: toLog, - } - ); + vAPI.messaging.send('scriptlets', { + what: 'logCosmeticFilteringData', + frameURL: window.location.href, + frameHostname: window.location.hostname, + matchedSelectors: toLog, + }); //console.timeEnd('dom logger/scanning for matches'); }); diff --git a/src/js/scriptlets/dom-survey.js b/src/js/scriptlets/dom-survey.js index b31778a98..4a9791c3c 100644 --- a/src/js/scriptlets/dom-survey.js +++ b/src/js/scriptlets/dom-survey.js @@ -49,37 +49,15 @@ const scriptTags = document.querySelectorAll('script[src]'); - let filteredElementCount = 0; + let elementCount = 0; if ( vAPI.domFilterer ) { - filteredElementCount = vAPI.domFilterer.getFilteredElementCount(); + elementCount = vAPI.domFilterer.getFilteredElementCount(); } - vAPI.messaging.send( - 'scriptlets', - { - what: 'domSurveyTransientReport', - filteredElementCount: filteredElementCount, - scriptCount: inlineScriptCount + scriptTags.length, - } - ); + // IMPORTANT: This is returned to the injector, so this MUST be + // the last statement. + return { + elementCount, + scriptCount: inlineScriptCount + scriptTags.length, + }; })(); - - - - - - - - -/******************************************************************************* - - DO NOT: - - Remove the following code - - Add code beyond the following code - Reason: - - https://github.com/gorhill/uBlock/pull/3721 - - uBO never uses the return value from injected content scripts - -**/ - -void 0; diff --git a/src/js/scriptlets/element-picker.js b/src/js/scriptlets/element-picker.js index 082dcda91..1da2e8ab4 100644 --- a/src/js/scriptlets/element-picker.js +++ b/src/js/scriptlets/element-picker.js @@ -371,15 +371,12 @@ const netFilterFromUnion = function(toMergeURL, out) { ) { lastNetFilterHostname = parsedURL.host; lastNetFilterUnion = toMergeURL; - vAPI.messaging.send( - 'elementPicker', - { - what: 'elementPickerEprom', - lastNetFilterSession: lastNetFilterSession, - lastNetFilterHostname: lastNetFilterHostname, - lastNetFilterUnion: lastNetFilterUnion - } - ); + vAPI.messaging.send('elementPicker', { + what: 'elementPickerEprom', + lastNetFilterSession: lastNetFilterSession, + lastNetFilterHostname: lastNetFilterHostname, + lastNetFilterUnion: lastNetFilterUnion, + }); return; } @@ -398,15 +395,12 @@ const netFilterFromUnion = function(toMergeURL, out) { lastNetFilterUnion = mergedURL; // Remember across element picker sessions - vAPI.messaging.send( - 'elementPicker', - { - what: 'elementPickerEprom', - lastNetFilterSession: lastNetFilterSession, - lastNetFilterHostname: lastNetFilterHostname, - lastNetFilterUnion: lastNetFilterUnion - } - ); + vAPI.messaging.send('elementPicker', { + what: 'elementPickerEprom', + lastNetFilterSession: lastNetFilterSession, + lastNetFilterHostname: lastNetFilterHostname, + lastNetFilterUnion: lastNetFilterUnion, + }); }; /******************************************************************************/ @@ -854,7 +848,7 @@ const filterToDOMInterface = (( ) => { applied = false, previewing = false; - const queryAll = function(filter, callback) { + const queryAll = async function(filter, callback) { filter = filter.trim(); if ( filter === lastFilter ) { callback(lastResultset); @@ -883,15 +877,13 @@ const filterToDOMInterface = (( ) => { return; } // Procedural cosmetic filter - vAPI.messaging.send( - 'elementPicker', - { what: 'compileCosmeticFilterSelector', selector: selector }, - response => { - lastResultset = fromCompiledCosmeticFilter(response); - if ( previewing ) { apply(); } - callback(lastResultset); - } - ); + const response = await vAPI.messaging.send('elementPicker', { + what: 'compileCosmeticFilterSelector', + selector, + }); + lastResultset = fromCompiledCosmeticFilter(response); + if ( previewing ) { apply(); } + callback(lastResultset); }; // https://github.com/gorhill/uBlock/issues/1629 @@ -1190,17 +1182,14 @@ const onDialogClicked = function(ev) { filterToDOMInterface.preview(false); userFilterFromCandidate((filter = undefined, isCosmetic = false) => { if ( filter === undefined ) { return; } - vAPI.messaging.send( - 'elementPicker', - { - what: 'createUserFilter', - autoComment: true, - filters: filter, - origin: window.location.origin, - pageDomain: window.location.hostname, - killCache: isCosmetic === false, - } - ); + vAPI.messaging.send('elementPicker', { + what: 'createUserFilter', + autoComment: true, + filters: filter, + origin: window.location.origin, + pageDomain: window.location.hostname, + killCache: isCosmetic === false, + }); filterToDOMInterface.preview(rawFilterFromTextarea(), true); stopPicker(); }); @@ -1697,14 +1686,12 @@ const startPicker = function(details) { /******************************************************************************/ -const bootstrapPicker = function() { - pickerRoot.removeEventListener('load', bootstrapPicker); +const bootstrapPicker = async function() { vAPI.shutdown.add(stopPicker); - vAPI.messaging.send( - 'elementPicker', - { what: 'elementPickerArguments' }, - startPicker - ); + const details = await vAPI.messaging.send('elementPicker', { + what: 'elementPickerArguments', + }); + startPicker(details); }; /******************************************************************************/ @@ -1762,7 +1749,11 @@ vAPI.userStylesheet.apply(); // https://github.com/gorhill/uBlock/issues/2060 vAPI.domFilterer.excludeNode(pickerRoot); -pickerRoot.addEventListener('load', bootstrapPicker); +pickerRoot.addEventListener( + 'load', + ( ) => { bootstrapPicker(); }, + { once: true } +); document.documentElement.appendChild(pickerRoot); /******************************************************************************/ diff --git a/src/js/scriptlets/load-large-media-interactive.js b/src/js/scriptlets/load-large-media-interactive.js index 7208af5a4..44c528c26 100644 --- a/src/js/scriptlets/load-large-media-interactive.js +++ b/src/js/scriptlets/load-large-media-interactive.js @@ -1,7 +1,7 @@ /******************************************************************************* uBlock Origin - a browser extension to block requests. - Copyright (C) 2015-2018 Raymond Hill + Copyright (C) 2015-present Raymond Hill This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -19,11 +19,11 @@ Home: https://github.com/gorhill/uBlock */ +'use strict'; + /******************************************************************************/ -(function() { - -'use strict'; +(( ) => { /******************************************************************************/ @@ -34,19 +34,18 @@ if ( typeof vAPI !== 'object' || vAPI.loadLargeMediaInteractive === true ) { /******************************************************************************/ -var largeMediaElementAttribute = 'data-' + vAPI.sessionId; -var largeMediaElementSelector = +const largeMediaElementAttribute = 'data-' + vAPI.sessionId; +const largeMediaElementSelector = ':root audio[' + largeMediaElementAttribute + '],\n' + ':root img[' + largeMediaElementAttribute + '],\n' + ':root video[' + largeMediaElementAttribute + ']'; /******************************************************************************/ -var mediaNotLoaded = function(elem) { - var src = elem.getAttribute('src') || ''; - if ( src === '' ) { - return false; - } +const mediaNotLoaded = function(elem) { + const src = elem.getAttribute('src') || ''; + if ( src === '' ) { return false; } + switch ( elem.localName ) { case 'audio': case 'video': @@ -55,7 +54,7 @@ var mediaNotLoaded = function(elem) { if ( elem.naturalWidth !== 0 || elem.naturalHeight !== 0 ) { break; } - var style = window.getComputedStyle(elem); + const style = window.getComputedStyle(elem); // For some reason, style can be null with Pale Moon. return style !== null ? style.getPropertyValue('display') !== 'none' : @@ -74,7 +73,7 @@ var mediaNotLoaded = function(elem) { // https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement // https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement -var surveyMissingMediaElements = function() { +const surveyMissingMediaElements = function() { var largeMediaElementCount = 0; var elems = document.querySelectorAll('audio,img,video'); var i = elems.length, elem; @@ -95,7 +94,7 @@ if ( surveyMissingMediaElements() === 0 ) { vAPI.loadLargeMediaInteractive = true; // Insert custom style tag. -var styleTag = document.createElement('style'); +let styleTag = document.createElement('style'); styleTag.setAttribute('type', 'text/css'); styleTag.textContent = [ largeMediaElementSelector + ' {', @@ -114,10 +113,10 @@ document.head.appendChild(styleTag); /******************************************************************************/ -var stayOrLeave = (function() { - var timer = null; +const stayOrLeave = (( ) => { + let timer = null; - var timeoutHandler = function(leaveNow) { + const timeoutHandler = function(leaveNow) { timer = null; if ( leaveNow !== true ) { if ( @@ -151,15 +150,26 @@ var stayOrLeave = (function() { /******************************************************************************/ -var onMouseClick = function(ev) { - if ( ev.button !== 0 ) { - return; - } +const loadImage = async function(elem) { + const src = elem.getAttribute('src'); + elem.removeAttribute('src'); - var elem = ev.target; - if ( elem.matches(largeMediaElementSelector) === false ) { - return; - } + await vAPI.messaging.send('scriptlets', { + what: 'temporarilyAllowLargeMediaElement', + }); + + elem.setAttribute('src', src); + elem.removeAttribute(largeMediaElementAttribute); + stayOrLeave(); +}; + +/******************************************************************************/ + +const onMouseClick = function(ev) { + if ( ev.button !== 0 ) { return; } + + const elem = ev.target; + if ( elem.matches(largeMediaElementSelector) === false ) { return; } if ( mediaNotLoaded(elem) === false ) { elem.removeAttribute(largeMediaElementAttribute); @@ -167,20 +177,7 @@ var onMouseClick = function(ev) { return; } - var src = elem.getAttribute('src'); - elem.removeAttribute('src'); - - var onLargeMediaElementAllowed = function() { - elem.setAttribute('src', src); - elem.removeAttribute(largeMediaElementAttribute); - stayOrLeave(); - }; - - vAPI.messaging.send( - 'scriptlets', - { what: 'temporarilyAllowLargeMediaElement' }, - onLargeMediaElementAllowed - ); + loadImage(elem); ev.preventDefault(); ev.stopPropagation(); @@ -190,8 +187,8 @@ document.addEventListener('click', onMouseClick, true); /******************************************************************************/ -var onLoad = function(ev) { - var elem = ev.target; +const onLoad = function(ev) { + const elem = ev.target; if ( elem.hasAttribute(largeMediaElementAttribute) ) { elem.removeAttribute(largeMediaElementAttribute); stayOrLeave(); @@ -202,8 +199,8 @@ document.addEventListener('load', onLoad, true); /******************************************************************************/ -var onLoadError = function(ev) { - var elem = ev.target; +const onLoadError = function(ev) { + const elem = ev.target; if ( mediaNotLoaded(elem) ) { elem.setAttribute(largeMediaElementAttribute, ''); } diff --git a/src/js/scriptlets/subscriber.js b/src/js/scriptlets/subscriber.js index 51784ea13..f654bb015 100644 --- a/src/js/scriptlets/subscriber.js +++ b/src/js/scriptlets/subscriber.js @@ -1,7 +1,7 @@ /******************************************************************************* uBlock Origin - a browser extension to block requests. - Copyright (C) 2015-2018 Raymond Hill + Copyright (C) 2015-present Raymond Hill This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -30,7 +30,7 @@ /******************************************************************************/ -(function() { +(( ) => { /******************************************************************************/ @@ -48,61 +48,57 @@ if ( typeof vAPI !== 'object' ) { /******************************************************************************/ -var onMaybeAbpLinkClicked = function(ev) { - if ( ev.button !== 0 ) { - return; - } +const processSubscription = async function(location, title) { + const details = await vAPI.messaging.send('scriptlets', { + what: 'subscriberData', + }); + + const confirmStr = details.confirmStr + .replace('{{url}}', location) + .replace('{{title}}', title); + if ( window.confirm(confirmStr) === false ) { return; } + + await vAPI.messaging.send('scriptlets', { + what: 'applyFilterListSelection', + toImport: location, + }); + + vAPI.messaging.send('scriptlets', { + what: 'reloadAllFilters', + }); +}; + +/******************************************************************************/ + +const onMaybeAbpLinkClicked = function(ev) { + if ( ev.button !== 0 ) { return; } // This addresses https://github.com/easylist/EasyListHebrew/issues/89 // Also, as per feedback to original fix: // https://github.com/gorhill/uBlock/commit/99a3d9631047d33dc7a454296ab3dd0a1e91d6f1 - var target = ev.target; + const target = ev.target; if ( ev.isTrusted === false || target instanceof HTMLAnchorElement === false ) { return; } - var href = target.href || ''; - if ( href === '' ) { - return; - } - var matches = /^(?:abp|ubo):\/*subscribe\/*\?location=([^&]+).*title=([^&]+)/.exec(href); + + const href = target.href || ''; + if ( href === '' ) { return; } + + let matches = /^(?:abp|ubo):\/*subscribe\/*\?location=([^&]+).*title=([^&]+)/.exec(href); if ( matches === null ) { matches = /^https?:\/\/.*?[&?]location=([^&]+).*?&title=([^&]+)/.exec(href); if ( matches === null ) { return; } } - var location = decodeURIComponent(matches[1]); - var title = decodeURIComponent(matches[2]); - var messaging = vAPI.messaging; + const location = decodeURIComponent(matches[1]); + const title = decodeURIComponent(matches[2]); + + processSubscription(location, title); ev.stopPropagation(); ev.preventDefault(); - - var onListsSelectionDone = function() { - messaging.send('scriptlets', { what: 'reloadAllFilters' }); - }; - - var onSubscriberDataReady = function(details) { - var confirmStr = details.confirmStr - .replace('{{url}}', location) - .replace('{{title}}', title); - if ( !window.confirm(confirmStr) ) { return; } - messaging.send( - 'scriptlets', - { - what: 'applyFilterListSelection', - toImport: location - }, - onListsSelectionDone - ); - }; - - messaging.send( - 'scriptlets', - { what: 'subscriberData' }, - onSubscriberDataReady - ); }; /******************************************************************************/ diff --git a/src/js/settings.js b/src/js/settings.js index aebab6c36..9ba495596 100644 --- a/src/js/settings.js +++ b/src/js/settings.js @@ -1,7 +1,7 @@ /******************************************************************************* uBlock Origin - a browser extension to block requests. - Copyright (C) 2014-2017 Raymond Hill + Copyright (C) 2014-present Raymond Hill This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -29,10 +29,6 @@ /******************************************************************************/ -const messaging = vAPI.messaging; - -/******************************************************************************/ - const handleImportFilePicker = function() { const file = this.files[0]; if ( file === undefined || file.name === '' ) { return; } @@ -74,16 +70,12 @@ const handleImportFilePicker = function() { const msg = vAPI.i18n('aboutRestoreDataConfirm') .replace('{{time}}', time.toLocaleString()); const proceed = window.confirm(msg); - if ( proceed ) { - messaging.send( - 'dashboard', - { - what: 'restoreUserData', - userData: userData, - file: filename - } - ); - } + if ( proceed !== true ) { return; } + vAPI.messaging.send('dashboard', { + what: 'restoreUserData', + userData, + file: filename, + }); }; const fr = new FileReader(); @@ -104,21 +96,22 @@ const startImportFilePicker = function() { /******************************************************************************/ -const exportToFile = function() { - messaging.send('dashboard', { what: 'backupUserData' }, response => { - if ( - response instanceof Object === false || - response.userData instanceof Object === false - ) { - return; - } - vAPI.download({ - 'url': 'data:text/plain;charset=utf-8,' + - encodeURIComponent(JSON.stringify(response.userData, null, ' ')), - 'filename': response.localData.lastBackupFile - }); - onLocalDataReceived(response.localData); +const exportToFile = async function() { + const response = await vAPI.messaging.send('dashboard', { + what: 'backupUserData', }); + if ( + response instanceof Object === false || + response.userData instanceof Object === false + ) { + return; + } + vAPI.download({ + 'url': 'data:text/plain;charset=utf-8,' + + encodeURIComponent(JSON.stringify(response.userData, null, ' ')), + 'filename': response.localData.lastBackupFile + }); + onLocalDataReceived(response.localData); }; /******************************************************************************/ @@ -175,9 +168,10 @@ const onLocalDataReceived = function(details) { const resetUserData = function() { const msg = vAPI.i18n('aboutResetDataConfirm'); const proceed = window.confirm(msg); - if ( proceed ) { - messaging.send('dashboard', { what: 'resetUserData' }); - } + if ( proceed !== true ) { return; } + vAPI.messaging.send('dashboard', { + what: 'resetUserData', + }); }; /******************************************************************************/ @@ -192,14 +186,11 @@ const synchronizeDOM = function() { /******************************************************************************/ const changeUserSettings = function(name, value) { - messaging.send( - 'dashboard', - { - what: 'userSettings', - name: name, - value: value - } - ); + vAPI.messaging.send('dashboard', { + what: 'userSettings', + name, + value, + }); }; /******************************************************************************/ @@ -253,7 +244,7 @@ const onUserSettingsReceived = function(details) { .on('click', onPreventDefault); }); - uDom('#export').on('click', exportToFile); + uDom('#export').on('click', ( ) => { exportToFile(); }); uDom('#import').on('click', startImportFilePicker); uDom('#reset').on('click', resetUserData); uDom('#restoreFilePicker').on('change', handleImportFilePicker); @@ -263,8 +254,13 @@ const onUserSettingsReceived = function(details) { /******************************************************************************/ -messaging.send('dashboard', { what: 'userSettings' }, onUserSettingsReceived); -messaging.send('dashboard', { what: 'getLocalData' }, onLocalDataReceived); +Promise.all([ + vAPI.messaging.send('dashboard', { what: 'userSettings' }), + vAPI.messaging.send('dashboard', { what: 'getLocalData' }), +]).then(results => { + onUserSettingsReceived(results[0]); + onLocalDataReceived(results[1]); +}); // https://github.com/uBlockOrigin/uBlock-issues/issues/591 document.querySelector( diff --git a/src/js/shortcuts.js b/src/js/shortcuts.js index 43551161e..8741f8d94 100644 --- a/src/js/shortcuts.js +++ b/src/js/shortcuts.js @@ -21,14 +21,14 @@ 'use strict'; -(function() { +(( ) => { // https://developer.mozilla.org/en-US/Add-ons/WebExtensions/manifest.json/commands#Shortcut_values - let validStatus0Keys = new Map([ + const validStatus0Keys = new Map([ [ 'alt', 'Alt' ], [ 'control', 'Ctrl' ], ]); - let validStatus1Keys = new Map([ + const validStatus1Keys = new Map([ [ 'a', 'A' ], [ 'b', 'B' ], [ 'c', 'C' ], @@ -93,42 +93,43 @@ [ 'shift', 'Shift' ], ]); - let commandNameFromElement = function(elem) { + const commandNameFromElement = function(elem) { while ( elem !== null ) { - let name = elem.getAttribute('data-name'); + const name = elem.getAttribute('data-name'); if ( typeof name === 'string' && name !== '' ) { return name; } elem = elem.parentElement; } }; - let captureShortcut = function(ev) { - let input = ev.target; - let name = commandNameFromElement(input); + const captureShortcut = function(ev) { + const input = ev.target; + const name = commandNameFromElement(input); if ( name === undefined ) { return; } - let before = input.value; - let after = new Set(); + const before = input.value; + const after = new Set(); let status = 0; - let updateCapturedShortcut = function() { + const updateCapturedShortcut = function() { return (input.value = Array.from(after).join('+')); }; - let blurHandler = function() { + const blurHandler = function() { input.removeEventListener('blur', blurHandler, true); input.removeEventListener('keydown', keydownHandler, true); input.removeEventListener('keyup', keyupHandler, true); if ( status === 2 ) { - vAPI.messaging.send( - 'dashboard', - { what: 'setShortcut', name: name, shortcut: updateCapturedShortcut() } - ); + vAPI.messaging.send('dashboard', { + what: 'setShortcut', + name, + shortcut: updateCapturedShortcut(), + }); } else { input.value = before; } }; - let keydownHandler = function(ev) { + const keydownHandler = function(ev) { ev.preventDefault(); ev.stopImmediatePropagation(); if ( ev.code === 'Escape' ) { @@ -136,7 +137,7 @@ return; } if ( status === 0 ) { - let keyName = validStatus0Keys.get(ev.key.toLowerCase()); + const keyName = validStatus0Keys.get(ev.key.toLowerCase()); if ( keyName !== undefined ) { after.add(keyName); updateCapturedShortcut(); @@ -161,11 +162,11 @@ } }; - let keyupHandler = function(ev) { + const keyupHandler = function(ev) { ev.preventDefault(); ev.stopImmediatePropagation(); if ( status !== 1 ) { return; } - let keyName = validStatus0Keys.get(ev.key.toLowerCase()); + const keyName = validStatus0Keys.get(ev.key.toLowerCase()); if ( keyName !== undefined && after.has(keyName) ) { after.clear(); updateCapturedShortcut(); @@ -185,29 +186,29 @@ input.addEventListener('keyup', keyupHandler, true); }; - let resetShortcut = function(ev) { - let name = commandNameFromElement(ev.target); + const resetShortcut = function(ev) { + const name = commandNameFromElement(ev.target); if ( name === undefined ) { return; } - let input = document.querySelector('[data-name="' + name + '"] input'); + const input = document.querySelector('[data-name="' + name + '"] input'); if ( input === null ) { return; } input.value = ''; - vAPI.messaging.send( - 'dashboard', - { what: 'setShortcut', name: name } - ); + vAPI.messaging.send('dashboard', { + what: 'setShortcut', + name, + }); }; - let onShortcutsReady = function(commands) { + const onShortcutsReady = function(commands) { if ( Array.isArray(commands) === false ) { return; } - let template = document.querySelector('#templates .commandEntry'); - let tbody = document.querySelector('.commandEntries tbody'); - for ( let command of commands ) { + const template = document.querySelector('#templates .commandEntry'); + const tbody = document.querySelector('.commandEntries tbody'); + for ( const command of commands ) { if ( command.description === '' ) { continue; } - let tr = template.cloneNode(true); + const tr = template.cloneNode(true); tr.setAttribute('data-name', command.name); tr.querySelector('.commandDesc').textContent = command.description; - let input = tr.querySelector('.commandShortcut input'); + const input = tr.querySelector('.commandShortcut input'); input.setAttribute('data-name', command.name); input.value = command.shortcut; input.addEventListener('focus', captureShortcut); @@ -216,6 +217,9 @@ } }; - vAPI.messaging.send('dashboard', { what: 'getShortcuts' }, onShortcutsReady); - + vAPI.messaging.send('dashboard', { + what: 'getShortcuts', + }).then(commands => { + onShortcutsReady(commands); + }); })(); diff --git a/src/js/whitelist.js b/src/js/whitelist.js index 66f48a8eb..63e77ab11 100644 --- a/src/js/whitelist.js +++ b/src/js/whitelist.js @@ -114,44 +114,45 @@ cmEditor.on('changes', whitelistChanged); /******************************************************************************/ -const renderWhitelist = function() { - const onRead = details => { - const first = reBadHostname === undefined; - if ( first ) { - reBadHostname = new RegExp(details.reBadHostname); - reHostnameExtractor = new RegExp(details.reHostnameExtractor); - whitelistDefaultSet = new Set(details.whitelistDefault); +const renderWhitelist = async function() { + const details = await messaging.send('dashboard', { + what: 'getWhitelist', + }); + + const first = reBadHostname === undefined; + if ( first ) { + reBadHostname = new RegExp(details.reBadHostname); + reHostnameExtractor = new RegExp(details.reHostnameExtractor); + whitelistDefaultSet = new Set(details.whitelistDefault); + } + const toAdd = new Set(whitelistDefaultSet); + for ( const line of details.whitelist ) { + const directive = directiveFromLine(line); + if ( whitelistDefaultSet.has(directive) === false ) { continue; } + toAdd.delete(directive); + if ( toAdd.size === 0 ) { break; } + } + if ( toAdd.size !== 0 ) { + details.whitelist.push(...Array.from(toAdd).map(a => `# ${a}`)); + } + details.whitelist.sort((a, b) => { + const ad = directiveFromLine(a); + const bd = directiveFromLine(b); + const abuiltin = whitelistDefaultSet.has(ad); + if ( abuiltin !== whitelistDefaultSet.has(bd) ) { + return abuiltin ? -1 : 1; } - const toAdd = new Set(whitelistDefaultSet); - for ( const line of details.whitelist ) { - const directive = directiveFromLine(line); - if ( whitelistDefaultSet.has(directive) === false ) { continue; } - toAdd.delete(directive); - if ( toAdd.size === 0 ) { break; } - } - if ( toAdd.size !== 0 ) { - details.whitelist.push(...Array.from(toAdd).map(a => `# ${a}`)); - } - details.whitelist.sort((a, b) => { - const ad = directiveFromLine(a); - const bd = directiveFromLine(b); - const abuiltin = whitelistDefaultSet.has(ad); - if ( abuiltin !== whitelistDefaultSet.has(bd) ) { - return abuiltin ? -1 : 1; - } - return ad.localeCompare(bd); - }); - let whitelistStr = details.whitelist.join('\n').trim(); - cachedWhitelist = whitelistStr; - if ( whitelistStr !== '' ) { - whitelistStr += '\n'; - } - cmEditor.setValue(whitelistStr); - if ( first ) { - cmEditor.clearHistory(); - } - }; - messaging.send('dashboard', { what: 'getWhitelist' }, onRead); + return ad.localeCompare(bd); + }); + let whitelistStr = details.whitelist.join('\n').trim(); + cachedWhitelist = whitelistStr; + if ( whitelistStr !== '' ) { + whitelistStr += '\n'; + } + cmEditor.setValue(whitelistStr); + if ( first ) { + cmEditor.clearHistory(); + } }; /******************************************************************************/ @@ -201,16 +202,13 @@ const exportWhitelistToFile = function() { /******************************************************************************/ -const applyChanges = function() { +const applyChanges = async function() { cachedWhitelist = cmEditor.getValue().trim(); - messaging.send( - 'dashboard', - { - what: 'setWhitelist', - whitelist: cachedWhitelist - }, - renderWhitelist - ); + await messaging.send('dashboard', { + what: 'setWhitelist', + whitelist: cachedWhitelist, + }); + renderWhitelist(); }; const revertChanges = function() { @@ -247,7 +245,7 @@ self.hasUnsavedData = function() { uDom('#importWhitelistFromFile').on('click', startImportFilePicker); uDom('#importFilePicker').on('change', handleImportFilePicker); uDom('#exportWhitelistToFile').on('click', exportWhitelistToFile); -uDom('#whitelistApply').on('click', applyChanges); +uDom('#whitelistApply').on('click', ( ) => { applyChanges(); }); uDom('#whitelistRevert').on('click', revertChanges); renderWhitelist();