# lib/goog/testing/jsunit.js

    1// Copyright 2007 The Closure Library Authors. All Rights Reserved.2//3// Licensed under the Apache License, Version 2.0 (the "License");4// you may not use this file except in compliance with the License.5// You may obtain a copy of the License at6//7//      http://www.apache.org/licenses/LICENSE-2.08//9// Unless required by applicable law or agreed to in writing, software10// distributed under the License is distributed on an "AS-IS" BASIS,11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.12// See the License for the specific language governing permissions and13// limitations under the License.1415/**16 * @fileoverview Utilities for working with JsUnit.  Writes out the JsUnit file17 * that needs to be included in every unit test.18 *19 * Testing code should not have dependencies outside of goog.testing so as to20 * reduce the chance of masking missing dependencies.21 *22 */2324goog.provide('goog.testing.jsunit');2526goog.require('goog.testing.TestCase');27goog.require('goog.testing.TestRunner');282930/**31 * Base path for JsUnit app files, relative to Closure's base path.32 * @type {string}33 */34goog.testing.jsunit.BASE_PATH =35    '../../third_party/java/jsunit/core/app/';363738/**39 * Filename for the core JS Unit script.40 * @type {string}41 */42goog.testing.jsunit.CORE_SCRIPT =43    goog.testing.jsunit.BASE_PATH + 'jsUnitCore.js';444546/**47 * @define {boolean} If this code is being parsed by JsTestC, we let it disable48 * the onload handler to avoid running the test in JsTestC.49 */50goog.define('goog.testing.jsunit.AUTO_RUN_ONLOAD', true);515253/**54 * @define {number} Sets a delay in milliseconds after the window onload event55 * and running the tests. Used to prevent interference with Selenium and give56 * tests with asynchronous operations time to finish loading.57 */58goog.define('goog.testing.jsunit.AUTO_RUN_DELAY_IN_MS', 500);596061(function() {62  // Increases the maximum number of stack frames in Google Chrome from the63  // default 10 to 50 to get more useful stack traces.64  Error.stackTraceLimit = 50;6566  // Store a reference to the window's timeout so that it can't be overridden67  // by tests.68  /** @type {!Function} */69  var realTimeout = window.setTimeout;7071  // Check for JsUnit's test runner (need to check for >2.2 and <=2.2)72  if (top['JsUnitTestManager'] || top['jsUnitTestManager']) {73    // Running inside JsUnit so add support code.74    var path = goog.basePath + goog.testing.jsunit.CORE_SCRIPT;75    document.write('<script type="text/javascript" src="' +76                   path + '"></' + 'script>');7778  } else {7980    // Create a test runner.81    var tr = new goog.testing.TestRunner();8283    // Export it so that it can be queried by Selenium and tests that use a84    // compiled test runner.85    goog.exportSymbol('G_testRunner', tr);86    goog.exportSymbol('G_testRunner.initialize', tr.initialize);87    goog.exportSymbol('G_testRunner.isInitialized', tr.isInitialized);88    goog.exportSymbol('G_testRunner.isFinished', tr.isFinished);89    goog.exportSymbol('G_testRunner.isSuccess', tr.isSuccess);90    goog.exportSymbol('G_testRunner.getReport', tr.getReport);91    goog.exportSymbol('G_testRunner.getRunTime', tr.getRunTime);92    goog.exportSymbol('G_testRunner.getNumFilesLoaded', tr.getNumFilesLoaded);93    goog.exportSymbol('G_testRunner.setStrict', tr.setStrict);94    goog.exportSymbol('G_testRunner.logTestFailure', tr.logTestFailure);95    goog.exportSymbol('G_testRunner.getTestResults', tr.getTestResults);9697    // Export debug as a global function for JSUnit compatibility.  This just98    // calls log on the current test case.99    if (!goog.global['debug']) {100      goog.exportSymbol('debug', goog.bind(tr.log, tr));101    }102103    // If the application has defined a global error filter, set it now.  This104    // allows users who use a base test include to set the error filter before105    // the testing code is loaded.106    if (goog.global['G_errorFilter']) {107      tr.setErrorFilter(goog.global['G_errorFilter']);108    }109110    // Add an error handler to report errors that may occur during111    // initialization of the page.112    var onerror = window.onerror;113    window.onerror = function(error, url, line) {114      // Call any existing onerror handlers.115      if (onerror) {116        onerror(error, url, line);117      }118      if (typeof error == 'object') {119        // Webkit started passing an event object as the only argument to120        // window.onerror.  It doesn't contain an error message, url or line121        // number.  We therefore log as much info as we can.122        if (error.target && error.target.tagName == 'SCRIPT') {123          tr.logError('UNKNOWN ERROR: Script ' + error.target.src);124        } else {125          tr.logError('UNKNOWN ERROR: No error information available.');126        }127      } else {128        tr.logError('JS ERROR: ' + error + '\nURL: ' + url + '\nLine: ' + line);129      }130    };131132    // Create an onload handler, if the test runner hasn't been initialized then133    // no test has been registered with the test runner by the test file.  We134    // then create a new test case and auto discover any tests in the global135    // scope. If this code is being parsed by JsTestC, we let it disable the136    // onload handler to avoid running the test in JsTestC.137    if (goog.testing.jsunit.AUTO_RUN_ONLOAD) {138      var onload = window.onload;139      window.onload = function(e) {140        // Call any existing onload handlers.141        if (onload) {142          onload(e);143        }144        // Wait so that we don't interfere with WebDriver.145        realTimeout(function() {146          if (!tr.initialized) {147            var test = new goog.testing.TestCase(document.title);148            test.autoDiscoverTests();149            tr.initialize(test);150          }151          tr.execute();152        }, goog.testing.jsunit.AUTO_RUN_DELAY_IN_MS);153        window.onload = null;154      };155    }156  }157})();