From a91c4fd27e3773e96a61892be71bc7d28826a948 Mon Sep 17 00:00:00 2001 From: gorhill Date: Mon, 20 Oct 2014 21:19:24 -0400 Subject: [PATCH] issue #1: no more background page reference in popup --- src/js/background.js | 6 +- src/js/httpsb.js | 46 ++--------- src/js/matrix.js | 29 +------ src/js/messaging-handlers.js | 46 ++++++++++- src/js/popup.js | 151 ++++++++++++++--------------------- 5 files changed, 113 insertions(+), 165 deletions(-) diff --git a/src/js/background.js b/src/js/background.js index 20100f4..576c4cf 100644 --- a/src/js/background.js +++ b/src/js/background.js @@ -55,14 +55,14 @@ return { deleteLocalStorage: false, displayTextSize: '13px', maxLoggedRequests: 50, - popupHideBlacklisted: false, popupCollapseDomains: false, popupCollapseSpecificDomains: {}, + popupHideBlacklisted: false, + popupScopeLevel: '*', processBehindTheSceneRequests: false, processHyperlinkAuditing: true, processReferer: false, - scopeLevel: '*', - smartAutoReload: 'all', + smartAutoReload: 'current', spoofUserAgent: false, spoofUserAgentEvery: 5, spoofUserAgentWith: getDefaultUserAgentStrings(), diff --git a/src/js/httpsb.js b/src/js/httpsb.js index 08a290f..e19f6e7 100644 --- a/src/js/httpsb.js +++ b/src/js/httpsb.js @@ -25,10 +25,15 @@ (function() { var µm = µMatrix; - µm.tMatrix = new µm.Matrix(); - µm.tMatrix.whitelistCell('*', '*', '*'); µm.pMatrix = new µm.Matrix(); µm.pMatrix.whitelistCell('*', '*', '*'); + µm.pMatrix.toggleSwitch('chrome-extension-scheme', false); + µm.pMatrix.toggleSwitch('chrome-scheme', false); + µm.pMatrix.toggleSwitch('chromium-behind-the-scene', false); + µm.pMatrix.toggleSwitch('opera-scheme', false); + + µm.tMatrix = new µm.Matrix(); + µm.tMatrix.assign(µm.pMatrix); })(); /******************************************************************************/ @@ -212,43 +217,6 @@ /******************************************************************************/ -// Reset all rules to their default state. - -µMatrix.revertScopeRules = function(scopeKey) { - var tscope = this.temporaryScopeFromScopeKey(scopeKey); - if ( !tscope ) { - return; - } - var pscope = this.permanentScopeFromScopeKey(scopeKey); - if ( pscope ) { - // TODO: if global scope, intersect using ruleset - tscope.assign(pscope); - return; - } - - // https://github.com/gorhill/httpswitchboard/issues/248 - // If no permanent scope found, use generic rules in global scope - tscope.removeAllRules(); - pscope = this.permanentScopeFromScopeKey('*'); - tscope.mtxFiltering = pscope.mtxFiltering; - var listKeys = ['white', 'black']; - var listKey, list; - while ( listKey = listKeys.pop() ) { - list = pscope[listKey]; - for ( var ruleKey in list.list ) { - if ( list.list.hasOwnProperty(ruleKey) === false ) { - continue; - } - // Mind only rules which apply on any domain - if ( list.hostnameFromRuleKey(ruleKey) === '*' ) { - tscope[listKey].addOne(ruleKey); - } - } - } -}; - -/******************************************************************************/ - µMatrix.turnOff = function() { // rhill 2013-12-07: // Relinquish control over javascript execution to the user. diff --git a/src/js/matrix.js b/src/js/matrix.js index 6775daa..127e455 100644 --- a/src/js/matrix.js +++ b/src/js/matrix.js @@ -287,32 +287,6 @@ Matrix.prototype.evaluateCellZXY = function(srcHostname, desHostname, type) { /******************************************************************************/ -Matrix.prototype.evaluateRow = function(srcHostname, desHostname) { - var out = []; - for ( var type in typeBitOffsets ) { - if ( typeBitOffsets.hasOwnProperty(type) === false ) { - continue; - } - out.push(this.evaluateCell(srcHostname, desHostname, type)); - } - return out.join(''); -}; - -/******************************************************************************/ - -Matrix.prototype.evaluateRowZ = function(srcHostname, desHostname) { - var out = []; - for ( var type in typeBitOffsets ) { - if ( typeBitOffsets.hasOwnProperty(type) === false ) { - continue; - } - out.push(this.evaluateCellZ(srcHostname, desHostname, type)); - } - return out.join(''); -}; - -/******************************************************************************/ - Matrix.prototype.evaluateRowZXY = function(srcHostname, desHostname) { var out = []; for ( var type in typeBitOffsets ) { @@ -369,6 +343,9 @@ Matrix.prototype.extractZRules = function(srcHostname, desHostname, out) { /******************************************************************************/ Matrix.prototype.toggleSwitch = function(srcHostname, newState) { + if ( newState === undefined ) { + newState = !this.evaluateSwitchZ(srcHostname); + } delete this.switchedOn[srcHostname]; var oldState = this.evaluateSwitchZ(srcHostname); if ( newState === oldState ) { diff --git a/src/js/messaging-handlers.js b/src/js/messaging-handlers.js index 9c8b17b..a39627b 100644 --- a/src/js/messaging-handlers.js +++ b/src/js/messaging-handlers.js @@ -63,19 +63,28 @@ RowSnapshot.counts = (function() { /******************************************************************************/ var matrixSnapshot = function(details) { + var µmuser = µm.userSettings; var r = { tabId: details.tabId, url: '', hostname: '', domain: '', - scopeLevel: µm.userSettings.scopeLevel, + blockedCount: 0, scope: '*', headers: µm.Matrix.getColumnHeaders(), tSwitch: false, pSwitch: false, rows: {}, rowCount: 0, - diff: [] + diff: [], + userSettings: { + colorBlindFriendly: µmuser.colorBlindFriendly, + displayTextSize: µmuser.displayTextSize, + popupCollapseDomains: µmuser.popupCollapseDomains, + popupCollapseSpecificDomains: µmuser.popupCollapseSpecificDomains, + popupHideBlacklisted: µmuser.popupHideBlacklisted, + popupScopeLevel: µmuser.popupScopeLevel + } }; /* // Allow to scope on behind-the-scene virtual tab @@ -97,10 +106,11 @@ var matrixSnapshot = function(details) { r.url = pageStore.pageUrl; r.hostname = pageStore.pageHostname; r.domain = pageStore.pageDomain; + r.blockedCount = pageStore.requestStats.blocked.all; - if ( r.scopeLevel === 'site' ) { + if ( µmuser.popupScopeLevel === 'site' ) { r.scope = r.hostname; - } else if ( r.scopeLevel === 'domain' ) { + } else if ( µmuser.popupScopeLevel === 'domain' ) { r.scope = r.domain; } @@ -198,6 +208,34 @@ var onMessage = function(request, sender, callback) { response = matrixSnapshot(request); break; + case 'toggleMatrixSwitch': + µm.tMatrix.toggleSwitch(request.srcHostname); + break; + + case 'blacklistMatrixCell': + µm.tMatrix.blacklistCell( + request.srcHostname, + request.desHostname, + request.type + ); + break; + + case 'whitelistMatrixCell': + µm.tMatrix.whitelistCell( + request.srcHostname, + request.desHostname, + request.type + ); + break; + + case 'graylistMatrixCell': + µm.tMatrix.graylistCell( + request.srcHostname, + request.desHostname, + request.type + ); + break; + case 'applyDiffToPermanentMatrix': // aka "persist" if ( µm.pMatrix.applyDiff(request.diff, µm.tMatrix) ) { µm.saveMatrix(); diff --git a/src/js/popup.js b/src/js/popup.js index 74f090f..e440f79 100644 --- a/src/js/popup.js +++ b/src/js/popup.js @@ -44,16 +44,11 @@ const PaleGreen = Pale | Green; const DarkGray = Dark | Gray; const PaleGray = Pale | Gray; -var µMatrix = chrome.extension.getBackgroundPage().µMatrix; var matrixSnapshot = {}; var groupsSnapshot = []; var allHostnamesSnapshot = 'do not leave this initial string empty'; var targetTabId; -var targetPageURL; -var targetPageHostname; -var targetPageDomain; -var targetScope = '*'; var matrixCellHotspots = null; var matrixHeaderPrettyNames = { @@ -77,7 +72,7 @@ messaging.start('popup.js'); var onMessage = function(msg) { if ( msg.what === 'urlStatsChanged' ) { - if ( targetPageURL === msg.pageURL ) { + if ( matrixSnapshot.url === msg.pageURL ) { makeMenu(); } } @@ -88,17 +83,12 @@ messaging.listen(onMessage); /******************************************************************************/ /******************************************************************************/ -function getPageStats() { - return µMatrix.pageStatsFromTabId(targetTabId); -} - -/******************************************************************************/ - function getUserSetting(setting) { - return µMatrix.userSettings[setting]; + return matrixSnapshot.userSettings[setting]; } function setUserSetting(setting, value) { + matrixSnapshot.userSettings[setting] = value; messaging.tell({ what: 'userSettings', name: setting, @@ -138,7 +128,7 @@ function getGroupStats() { // First, group according to whether at least one node in the domain // hierarchy is white or blacklisted - var pageDomain = targetPageDomain; + var pageDomain = matrixSnapshot.domain; var rows = matrixSnapshot.rows; var columnOffsets = matrixSnapshot.headers; var anyTypeOffset = columnOffsets['*']; @@ -227,28 +217,6 @@ function getCellClass(hostname, type) { ' p' + getPermanentColor(hostname, type).toString(16); } -function getNextAction(hostname, type, leaning) { - var temporaryColor = getTemporaryColor(hostname, type); - var hue = temporaryColor & 0x03; - var saturation = temporaryColor & 0x80; - // special case: root toggle only between two states - if ( type === '*' && hostname === '*' ) { - return hue === Green ? 'blacklist' : 'whitelist'; - } - // Lean toward whitelisting? - if ( leaning === 'whitelisting' ) { - if ( saturation !== Dark ) { - return 'whitelist'; - } - return 'graylist'; - } - // Lean toward blacklisting - if ( saturation !== Dark ) { - return 'blacklist'; - } - return 'graylist'; -} - /******************************************************************************/ // This is required for when we update the matrix while it is open: @@ -351,21 +319,33 @@ function updateMatrixBehavior() { // handle user interaction with filters +function getCellAction(hostname, type, leaning) { + var temporaryColor = getTemporaryColor(hostname, type); + var hue = temporaryColor & 0x03; + // Special case: root toggle only between two states + if ( type === '*' && hostname === '*' ) { + return hue === Green ? 'blacklistMatrixCell' : 'whitelistMatrixCell'; + } + // When explicitly blocked/allowed, can only graylist + var saturation = temporaryColor & 0x80; + if ( saturation === Dark ) { + return 'graylistMatrixCell'; + } + return leaning === 'whitelisting' ? 'whitelistMatrixCell' : 'blacklistMatrixCell'; +} + function handleFilter(button, leaning) { - var µm = µMatrix; // our parent cell knows who we are var cell = button.ancestors('div.matCell'); var type = cell.prop('reqType'); var hostname = cell.prop('hostname'); - var nextAction = getNextAction(hostname, type, leaning); - if ( nextAction === 'blacklist' ) { - µm.blacklistTemporarily(targetScope, hostname, type); - } else if ( nextAction === 'whitelist' ) { - µm.whitelistTemporarily(targetScope, hostname, type); - } else { - µm.graylistTemporarily(targetScope, hostname, type); - } - updateMatrixSnapshot(); + var request = { + what: getCellAction(hostname, type, leaning), + srcHostname: matrixSnapshot.scope, + desHostname: hostname, + type: type + }; + messaging.ask(request, updateMatrixSnapshot); } function handleWhitelistFilter(button) { @@ -854,6 +834,9 @@ var makeMenu = function() { // Do all the stuff that needs to be done before building menu et al. function initMenuEnvironment() { + uDom('body').css('font-size', getUserSetting('displayTextSize')); + uDom('body').toggleClass('colorblind', getUserSetting('colorBlindFriendly') === true); + var prettyNames = matrixHeaderPrettyNames; var keys = Object.keys(prettyNames); var i = keys.length; @@ -871,32 +854,29 @@ function initMenuEnvironment() { // Create page scopes for the web page -function createGlobalScope() { - targetScope = '*'; - setUserSetting('scopeLevel', '*'); +function selectGlobalScope() { + setUserSetting('popupScopeLevel', '*'); updateMatrixSnapshot(); dropDownMenuHide(); } -function createDomainScope() { - targetScope = targetPageDomain; - setUserSetting('scopeLevel', 'domain'); +function selectDomainScope() { + setUserSetting('popupScopeLevel', 'domain'); updateMatrixSnapshot(); dropDownMenuHide(); } -function createSiteScope() { - targetScope = targetPageHostname; - setUserSetting('scopeLevel', 'site'); +function selectSiteScope() { + setUserSetting('popupScopeLevel', 'site'); updateMatrixSnapshot(); dropDownMenuHide(); } -function getClassFromTargetScope() { - if ( targetScope === '*' ) { +function getClassFromScope() { + if ( matrixSnapshot.scope === '*' ) { return 'tScopeGlobal'; } - if ( targetScope === targetPageDomain ) { + if ( matrixSnapshot.scope === matrixSnapshot.domain ) { return 'tScopeNarrow'; } return 'tScopeNarrow'; @@ -905,52 +885,44 @@ function getClassFromTargetScope() { function initScopeCell() { // It's possible there is no page URL at this point: some pages cannot // be filtered by µMatrix. - if ( !targetPageURL ) { + if ( matrixSnapshot.url === '' ) { return; } // Fill in the scope menu entries - if ( targetPageDomain === '' || targetPageDomain === targetPageHostname ) { - uDom('#scopeKeyDomain').css('display', 'none'); - } else { - uDom('#scopeKeyDomain').text(targetPageDomain); - } - uDom('#scopeKeySite').text(targetPageHostname); - var scopeLevel = getUserSetting('scopeLevel'); - if ( scopeLevel === 'site' ) { - targetScope = targetPageHostname; - } else if ( scopeLevel === 'domain' ) { - targetScope = targetPageDomain; + if ( matrixSnapshot.hostname === matrixSnapshot.domain ) { + uDom('#scopeKeySite').css('display', 'none'); } else { - targetScope = '*'; + uDom('#scopeKeySite').text(matrixSnapshot.hostname); } + uDom('#scopeKeyDomain').text(matrixSnapshot.domain); updateScopeCell(); } function updateScopeCell() { uDom('body') .removeClass('tScopeGlobal tScopeNarrow') - .addClass(getClassFromTargetScope()); - uDom('#scopeCell').text(targetScope.replace('*', '\u2217')); + .addClass(getClassFromScope()); + uDom('#scopeCell').text(matrixSnapshot.scope.replace('*', '\u2217')); } /******************************************************************************/ function updateMtxbutton() { - var µm = µMatrix; var masterSwitch = matrixSnapshot.tSwitch; - var pageStats = getPageStats(); - var count = pageStats ? pageStats.requestStats.blocked.all : ''; + var count = matrixSnapshot.blockedCount; var button = uDom('#buttonMtxFiltering'); button.toggleClass('disabled', !masterSwitch); - button.descendants('span.badge').text(µm.formatCount(count)); + button.descendants('span.badge').text(count.toLocaleString()); button.attr('data-tip', button.attr('data-tip').replace('{{count}}', count)); uDom('body').toggleClass('powerOff', !masterSwitch); } function toggleMtxFiltering() { - var µm = µMatrix; - µm.toggleTemporaryMtxFiltering(targetScope); - updateMatrixSnapshot(); + var request = { + what: 'toggleMatrixSwitch', + srcHostname: matrixSnapshot.scope + }; + messaging.ask(request, updateMatrixSnapshot); } /******************************************************************************/ @@ -1015,7 +987,7 @@ function revertAll() { function buttonReloadHandler() { messaging.tell({ what: 'forceReloadTab', - pageURL: targetPageURL + pageURL: matrixSnapshot.url }); } @@ -1065,16 +1037,13 @@ var onMatrixSnapshotReady = function(response) { matrixSnapshot = response; targetTabId = response.tabId; - targetPageURL = response.url; - targetPageHostname = response.hostname; - targetPageDomain = response.domain; // Now that tabId and pageURL are set, we can build our menu initMenuEnvironment(); makeMenu(); // After popup menu is built, check whether there is a non-empty matrix - if ( !targetPageURL ) { + if ( matrixSnapshot.url === '' ) { uDom('#matHead').remove(); uDom('#toolbarLeft').remove(); @@ -1116,10 +1085,6 @@ uDom.onLoad(function() { // Below is UI stuff which is not key to make the menu, so this can // be done without having to wait for a tab to be bound to the menu. - // Matrix appearance - uDom('body').css('font-size', getUserSetting('displayTextSize')); - uDom('body').toggleClass('colorblind', getUserSetting('colorBlindFriendly') === true); - // We reuse for all cells the one and only cell hotspots. uDom('#whitelist').on('click', function() { handleWhitelistFilter(uDom(this)); @@ -1137,9 +1102,9 @@ uDom.onLoad(function() { uDom('body') .on('mouseenter', '.matCell', mouseenterMatrixCellHandler) .on('mouseleave', '.matCell', mouseleaveMatrixCellHandler); - uDom('#scopeKeyGlobal').on('click', createGlobalScope); - uDom('#scopeKeyDomain').on('click', createDomainScope); - uDom('#scopeKeySite').on('click', createSiteScope); + uDom('#scopeKeyGlobal').on('click', selectGlobalScope); + uDom('#scopeKeyDomain').on('click', selectDomainScope); + uDom('#scopeKeySite').on('click', selectSiteScope); uDom('#buttonMtxFiltering').on('click', toggleMtxFiltering); uDom('#buttonPersist').on('click', persistMatrix); uDom('#buttonRevertScope').on('click', revertMatrix); @@ -1155,7 +1120,7 @@ uDom.onLoad(function() { uDom('#matList').on('click', '.g3Meta', function() { var collapsed = uDom(this) .toggleClass('g3Collapsed') - .hasClass('g3Collapsed'); + .hasClassName('g3Collapsed'); setUserSetting('popupHideBlacklisted', collapsed); }); });