I'm implementing a Firefox plugin. In the plugin's toolbar, I capture the current page and redirect users to the UK Google when they try to go to the Netherlands Google instead. However, this code takes forever to complete. When I type "google.nl" or "google.com/nl", my browser shows the Netherlands page and takes at least 1 second before redirecting.
Is there any way to make the redirect faster? Ideally, I'd like the user to not see the Netherlands Google page at all.
function loadURL(url) {
window._content.document.location = url;
window.content.focus();
}
var redirected = false;
function onChange()
{
var url = gBrowser.selectedBrowser.currentURI.spec;
url = encodeURIComponent(url);
if(url.indexOf("google.nl") !=-1 || url.indexOf("hl%3Dnl") !=-1){
if (!redirected){
redirected = true;
loadURL("https://www.google.co.uk/");
return;
}
}else{
redirected = false;
}
}
Note: onChange()
is triggered by container.addEventListener('DOMSubtreeModified',onChange, false);
Never use DOMSubtreeModified
that's a MutationEvent
which was supposed to have been removed. You should use MutationObserver
So in your case instead of container.addEventListener('DOMSubtreeModified, onChange, false);
do this:
const gMutationConfig = {
subtree: true,
childList: true
};
var gMutationFunc = function(ms) {
for (let m of ms) {
console.log(m.type, m);
//if (mutation.addedNodes && mutation.addedNodes.length > 0) { //this test if elements added
onChange();
}
};
var gMutationObserver = new this.DOMWindow.MutationObserver(container);
You probably should use nsIHTTPChannel
for the redirect to be the fastest
const { Ci, Cu, Cc, Cr } = require('chrome'); //const {interfaces: Ci, utils: Cu, classes: Cc, results: Cr } = Components;
Cu.import('resource://gre/modules/Services.jsm');
Cu.import('resource://gre/modules/devtools/Console.jsm');
var observers = {
'http-on-modify-request': {
observe: function (aSubject, aTopic, aData) {
console.info('http-on-modify-request: aSubject = ' + aSubject + ' | aTopic = ' + aTopic + ' | aData = ' + aData);
var httpChannel = aSubject.QueryInterface(Ci.nsIHttpChannel);
var requestUrl = httpChannel.URI.spec
if (requestUrl.indexOf('google.com') > -1) {
//httpChannel.cancel(Cr.NS_BINDING_ABORTED); //this aborts the load
httpChannel.redirectTo(Services.io.newURI('data:text,url_blocked', null, null)); //can redirect with this line, if dont want to redirect and just block, then uncomment this line and comment out line above (line 17)
}
},
reg: function () {
Services.obs.addObserver(observers['http-on-modify-request'], 'http-on-modify-request', false);
},
unreg: function () {
Services.obs.removeObserver(observers['http-on-modify-request'], 'http-on-modify-request');
}
}
};
To start start obseving all requests do this (for example on startup of your addon)
for (var o in observers) {
observers[o].reg();
}
Its important to stop observring (make sure to run this at least on shutdown of addon, you dont want to leave the observer registered for memory reasons)
for (var o in observers) {
observers[o].unreg();
}
Full working example of the observer service to block/redirect urls: https://github.com/Noitidart/PortableTester/tree/block-urls