From ee610b3aad679440da51da9449b345afda6f274d Mon Sep 17 00:00:00 2001 From: gorhill Date: Sun, 6 Jul 2014 19:14:32 -0400 Subject: [PATCH] toward 0.1.4.0 --- _locales/en/messages.json | 32 +++++++++-- _locales/fr/messages.json | 34 +++++++++--- _locales/it/messages.json | 34 +++++++++--- _locales/ru/messages.json | 32 +++++++++-- _locales/zh_CN/messages.json | 32 +++++++++-- dist/it/description.txt | 8 --- js/abp-filters.js | 20 +++---- js/async.js | 2 +- js/background.js | 1 + js/messaging-handlers.js | 55 ++++++++++-------- js/pagestore.js | 23 +++----- js/popup.js | 2 +- js/stats.js | 104 +++++++++++++++++++++-------------- js/tab.js | 40 +++++--------- js/traffic.js | 2 +- js/udom.js | 4 +- stats.html | 53 +++++++++++++----- 17 files changed, 307 insertions(+), 171 deletions(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 57ef7e5f734a0..0dd67de0fc240 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -113,19 +113,35 @@ "message": "You can inspect the details of blocked requests if you wish by enabling this option. The logging of blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", "description": "English: see _locales/en/messages.log" }, - "logBlockedRequestsHeaderType" : { + "logAllowedRequestsPrompt" : { + "message": "Enable the logging of non-blocked requests", + "description": "English: Enable the logging of non-blocked requests" + }, + "logAllowedRequestsHelp" : { + "message": "You can inspect the details of non-blocked requests if you wish by enabling this option. The logging of non-blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", + "description": "English: see _locales/en/messages.log" + }, + "logBlockedRequestsHeader" : { + "message": "Blocked requests", + "description": "English: Blocked requests" + }, + "logAllowedRequestsHeader" : { + "message": "Allowed requests", + "description": "English: Allowed requests" + }, + "logRequestsHeaderType" : { "message": "Type", "description": "English: Type" }, - "logBlockedRequestsHeaderDomain" : { + "logRequestsHeaderDomain" : { "message": "Domain", "description": "English: Domain" }, - "logBlockedRequestsHeaderURL" : { - "message": "Blocked URL", - "description": "English: Blocked URL" + "logRequestsHeaderURL" : { + "message": "URL", + "description": "English: URL" }, - "logBlockedRequestsHeaderFilter" : { + "logRequestsHeaderFilter" : { "message": "Filter", "description": "English: Filter" }, @@ -133,6 +149,10 @@ "message": "No blocked requests logged for this page", "description": "English: No blocked requests logged for this page" }, + "logAllowedRequestsEmpty" : { + "message": "No non-blocked requests logged for this page", + "description": "English: No non-blocked requests logged for this page" + }, "aboutChangelog" : { diff --git a/_locales/fr/messages.json b/_locales/fr/messages.json index a918fc1fc5aaa..0f91250f34f8d 100644 --- a/_locales/fr/messages.json +++ b/_locales/fr/messages.json @@ -113,19 +113,35 @@ "message": "Vous pouvez inspecter les détails des requêtes bloquées en activant cette option. La journalisation des requêtes bloquées augmente l'empreinte mémoire utilisée par µBlock. Puisque que bon nombre d'utilisateurs n'utiliseront jamais cette fonctionnalité, elle est désactivée par défaut.", "description": "English: see _locales/en/messages.log" }, - "logBlockedRequestsHeaderType" : { + "logAllowedRequestsPrompt" : { + "message": "Activer la journalisation des requêtes permises", + "description": "English: Enable the logging of non-blocked requests" + }, + "logAllowedRequestsHelp" : { + "message": "Vous pouvez inspecter les détails des requêtes permises en activant cette option. La journalisation des requêtes permises augmente l'empreinte mémoire utilisée par µBlock. Puisque que bon nombre d'utilisateurs n'utiliseront jamais cette fonctionnalité, elle est désactivée par défaut.", + "description": "English: see _locales/en/messages.log" + }, + "logBlockedRequestsHeader" : { + "message": "Requêtes bloquées", + "description": "English: Blocked requests" + }, + "logAllowedRequestsHeader" : { + "message": "Requêtes permises", + "description": "English: Allowed requests" + }, + "logRequestsHeaderType" : { "message": "Type", "description": "English: Type" }, - "logBlockedRequestsHeaderDomain" : { + "logRequestsHeaderDomain" : { "message": "Domaine", - "description": "English: Domaine" + "description": "English: Domain" }, - "logBlockedRequestsHeaderURL" : { - "message": "URL bloquée", - "description": "English: Blocked URL" + "logRequestsHeaderURL" : { + "message": "URL", + "description": "English: URL" }, - "logBlockedRequestsHeaderFilter" : { + "logRequestsHeaderFilter" : { "message": "Filtre", "description": "English: Filter" }, @@ -133,6 +149,10 @@ "message": "Il n'y a aucune requête bloquée dans le journal", "description": "English: No blocked requests logged for this page" }, + "logAllowedRequestsEmpty" : { + "message": "Il n'y a aucune requête non-bloquée dans le journal", + "description": "English: No non-blocked requests logged for this page" + }, "aboutChangelog" : { diff --git a/_locales/it/messages.json b/_locales/it/messages.json index cb04d3ac2b12d..b603cd81d3257 100644 --- a/_locales/it/messages.json +++ b/_locales/it/messages.json @@ -113,26 +113,46 @@ "message": "Puoi controllare i dettagli delle richieste bloccate se abiliti questa opzione. La registrazione delle richieste bloccate aumenta l'uso della memoria da parte di µBlock. Di default è disabilitata, poiché la maggior parte degli utenti non ha bisogno di questa funzione.", "description": "English: see _locales/en/messages.log" }, - "logBlockedRequestsHeaderType" : { + "logAllowedRequestsPrompt" : { + "message": "Enable the logging of non-blocked requests", + "description": "English: Enable the logging of non-blocked requests" + }, + "logAllowedRequestsHelp" : { + "message": "You can inspect the details of non-blocked requests if you wish by enabling this option. The logging of non-blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", + "description": "English: see _locales/en/messages.log" + }, + "logBlockedRequestsHeader" : { + "message": "Richieste bloccate", + "description": "English: Blocked requests" + }, + "logAllowedRequestsHeader" : { + "message": "Allowed requests", + "description": "English: Allowed requests" + }, + "logRequestsHeaderType" : { "message": "Tipo", "description": "English: Type" }, - "logBlockedRequestsHeaderDomain" : { + "logRequestsHeaderDomain" : { "message": "Dominio", "description": "English: Domain" }, - "logBlockedRequestsHeaderURL" : { - "message": "Indirizzo bloccato", - "description": "English: Blocked URL" + "logRequestsHeaderURL" : { + "message": "Indirizzo", + "description": "English: URL" }, - "logBlockedRequestsHeaderFilter" : { + "logRequestsHeaderFilter" : { "message": "Filtro", "description": "English: Filter" }, "logBlockedRequestsEmpty" : { - "message": "Nel registro, non ci sono richieste bloccate per questa pagina.", + "message": "Nel registro, non ci sono richieste bloccate per questa pagina", "description": "English: No blocked requests logged for this page" }, + "logAllowedRequestsEmpty" : { + "message": "No non-blocked requests logged for this page", + "description": "English: No non-blocked requests logged for this page" + }, "aboutChangelog" : { diff --git a/_locales/ru/messages.json b/_locales/ru/messages.json index b7fa549ccfa71..b4603a84b4191 100644 --- a/_locales/ru/messages.json +++ b/_locales/ru/messages.json @@ -113,19 +113,35 @@ "message": "You can inspect the details of blocked requests if you wish by enabling this option. The logging of blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", "description": "English: see _locales/en/messages.log" }, - "logBlockedRequestsHeaderType" : { + "logAllowedRequestsPrompt" : { + "message": "Enable the logging of non-blocked requests", + "description": "English: Enable the logging of non-blocked requests" + }, + "logAllowedRequestsHelp" : { + "message": "You can inspect the details of non-blocked requests if you wish by enabling this option. The logging of non-blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", + "description": "English: see _locales/en/messages.log" + }, + "logBlockedRequestsHeader" : { + "message": "Blocked requests", + "description": "English: Blocked requests" + }, + "logAllowedRequestsHeader" : { + "message": "Allowed requests", + "description": "English: Allowed requests" + }, + "logRequestsHeaderType" : { "message": "Type", "description": "English: Type" }, - "logBlockedRequestsHeaderDomain" : { + "logRequestsHeaderDomain" : { "message": "Domain", "description": "English: Domain" }, - "logBlockedRequestsHeaderURL" : { - "message": "Blocked URL", - "description": "English: Blocked URL" + "logRequestsHeaderURL" : { + "message": "URL", + "description": "English: URL" }, - "logBlockedRequestsHeaderFilter" : { + "logRequestsHeaderFilter" : { "message": "Filter", "description": "English: Filter" }, @@ -133,6 +149,10 @@ "message": "No blocked requests logged for this page", "description": "English: No blocked requests logged for this page" }, + "logAllowedRequestsEmpty" : { + "message": "No non-blocked requests logged for this page", + "description": "English: No non-blocked requests logged for this page" + }, "aboutChangelog" : { diff --git a/_locales/zh_CN/messages.json b/_locales/zh_CN/messages.json index 1d62946289796..a362338d9ed46 100644 --- a/_locales/zh_CN/messages.json +++ b/_locales/zh_CN/messages.json @@ -113,19 +113,35 @@ "message": "如果你想要开启此选项,你将可以查看拦截广告的详情。拦截记录会增加µBlock的内存占用。由于很多用户用不到这个功能,它默认是禁用的。", "description": "English: see _locales/en/messages.log" }, - "logBlockedRequestsHeaderType" : { + "logAllowedRequestsPrompt" : { + "message": "Enable the logging of non-blocked requests", + "description": "English: Enable the logging of non-blocked requests" + }, + "logAllowedRequestsHelp" : { + "message": "You can inspect the details of non-blocked requests if you wish by enabling this option. The logging of non-blocked requests increases the memory footprint of µBlock. Since many users will never use this feature, it is disabled by default.", + "description": "English: see _locales/en/messages.log" + }, + "logBlockedRequestsHeader" : { + "message": "Blocked requests", + "description": "English: Blocked requests" + }, + "logAllowedRequestsHeader" : { + "message": "Allowed requests", + "description": "English: Allowed requests" + }, + "logRequestsHeaderType" : { "message": "类型", "description": "English: Type" }, - "logBlockedRequestsHeaderDomain" : { + "logRequestsHeaderDomain" : { "message": "域名", "description": "English: Domain" }, - "logBlockedRequestsHeaderURL" : { - "message": "屏蔽网站", - "description": "English: Blocked URL" + "logRequestsHeaderURL" : { + "message": "网址", + "description": "English: URL" }, - "logBlockedRequestsHeaderFilter" : { + "logRequestsHeaderFilter" : { "message": "过滤", "description": "English: Filter" }, @@ -133,6 +149,10 @@ "message": "该页面没有拦截记录", "description": "English: No blocked requests logged for this page" }, + "logAllowedRequestsEmpty" : { + "message": "No non-blocked requests logged for this page", + "description": "English: No non-blocked requests logged for this page" + }, "aboutChangelog" : { diff --git a/dist/it/description.txt b/dist/it/description.txt index 1660960ca7d16..7075ab8d6c51d 100644 --- a/dist/it/description.txt +++ b/dist/it/description.txt @@ -36,14 +36,6 @@ Senza queste liste di filtri, questa estensione non è niente. Così se vuoi con *** -Poichè le recensioni non consentono all'autore di rispondere, ho deciso di rispondere attraverso il sito principale del progetto. - -https://github.com/gorhill/uBlock/wiki/My-answer-to-web-store-reviews-where-appropriate - -*** - -Dall'autore di HTTP Switchboard. - Gratuito. Open source with public license (GPLv3) Fatto dagli utenti per gli utenti. diff --git a/js/abp-filters.js b/js/abp-filters.js index f990bc92a2784..7a64a9b9641aa 100644 --- a/js/abp-filters.js +++ b/js/abp-filters.js @@ -1415,17 +1415,16 @@ FilterContainer.prototype.matchString = function(pageDetails, url, requestType, var categories = this.categories; // Test hostname-based block filters - var bf = false; - bf = this.matchAnyPartyHostname(requestHostname); - if ( bf === false && party === ThirdParty ) { - bf = this.match3rdPartyHostname(requestHostname); + var br = this.matchAnyPartyHostname(requestHostname); + if ( br === false && party === ThirdParty ) { + br = this.match3rdPartyHostname(requestHostname); } // This will be used by hostname-based filters pageHostname = pageDetails.pageHostname || ''; // Test against block filters - if ( bf === false ) { + if ( br === false ) { this.bucket0 = categories[this.makeCategoryKey(BlockAnyTypeAnyParty)]; this.bucket1 = categories[this.makeCategoryKey(BlockAnyType | party)]; this.bucket2 = categories[this.makeCategoryKey(BlockAnyTypeOneParty | domainParty)]; @@ -1435,11 +1434,11 @@ FilterContainer.prototype.matchString = function(pageDetails, url, requestType, this.bucket6 = categories[this.makeCategoryKey(BlockOneParty | type | domainParty)]; this.bucket7 = categories[this.makeCategoryKey(BlockOtherParties | type)]; - bf = this.matchTokens(); + br = this.matchTokens(); } // If there is no block filter, no need to test against allow filters - if ( bf === false ) { + if ( br === false ) { return false; } @@ -1453,11 +1452,12 @@ FilterContainer.prototype.matchString = function(pageDetails, url, requestType, this.bucket6 = categories[this.makeCategoryKey(AllowOneParty | type | domainParty)]; this.bucket7 = categories[this.makeCategoryKey(AllowOtherParties | type | domainParty)]; - if ( this.matchTokens() !== false ) { - return false; + var ar = this.matchTokens(); + if ( ar !== false ) { + return '@@' + ar; } - return bf; + return br; }; /******************************************************************************/ diff --git a/js/async.js b/js/async.js index fa0d680ec0e4f..c232829a27169 100644 --- a/js/async.js +++ b/js/async.js @@ -133,7 +133,7 @@ return asyncJobManager; // Update visual of extension icon. // A time out is used to coalesce adjacent requests to update badge. -µBlock.updateBadge = function(tabId) { +µBlock.updateBadgeAsync = function(tabId) { if ( tabId < 0 ) { return; } diff --git a/js/background.js b/js/background.js index 1cb5278d3de26..b1d883cb9e238 100644 --- a/js/background.js +++ b/js/background.js @@ -33,6 +33,7 @@ return { userSettings: { collapseBlocked: true, logBlockedRequests: false, + logAllowedRequests: false, parseAllABPHideFilters: true, netExceptionList: {}, showIconBadge: true diff --git a/js/messaging-handlers.js b/js/messaging-handlers.js index 597e6cbcbf7f7..e5ce663b70269 100644 --- a/js/messaging-handlers.js +++ b/js/messaging-handlers.js @@ -40,7 +40,8 @@ var getStats = function(request) { pageAllowedRequestCount: 0, netFilteringSwitch: false, cosmeticFilteringSwitch: false, - logBlockedRequests: µb.userSettings.logBlockedRequests + logBlockedRequests: µb.userSettings.logBlockedRequests, + logAllowedRequests: µb.userSettings.logAllowedRequests }; var pageStore = µb.pageStoreFromTabId(request.tabId); if ( pageStore ) { @@ -75,7 +76,7 @@ var onMessage = function(request, sender, callback) { request.hostname, request.state ); - µBlock.updateBadge(request.tabId); + µBlock.updateBadgeAsync(request.tabId); break; default: @@ -260,33 +261,43 @@ var onMessage = function(request, sender, callback) { var getPageDetails = function(µb, tabId) { var r = { - requests: [], + blockedRequests: [], + allowedRequests: [], hash: '' }; var pageStore = µb.pageStores[tabId]; if ( !pageStore ) { return r; } - var blockedRequests = pageStore.blockedRequests; - var details, pos; - var hasher = new YaMD5(); - for ( var requestURL in blockedRequests ) { - if ( blockedRequests.hasOwnProperty(requestURL) === false ) { - continue; - } - details = blockedRequests[requestURL]; - if ( typeof details !== 'string' ) { - continue; + var prepareRequests = function(requests, hasher) { + var r = []; + var details, pos; + for ( var requestURL in requests ) { + if ( requests.hasOwnProperty(requestURL) === false ) { + continue; + } + details = requests[requestURL]; + if ( typeof details !== 'string' ) { + continue; + } + hasher.appendStr(requestURL); + hasher.appendStr(details); + pos = details.indexOf('\t'); + r.push({ + type: details.slice(0, pos), + domain: µb.URI.domainFromURI(requestURL), + url: requestURL, + reason: details.slice(pos + 1) + }); } - hasher.appendStr(requestURL); - hasher.appendStr(details); - pos = details.indexOf('\t'); - r.requests.push({ - type: details.slice(0, pos), - domain: µb.URI.domainFromURI(requestURL), - url: requestURL, - reason: details.slice(pos + 1) - }); + return r; + } + var hasher = new YaMD5(); + if ( µb.userSettings.logBlockedRequests ) { + r.blockedRequests = prepareRequests(pageStore.blockedRequests, hasher); + } + if ( µb.userSettings.logAllowedRequests ) { + r.allowedRequests = prepareRequests(pageStore.allowedRequests, hasher); } r.hash = hasher.end(); return r; diff --git a/js/pagestore.js b/js/pagestore.js index fd94d9f168b04..d28459f080f7f 100644 --- a/js/pagestore.js +++ b/js/pagestore.js @@ -53,14 +53,6 @@ var pageStoreFactory = function(tabId, pageURL) { /******************************************************************************/ function PageStore(tabId, pageURL) { - this.tabId = -1; - this.pageURL = ''; - this.pageHostname = ''; - this.pageDomain = ''; - this.perLoadBlockedRequestCount = 0; - this.perLoadAllowedRequestCount = 0; - this.blockedRequests = {}; - this.disposeTime = 0; this.init(tabId, pageURL); } @@ -74,6 +66,7 @@ PageStore.prototype.init = function(tabId, pageURL) { this.perLoadBlockedRequestCount = 0; this.perLoadAllowedRequestCount = 0; this.blockedRequests = {}; + this.allowedRequests = {}; this.disposeTime = 0; return this; }; @@ -88,7 +81,7 @@ PageStore.prototype.dispose = function() { this.pageURL = ''; this.pageHostname = ''; this.pageDomain = ''; - if ( pageStoreJunkyard.length < 32 ) { + if ( pageStoreJunkyard.length < 8 ) { pageStoreJunkyard.push(this); } }; @@ -96,17 +89,19 @@ PageStore.prototype.dispose = function() { /******************************************************************************/ PageStore.prototype.recordRequest = function(type, url, reason) { - // rhill 2013-10-26: This needs to be called even if the request is - // already logged, since the request stats are cached for a while after - // the page is no longer visible in a browser tab. - µb.updateBadge(this.tabId); + var blocked = reason !== false && reason.slice(0, 2) !== '@@'; - if ( reason === false ) { + if ( !blocked ) { this.perLoadAllowedRequestCount++; µb.localSettings.allowedRequestCount++; + if ( µb.userSettings.logAllowedRequests ) { + this.allowedRequests[url] = type + '\t' + (reason || ''); + } return; } + µb.updateBadgeAsync(this.tabId); + this.perLoadBlockedRequestCount++; µb.localSettings.blockedRequestCount++; diff --git a/js/popup.js b/js/popup.js index adde7b02e5359..7e6c94c5e6b11 100644 --- a/js/popup.js +++ b/js/popup.js @@ -70,7 +70,7 @@ var renderStats = function() { uDom('#gotoLog').toggleClass( 'enabled', - stats.netFilteringSwitch && stats.logBlockedRequests + stats.logBlockedRequests || stats.logAllowedRequests ); var blocked = stats.pageBlockedRequestCount; diff --git a/js/stats.js b/js/stats.js index 6ea6d3f4f5392..5f6a430bfc714 100644 --- a/js/stats.js +++ b/js/stats.js @@ -31,13 +31,27 @@ messaging.start('stats.js'); /******************************************************************************/ -var logSettingChanged = function() { +var logBlockedSettingChanged = function() { messaging.tell({ what: 'userSettings', name: 'logBlockedRequests', value: this.checked }); - uDom('#blockedRequests').toggleClass('logEnabled', this.checked); + uDom('#requests table').toggleClass('hideBlocked', !this.checked); + uDom('#requests').toggleClass('logEnabled', this.checked || uDom('#logAllowedRequests').prop('checked')); + renderPageSelector(); +}; + +/******************************************************************************/ + +var logAllowedSettingChanged = function() { + messaging.tell({ + what: 'userSettings', + name: 'logAllowedRequests', + value: this.checked + }); + uDom('#requests table').toggleClass('hideAllowed', !this.checked); + uDom('#requests').toggleClass('logEnabled', this.checked || uDom('#logBlockedRequests').prop('checked')); renderPageSelector(); }; @@ -47,9 +61,10 @@ var cachedPageSelectors = {}; var cachedPageHash = ''; var toPrettyTypeNames = { - 'sub_frame': 'frame', - 'object': 'plugin', - 'xmlhttprequest': 'XHR' + 'stylesheet': 'css', + 'sub_frame': 'frame', + 'object': 'plugin', + 'xmlhttprequest': 'XHR' }; /******************************************************************************/ @@ -62,6 +77,9 @@ var renderURL = function(url, filter) { if ( pos > 0 ) { reText = reText.slice(0, pos); } + if ( reText.slice(0, 2) === '@@' ) { + reText = reText.slice(2); + } reText = reText .replace(/\./g, '\\.') .replace(/\?/g, '\\?') @@ -112,41 +130,40 @@ var renderPageDetails = function(tabId) { if ( details.hash === cachedPageHash ) { return; } - var blockedRequests = details.requests || []; - blockedRequests.sort(function(a, b) { - var r = a.domain.localeCompare(b.domain); - if ( r === 0 ) { + cachedPageHash = details.hash; + var renderRequests = function(requests, className) { + requests.sort(function(a, b) { + var r = a.domain.localeCompare(b.domain); + if ( r ) { return r; } r = a.reason.localeCompare(b.reason); - if ( r === 0 ) { - r = a.type.localeCompare(b.type); - } - } - return r; - }); - - uDom('#tableHeader ~ tr').remove(); - - var blockedRequest, requestURL; - var html = []; - - for ( var i = 0; i < blockedRequests.length; i++ ) { - blockedRequest = blockedRequests[i]; - html.push( - '', - '', toPrettyTypeNames[blockedRequest.type] || blockedRequest.type, - '', blockedRequest.domain, - '', renderURL(blockedRequest.url, blockedRequest.reason), - '', blockedRequest.reason - ); - } - if ( !html.length ) { + if ( r ) { return r; } + r = a.type.localeCompare(b.type); + if ( r ) { return r; } + return a.url.localeCompare(b.url); + }); + var html = [], request; html.push( - '', - chrome.i18n.getMessage('logBlockedRequestsEmpty') + '', + '

', + chrome.i18n.getMessage(className + (requests.length ? 'RequestsHeader' : 'RequestsEmpty')), + '

' ); - } - uDom('#tableHeader').insertAfter(html.join('')); - cachedPageHash = details.hash; + for ( var i = 0; i < requests.length; i++ ) { + request = requests[i]; + html.push( + '', + '', request.domain, + '', toPrettyTypeNames[request.type] || request.type, + '', renderURL(request.url, request.reason), + '', request.reason || '' + ); + } + return html; + }; + uDom('#requests .tableHeader ~ tr').remove(); + var htmlBlocked = renderRequests(details.blockedRequests || [], 'logBlocked'); + var htmlAllowed = renderRequests(details.allowedRequests || [], 'logAllowed'); + uDom('#requests .tableHeader').insertAfter(htmlBlocked.concat(htmlAllowed).join('')); }; messaging.ask({ what: 'getPageDetails', tabId: tabId }, onDataReceived); @@ -161,11 +178,14 @@ var pageSelectorChanged = function() { /******************************************************************************/ var renderPageSelector = function(targetTabId) { - if ( uDom('#logBlockedRequests').prop('checked') !== true ) { + if ( !uDom('#logBlockedRequests').prop('checked') && !uDom('#logAllowedRequests').prop('checked') ) { return; } var selectedTabId = targetTabId || parseInt(uDom('#pageSelector').val(), 10); var onTabReceived = function(tab) { + if ( !tab ) { + return; + } var html = [ '