开发者

Accesing DOM with pages using AJAX (Firefox extension)

I'm trying to learn to create extensions with Firefox but I'm running into some issues and I hope someone more experienced could give me some tips.

The idea was doing a dummy extension that would access the DOM once the page is loaded, so I hook onto DOMContentLoaded to later iterate over certain element class getElementsByClassName. The problem I noticed is that I get a zero length array as response. I assume this is due to the fact that the page uses asynchronous scripts to load some parts of the content, do when the event is triggered the content is not yet complete.

I found this interesting thread of someone running into a very similar problem: Interacting with DOM for AJAX webpages? and tried to test the answer proposed by someone. Unfortunately, when I run my script I get the following error: "getattribute is not a function"

Just for clarity, I'm using the same snippet from that post (which uses twitter.com for test)

window.addEventListener("DOMNodeInserted",
function(event){ 
    var streamItem = event.target;
    if (streamItem == null)
        return;

    if (streamItem.getAttribute('class') != 'stream-item')
        return;

    var tweet = streamItem.getElementsByClassName("tweet",streamItem)[0];
    var name = tweet.getAttribute("data-screen-name");
    if (name.toLowerCase() == 'some-username'.toLowerCase()) 
    {
        var icon = tweet.getElementsByTagName("img")[0];
        icon.style.display='none';
    }
}, 
false);

except that I'm using gBrowser.addEventListener() instead, which is called whenever I get a callback from window.add开发者_开发知识库EventListener("load") in my extension.

Any idea how to solve this issue? I'm currently using exactly the above script just for testing purposes, as it's an identical case for what I'm trying to achieve.


Felix Kling is correct, you should register your event handler on the content document - right now you are listening for nodes that are being added to the browser (most likely new tabs). Of course that's only possible when the content document is available, e.g. in the DOMContentLoaded event. This also has the advantage that you only slow down the documents that you really want to look at (having a DOMNodeInserted event listener in a document slows down DOM modifications quite a lot). Something like this (untested but should work):

gBrowser.addEventListener("DOMContentLoaded", function(event)
{
  var contentDoc = event.target;  // That's the document that just loaded

  // Check document URL, only add a listener to the document we want
  if (contentDoc.URL.indexOf("http://example.com/") != 0)
    return;

  contentDoc.addEventListener("DOMNodeInserted", function(event)
  {
    var streamItem = event.target;
    if (streamItem == null || streamItem.nodeType != Node.ELEMENT_NODE)
      return;

    ...
  });
}, false);

Note the additional check of the node type - there are also text nodes being inserted for example and those don't have the getAttribute method (which is probably causing your error). You only want to look at the element nodes.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜