Equivalent to beforeload event for Firefox extensions

04Apr11

Equivalent to beforeload event for Firefox extensions

Author: James Brady (Co-founder)

Level: Expert

Description: assumes detailed knowledge of Chrome and Firefox extension development

You can use the beforeload event to block loading of resources on webpages – Disconnect uses this to prevent Facebook widgets from loading and capturing your browsing data.

Disconnect

Here’s how you use it in Chrome. First, setup your a content script to run right at the start of a new document load, here’s what a manifest.json file might look like to get that done:

{
  "name": "Disconnect",
  "version": "0.1",
  "description": "Stop major third parties and search engines 
from tracking your browsing and search history (built on WebMynd).",
  "permissions": [ "tabs",  "http://*/*",  "https://*/*" ],
  "background_page": "webmynd.html",
  "content_scripts": [
    {
      "matches": [ "http://*/*", "https://*/*" ],
      "js": [
        "content.js"
      ],
      "run_at" : "document_start"
    }
  ]
} 

Second, in your content script (content.js), add an event listener for the beforeload event. Then within the event listener you can selectively use event.preventDefault() to stop a resource from loading.

document.addEventListener('beforeload', function(event) {
  if (event.url.match('facebook')) {
    event.preventDefault();
    $(event.target).remove();
  }
}, false);

Easy right? You need to be careful to not to put too much inside the event listener, like back-and-forth with the background page, since Chrome has pretty aggressive timeouts (presumably to stop extensions slowing down page loads too much)

But what about Firefox? Problem is, it doesn’t support the beforeload event. Luckily there’s an alternative though it’s harder work. You can setup an observer to listen for the http-on-modify-request event. This is called as the http request is made and allows you to modify headers and even cancel the request – here’s a snippet you can add to your overlay javascript to get this working:

Components.classes["@mozilla.org/observer-service;1"]
  .getService(Components.interfaces.nsIObserverService)
  .addObserver({
    observe: function(aSubject, aTopic, aData) {
  if ("http-on-modify-request" == aTopic) {
    var url = aSubject
    .QueryInterface(Components.interfaces.nsIHttpChannel)
    .originalURI.spec;
    if (url && url.match('facebook')) {
    aSubject.cancel(Components.results.NS_BINDING_SUCCEEDED);
    }
        }
    }
  }, "http-on-modify-request", false);

Learn more in Mozilla’s documentation on intercepting page loads and the observer service.

There are a few drawbacks to Mozilla’s approach that you need to watch for as compared to listening for the beforeload event in Chrome and Safari:

  • Your observer method is called for every single load request and there is no timeout so if you write inefficient code, you will significantly slow down the users’ browsing experience
  • The requests are not necessarily tied to a particular document object – some http-on-modify-request events are fired even before the onLocationChange event for a document load. This makes it tricky to get to the document and browser that actually triggered the request

That said, it’s good to know that you can intercept requests to load remote resources on Firefox as well as Chrome and Safari.

Advertisements


5 Responses to “Equivalent to beforeload event for Firefox extensions”

  1. nsIContentPolicy is a much better option for simply blocking certain types of content.

    • 2 Amir Nathoo

      Thanks for the comment Mike. nsiContentPolicy is definitely an option for intercepting page loads if you want to get into XPCOM solutions. AdBlock plus uses it.

      I’m guessing that most developers who are looking for as simple a solution as setting up a ‘beforeload’ listener in Chrome aren’t going to want to get that complex however. Other extensions like Tamper Data use the http-on-modify-request observer approach according to MDC.


  1. 1 My daily readings 04/05/2011 « Strange Kite
  2. 2 Some Firefox Extension Tricks | It May Be Pure Illusion
  3. 3 firefox » Blog Archive » Some Firefox Extension Tricks | It May Be Pure Illusion

%d bloggers like this: