1
0
mirror of https://github.com/gorhill/uBlock.git synced 2024-10-06 09:37:12 +02:00

code review: saner way to find a popup's opener tab id

This commit is contained in:
gorhill 2017-01-08 17:52:38 -05:00
parent eca33ea659
commit 3b0d3e3330
2 changed files with 61 additions and 38 deletions

View File

@ -160,6 +160,7 @@ var contentObserver = {
cpMessageName: hostName + ':shouldLoad', cpMessageName: hostName + ':shouldLoad',
popupMessageName: hostName + ':shouldLoadPopup', popupMessageName: hostName + ':shouldLoadPopup',
ignoredPopups: new WeakMap(), ignoredPopups: new WeakMap(),
uniquePopupEventId: 1,
uniqueSandboxId: 1, uniqueSandboxId: 1,
modernFirefox: Services.vc.compare(Services.appinfo.platformVersion, '44') > 0, modernFirefox: Services.vc.compare(Services.appinfo.platformVersion, '44') > 0,
@ -466,35 +467,44 @@ var contentObserver = {
this.removeEventListener('keydown', contObs.ignorePopup, true); this.removeEventListener('keydown', contObs.ignorePopup, true);
this.removeEventListener('mousedown', contObs.ignorePopup, true); this.removeEventListener('mousedown', contObs.ignorePopup, true);
}, },
lookupPopupOpenerURL: function(popup) { lookupPopupOpener: function(popup) {
var opener, openerURL;
for (;;) { for (;;) {
opener = popup.opener; let opener = popup.opener;
if ( !opener ) { break; } if ( !opener ) { return; }
if ( opener.top ) { opener = opener.top; } if ( opener.top ) { opener = opener.top; }
if ( opener === popup ) { break; } if ( opener === popup ) { return; }
if ( !opener.location ) { break; } if ( !opener.location ) { return; }
if ( !this.reGoodPopupURLs.test(opener.location.href) ) { break; } if ( this.reValidPopups.test(opener.location.protocol) ) {
openerURL = opener.location.href; return opener;
}
// https://github.com/uBlockOrigin/uAssets/issues/255 // https://github.com/uBlockOrigin/uAssets/issues/255
// - Mind chained about:blank popups. // - Mind chained about:blank popups.
if ( openerURL !== 'about:blank' ) { break; } if ( opener.location.href !== 'about:blank' ) { return; }
popup = opener; popup = opener;
} }
return openerURL;
}, },
reGoodPopupURLs: /^(?:about:blank|blob:|data:|https?:|javascript:)/, reValidPopups: /^(?:blob|data|https?|javascript):/,
observe: function(subject, topic) { observe: function(subject, topic) {
// https://github.com/gorhill/uBlock/issues/2290 // https://github.com/gorhill/uBlock/issues/2290
if ( topic === 'content-document-global-created' ) { if ( topic === 'content-document-global-created' ) {
if ( subject !== subject.top ) { return; } if ( subject !== subject.top ) { return; }
if ( this.ignoredPopups.has(subject) ) { return; } if ( this.ignoredPopups.has(subject) ) { return; }
let openerURL = this.lookupPopupOpenerURL(subject); let opener = this.lookupPopupOpener(subject);
if ( !openerURL ) { return; } if ( !opener ) { return; }
let messager = getMessageManager(subject); let popupMessager = getMessageManager(subject);
if ( !messager ) { return; } if ( !popupMessager ) { return; }
messager.sendAsyncMessage(this.popupMessageName, openerURL); let openerMessager = getMessageManager(opener);
if ( !openerMessager ) { return; }
popupMessager.sendAsyncMessage(this.popupMessageName, {
id: this.uniquePopupEventId,
popup: true
});
openerMessager.sendAsyncMessage(this.popupMessageName, {
id: this.uniquePopupEventId,
opener: true
});
this.uniquePopupEventId += 1;
return; return;
} }

View File

@ -2362,32 +2362,45 @@ vAPI.net.registerListeners = function() {
} }
var shouldLoadPopupListenerMessageName = location.host + ':shouldLoadPopup'; var shouldLoadPopupListenerMessageName = location.host + ':shouldLoadPopup';
var shouldLoadPopupListenerEntries = [];
var shouldLoadPopupListener = function(e) { var shouldLoadPopupListener = function(e) {
if ( typeof vAPI.tabs.onPopupCreated !== 'function' ) { return; } if ( typeof vAPI.tabs.onPopupCreated !== 'function' ) { return; }
var target = e.target, var target = e.target,
openerURL = e.data, data = e.data,
popupTabId = tabWatcher.tabIdFromTarget(target), now = Date.now(),
openerTabId, entries = shouldLoadPopupListenerEntries,
uri; entry;
for ( var browser of tabWatcher.browsers() ) { var i = entries.length;
uri = browser.currentURI; while ( i-- ) {
entry = entries[i];
// Probably isn't the best method to identify the source tab. if ( entry.id === data.id ) {
entries.splice(i, 1);
// https://github.com/gorhill/uBlock/issues/450 break;
// Skip entry if no valid URI available. }
// Apparently URI can be undefined under some circumstances: I if ( entry.expire <= now ) {
// believe this may have to do with those very temporary entries.splice(i, 1);
// browser objects created when opening a new tab, i.e. related }
// to https://github.com/gorhill/uBlock/issues/212 entry = undefined;
if ( !uri || uri.spec !== openerURL ) { continue; } }
if ( !entry ) {
openerTabId = tabWatcher.tabIdFromTarget(browser); entry = {
if ( openerTabId === popupTabId ) { continue; } id: data.id,
popupTabId: undefined,
vAPI.tabs.onPopupCreated(popupTabId, openerTabId); openerTabId: undefined,
break; expire: now + 10000
};
entries.push(entry);
}
var tabId = tabWatcher.tabIdFromTarget(target);
if ( data.popup ) {
entry.popupTabId = tabId;
} else /* if ( data.opener ) */ {
entry.openerTabId = tabId;
}
if ( entry.popupTabId && entry.openerTabId ) {
vAPI.tabs.onPopupCreated(entry.popupTabId, entry.openerTabId);
} }
}; };