PageRenderTime 18ms CodeModel.GetById 2ms app.highlight 12ms RepoModel.GetById 1ms app.codeStats 0ms

/services/sync/tps/extensions/mozmill/resource/modules/init.js

http://github.com/zpao/v8monkey
JavaScript | 212 lines | 106 code | 30 blank | 76 comment | 14 complexity | 3d71aacca4d0c339b41ec1e8ca02a14b MD5 | raw file
  1/* ***** BEGIN LICENSE BLOCK *****
  2 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
  3 *
  4 * The contents of this file are subject to the Mozilla Public License Version
  5 * 1.1 (the "License"); you may not use this file except in compliance with
  6 * the License. You may obtain a copy of the License at
  7 * http://www.mozilla.org/MPL/
  8 *
  9 * Software distributed under the License is distributed on an "AS IS" basis,
 10 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 11 * for the specific language governing rights and limitations under the
 12 * License.
 13 *
 14 * The Original Code is Mozilla Corporation Code.
 15 *
 16 * The Initial Developer of the Original Code is
 17 * Adam Christian.
 18 * Portions created by the Initial Developer are Copyright (C) 2008
 19 * the Initial Developer. All Rights Reserved.
 20 *
 21 * Contributor(s):
 22 *  Adam Christian <adam.christian@gmail.com>
 23 *  Mikeal Rogers <mikeal.rogers@gmail.com>
 24 *  Henrik Skupin <hskupin@mozilla.com>
 25 *
 26 * Alternatively, the contents of this file may be used under the terms of
 27 * either the GNU General Public License Version 2 or later (the "GPL"), or
 28 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 29 * in which case the provisions of the GPL or the LGPL are applicable instead
 30 * of those above. If you wish to allow use of your version of this file only
 31 * under the terms of either the GPL or the LGPL, and not to allow others to
 32 * use your version of this file under the terms of the MPL, indicate your
 33 * decision by deleting the provisions above and replace them with the notice
 34 * and other provisions required by the GPL or the LGPL. If you do not delete
 35 * the provisions above, a recipient may use your version of this file under
 36 * the terms of any one of the MPL, the GPL or the LGPL.
 37 *
 38 * ***** END LICENSE BLOCK ***** */
 39
 40var frame = {};   Components.utils.import('resource://mozmill/modules/frame.js', frame);
 41
 42/**
 43* Console listener which listens for error messages in the console and forwards
 44* them to the Mozmill reporting system for output.
 45*/
 46function ConsoleListener() {
 47 this.register();
 48}
 49ConsoleListener.prototype = {
 50 observe: function(aMessage) {
 51   var msg = aMessage.message;
 52   var re = /^\[.*Error:.*(chrome|resource):\/\/.*/i;
 53   if (msg.match(re)) {
 54     frame.events.fail(aMessage);
 55   }
 56 },
 57 QueryInterface: function (iid) {
 58	if (!iid.equals(Components.interfaces.nsIConsoleListener) && !iid.equals(Components.interfaces.nsISupports)) {
 59		throw Components.results.NS_ERROR_NO_INTERFACE;
 60   }
 61   return this;
 62 },
 63 register: function() {
 64   var aConsoleService = Components.classes["@mozilla.org/consoleservice;1"]
 65                              .getService(Components.interfaces.nsIConsoleService);
 66   aConsoleService.registerListener(this);
 67 },
 68 unregister: function() {
 69   var aConsoleService = Components.classes["@mozilla.org/consoleservice;1"]
 70                              .getService(Components.interfaces.nsIConsoleService);
 71   aConsoleService.unregisterListener(this);
 72 }
 73}
 74
 75// start listening
 76var consoleListener = new ConsoleListener();
 77
 78var EXPORTED_SYMBOLS = ["mozmill"];
 79
 80const Cc = Components.classes;
 81const Ci = Components.interfaces;
 82const Cu = Components.utils;
 83
 84var mozmill = Cu.import('resource://mozmill/modules/mozmill.js');
 85
 86// Observer for new top level windows
 87var windowObserver = {
 88  observe: function(subject, topic, data) {
 89    attachEventListeners(subject);
 90  }
 91};
 92
 93/**
 94 * Attach event listeners
 95 */
 96function attachEventListeners(window) {
 97  // These are the event handlers
 98  function pageShowHandler(event) {
 99    var doc = event.originalTarget;
100    var tab = window.gBrowser.getBrowserForDocument(doc);
101
102    if (tab) {
103      //log("*** Loaded tab: location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
104      tab.mozmillDocumentLoaded = true;
105    } else {
106      //log("*** Loaded HTML location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
107      doc.defaultView.mozmillDocumentLoaded = true;
108    }
109
110    // We need to add/remove the unload/pagehide event listeners to preserve caching.
111    window.gBrowser.addEventListener("beforeunload", beforeUnloadHandler, true);
112    window.gBrowser.addEventListener("pagehide", pageHideHandler, true);
113  };
114
115  var DOMContentLoadedHandler = function(event) {
116    var errorRegex = /about:.+(error)|(blocked)\?/;
117    if (errorRegex.exec(event.target.baseURI)) {
118      // Wait about 1s to be sure the DOM is ready
119      mozmill.utils.sleep(1000);
120
121      var tab = window.gBrowser.getBrowserForDocument(event.target);
122      if (tab)
123        tab.mozmillDocumentLoaded = true;
124
125      // We need to add/remove the unload event listener to preserve caching.
126      window.gBrowser.addEventListener("beforeunload", beforeUnloadHandler, true);
127    }
128  };
129
130  // beforeunload is still needed because pagehide doesn't fire before the page is unloaded.
131  // still use pagehide for cases when beforeunload doesn't get fired
132  function beforeUnloadHandler(event) {
133    var doc = event.originalTarget;
134    var tab = window.gBrowser.getBrowserForDocument(event.target);
135
136    if (tab) {
137      //log("*** Unload tab: location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
138      tab.mozmillDocumentLoaded = false;
139    } else {
140      //log("*** Unload HTML location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
141      doc.defaultView.mozmillDocumentLoaded = false;
142    }
143
144    window.gBrowser.removeEventListener("beforeunload", beforeUnloadHandler, true);
145  };
146
147  var pageHideHandler = function(event) {
148    // If event.persisted is false, the beforeUnloadHandler should fire
149    // and there is no need for this event handler.
150    if (event.persisted) {
151      var doc = event.originalTarget;
152      var tab = window.gBrowser.getBrowserForDocument(event.target);
153
154      if (tab) {
155        //log("*** Unload tab: location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
156        tab.mozmillDocumentLoaded = false;
157      } else {
158        //log("*** Unload HTML location=" + doc.location + ", baseURI=" + doc.baseURI + "\n");
159        doc.defaultView.mozmillDocumentLoaded = false;
160      }
161
162      window.gBrowser.removeEventListener("beforeunload", beforeUnloadHandler, true);
163    }
164
165  };
166
167  // Add the event handlers to the tabbedbrowser once its window has loaded
168  window.addEventListener("load", function(event) {
169    window.mozmillDocumentLoaded = true;
170
171
172    if (window.gBrowser) {
173      // Page is ready
174      window.gBrowser.addEventListener("pageshow", pageShowHandler, true);
175
176      // Note: Error pages will never fire a "load" event. For those we
177      // have to wait for the "DOMContentLoaded" event. That's the final state.
178      // Error pages will always have a baseURI starting with
179      // "about:" followed by "error" or "blocked".
180      window.gBrowser.addEventListener("DOMContentLoaded", DOMContentLoadedHandler, true);
181
182      // Leave page (use caching)
183      window.gBrowser.addEventListener("pagehide", pageHideHandler, true);
184    }
185  }, false);
186}
187
188/**
189 * Initialize Mozmill
190 */
191function initialize() {
192  // Activate observer for new top level windows
193  var observerService = Cc["@mozilla.org/observer-service;1"].
194                        getService(Ci.nsIObserverService);
195  observerService.addObserver(windowObserver, "toplevel-window-ready", false);
196
197  // Attach event listeners to all open windows
198  var enumerator = Cc["@mozilla.org/appshell/window-mediator;1"].
199                   getService(Ci.nsIWindowMediator).getEnumerator("");
200  while (enumerator.hasMoreElements()) {
201    var win = enumerator.getNext();
202    attachEventListeners(win);
203
204    // For windows or dialogs already open we have to explicitly set the property
205    // otherwise windows which load really quick never gets the property set and
206    // we fail to create the controller
207    win.mozmillDocumentLoaded = true;
208  };
209}
210
211initialize();
212