summaryrefslogtreecommitdiff
path: root/tests/qunit/data
diff options
context:
space:
mode:
Diffstat (limited to 'tests/qunit/data')
-rw-r--r--tests/qunit/data/callMwLoaderTestCallback.js1
-rw-r--r--tests/qunit/data/defineTestCallback.js4
-rw-r--r--tests/qunit/data/load.mock.php58
-rw-r--r--tests/qunit/data/qunitOkCall.js4
-rw-r--r--tests/qunit/data/styleTest.css.php61
-rw-r--r--tests/qunit/data/testrunner.js194
-rw-r--r--tests/qunit/data/testwarm.inject.js349
7 files changed, 258 insertions, 413 deletions
diff --git a/tests/qunit/data/callMwLoaderTestCallback.js b/tests/qunit/data/callMwLoaderTestCallback.js
new file mode 100644
index 00000000..3f2ee92f
--- /dev/null
+++ b/tests/qunit/data/callMwLoaderTestCallback.js
@@ -0,0 +1 @@
+mw.loader.testCallback();
diff --git a/tests/qunit/data/defineTestCallback.js b/tests/qunit/data/defineTestCallback.js
deleted file mode 100644
index 6fcd4595..00000000
--- a/tests/qunit/data/defineTestCallback.js
+++ /dev/null
@@ -1,4 +0,0 @@
-window.mw.loader.testCallback = function() {
- start();
- ok( true, 'Implementing a module, is the callback timed properly ?');
-};
diff --git a/tests/qunit/data/load.mock.php b/tests/qunit/data/load.mock.php
new file mode 100644
index 00000000..1c189703
--- /dev/null
+++ b/tests/qunit/data/load.mock.php
@@ -0,0 +1,58 @@
+<?php
+/**
+ * Mock load.php with pre-defined test modules.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * @file
+ * @package MediaWiki
+ * @author Lupo
+ * @since 1.20
+ */
+header( 'Content-Type: text/javascript; charset=utf-8' );
+
+require_once '../../../includes/Xml.php';
+
+$moduleImplementations = array(
+ 'testUsesMissing' => "
+mw.loader.implement( 'testUsesMissing', function () {
+ QUnit.ok( false, 'Module test.usesMissing script should not run.');
+ QUnit.start();
+}, {}, {});
+",
+
+ 'testUsesNestedMissing' => "
+mw.loader.implement( 'testUsesNestedMissing', function () {
+ QUnit.ok( false, 'Module testUsesNestedMissing script should not run.');
+}, {}, {});
+",
+);
+
+$response = '';
+
+// Only support for non-encoded module names, full module names expected
+if ( isset( $_GET['modules'] ) ) {
+ $modules = explode( ',', $_GET['modules'] );
+ foreach ( $modules as $module ) {
+ if ( isset( $moduleImplementations[$module] ) ) {
+ $response .= $moduleImplementations[$module];
+ } else {
+ $response .= Xml::encodeJsCall( 'mw.loader.state', array( $module, 'missing' ) );
+ }
+ }
+}
+
+echo $response;
diff --git a/tests/qunit/data/qunitOkCall.js b/tests/qunit/data/qunitOkCall.js
index 2fb6e01d..25c42d6a 100644
--- a/tests/qunit/data/qunitOkCall.js
+++ b/tests/qunit/data/qunitOkCall.js
@@ -1,2 +1,2 @@
-start();
-ok( true, 'Successfully loaded!');
+QUnit.start();
+QUnit.assert.ok( true, 'Successfully loaded!');
diff --git a/tests/qunit/data/styleTest.css.php b/tests/qunit/data/styleTest.css.php
new file mode 100644
index 00000000..1870d5a3
--- /dev/null
+++ b/tests/qunit/data/styleTest.css.php
@@ -0,0 +1,61 @@
+<?php
+/**
+ * Dynamically create a simple stylesheet for unit tests in MediaWiki.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ * http://www.gnu.org/copyleft/gpl.html
+ *
+ * @file
+ * @package MediaWiki
+ * @author Timo Tijhof
+ * @since 1.20
+ */
+header( 'Content-Type: text/css; charset=utf-8' );
+
+/**
+ * Allows characters in ranges [a-z], [A-Z] and [0-9],
+ * in addition to a dot ("."), dash ("-"), space (" ") and hash ("#").
+ * @since 1.20
+ *
+ * @param string $val
+ * @return string Value with any illegal characters removed.
+ */
+function cssfilter( $val ) {
+ return preg_replace( '/[^A-Za-z0-9\.\- #]/', '', $val );
+}
+
+// Do basic sanitization
+$params = array_map( 'cssfilter', $_GET );
+
+// Defaults
+$selector = isset( $params['selector'] ) ? $params['selector'] : '.mw-test-example';
+$property = isset( $params['prop'] ) ? $params['prop'] : 'float';
+$value = isset( $params['val'] ) ? $params['val'] : 'right';
+$wait = isset( $params['wait'] ) ? (int)$params['wait'] : 0; // seconds
+
+sleep( $wait );
+
+$css = "
+/**
+ * Generated " . gmdate( 'r' ) . ".
+ * Waited {$wait}s.
+ */
+
+$selector {
+ $property: $value;
+}
+";
+
+echo trim( $css ) . "\n";
diff --git a/tests/qunit/data/testrunner.js b/tests/qunit/data/testrunner.js
index fdd3116b..efa65493 100644
--- a/tests/qunit/data/testrunner.js
+++ b/tests/qunit/data/testrunner.js
@@ -1,44 +1,61 @@
( function ( $, mw, QUnit, undefined ) {
-"use strict";
+/*global CompletenessTest */
+/*jshint evil:true */
+'use strict';
var mwTestIgnore, mwTester, addons;
/**
* Add bogus to url to prevent IE crazy caching
*
- * @param value {String} a relative path (eg. 'data/defineTestCallback.js'
+ * @param value {String} a relative path (eg. 'data/foo.js'
* or 'data/test.php?foo=bar').
- * @return {String} Such as 'data/defineTestCallback.js?131031765087663960'
+ * @return {String} Such as 'data/foo.js?131031765087663960'
*/
-QUnit.fixurl = function (value) {
+QUnit.fixurl = function ( value ) {
return value + (/\?/.test( value ) ? '&' : '?')
+ String( new Date().getTime() )
- + String( parseInt( Math.random()*100000, 10 ) );
+ + String( parseInt( Math.random() * 100000, 10 ) );
};
/**
* Configuration
*/
-QUnit.config.testTimeout = 5000;
-/**
- * MediaWiki debug mode
- */
-QUnit.config.urlConfig.push( 'debug' );
+// When a test() indicates asynchronicity with stop(),
+// allow 10 seconds to pass before killing the test(),
+// and assuming failure.
+QUnit.config.testTimeout = 10 * 1000;
+
+// Add a checkbox to QUnit header to toggle MediaWiki ResourceLoader debug mode.
+QUnit.config.urlConfig.push( {
+ id: 'debug',
+ label: 'Enable ResourceLoaderDebug',
+ tooltip: 'Enable debug mode in ResourceLoader'
+} );
/**
- * Load TestSwarm agent
+ * Load TestSwarm agent
*/
-if ( QUnit.urlParams.swarmURL ) {
- document.write( "<scr" + "ipt src='" + QUnit.fixurl( mw.config.get( 'wgScriptPath' )
- + '/tests/qunit/data/testwarm.inject.js' ) + "'></scr" + "ipt>" );
+// Only if the current url indicates that there is a TestSwarm instance watching us
+// (TestSwarm appends swarmURL to the test suites url it loads in iframes).
+// Otherwise this is just a simple view of Special:JavaScriptTest/qunit directly,
+// no point in loading inject.js in that case. Also, make sure that this instance
+// of MediaWiki has actually been configured with the required url to that inject.js
+// script. By default it is false.
+if ( QUnit.urlParams.swarmURL && mw.config.get( 'QUnitTestSwarmInjectJSPath' ) ) {
+ document.write( "<scr" + "ipt src='" + QUnit.fixurl( mw.config.get( 'QUnitTestSwarmInjectJSPath' ) ) + "'></scr" + "ipt>" );
}
/**
* CompletenessTest
*/
// Adds toggle checkbox to header
-QUnit.config.urlConfig.push( 'completenesstest' );
+QUnit.config.urlConfig.push( {
+ id: 'completenesstest',
+ label: 'Run CompletenessTest',
+ tooltip: 'Run the completeness test'
+} );
// Initiate when enabled
if ( QUnit.urlParams.completenesstest ) {
@@ -77,70 +94,87 @@ if ( QUnit.urlParams.completenesstest ) {
QUnit.config.urlConfig.push( 'mwlogenv' );
/**
- * Reset mw.config to a fresh copy of the live config for each test();
- * @param override {Object} [optional]
- * @example:
- * <code>
- * module( .., newMwEnvironment() );
- *
- * test( .., function () {
- * mw.config.set( 'foo', 'bar' ); // just for this test
- * } );
- *
- * test( .., function () {
- * mw.config.get( 'foo' ); // doesn't exist
- * } );
- *
- *
- * module( .., newMwEnvironment({ quux: 'corge' }) );
- *
- * test( .., function () {
- * mw.config.get( 'quux' ); // "corge"
- * mw.config.set( 'quux', "grault" );
- * } );
- *
- * test( .., function () {
- * mw.config.get( 'quux' ); // "corge"
- * } );
+ * Reset mw.config and others to a fresh copy of the live config for each test(),
+ * and restore it back to the live one afterwards.
+ * @param localEnv {Object} [optional]
+ * @example (see test suite at the bottom of this file)
* </code>
*/
QUnit.newMwEnvironment = ( function () {
- var liveConfig, freshConfigCopy, log;
+ var log, liveConfig, liveMessages;
liveConfig = mw.config.values;
+ liveMessages = mw.messages.values;
- freshConfigCopy = function ( custom ) {
+ function freshConfigCopy( custom ) {
// "deep=true" is important here.
// Otherwise we just create a new object with values referring to live config.
// e.g. mw.config.set( 'wgFileExtensions', [] ) would not effect liveConfig,
// but mw.config.get( 'wgFileExtensions' ).push( 'png' ) would as the array
// was passed by reference in $.extend's loop.
- return $.extend({}, liveConfig, custom, /*deep=*/true );
- };
+ return $.extend( {}, liveConfig, custom, /*deep=*/true );
+ }
+
+ function freshMessagesCopy( custom ) {
+ return $.extend( {}, liveMessages, custom, /*deep=*/true );
+ }
log = QUnit.urlParams.mwlogenv ? mw.log : function () {};
- return function ( override ) {
- override = override || {};
+ return function ( localEnv ) {
+ localEnv = $.extend( {
+ // QUnit
+ setup: $.noop,
+ teardown: $.noop,
+ // MediaWiki
+ config: {},
+ messages: {}
+ }, localEnv );
return {
setup: function () {
log( 'MwEnvironment> SETUP for "' + QUnit.config.current.module
+ ': ' + QUnit.config.current.testName + '"' );
- // Greetings, mock configuration!
- mw.config.values = freshConfigCopy( override );
+
+ // Greetings, mock environment!
+ mw.config.values = freshConfigCopy( localEnv.config );
+ mw.messages.values = freshMessagesCopy( localEnv.messages );
+
+ localEnv.setup();
},
teardown: function () {
log( 'MwEnvironment> TEARDOWN for "' + QUnit.config.current.module
+ ': ' + QUnit.config.current.testName + '"' );
- // Farewell, mock configuration!
+
+ localEnv.teardown();
+
+ // Farewell, mock environment!
mw.config.values = liveConfig;
+ mw.messages.values = liveMessages;
}
};
};
}() );
+// $.when stops as soon as one fails, which makes sense in most
+// practical scenarios, but not in a unit test where we really do
+// need to wait until all of them are finished.
+QUnit.whenPromisesComplete = function () {
+ var altPromises = [];
+
+ $.each( arguments, function ( i, arg ) {
+ var alt = $.Deferred();
+ altPromises.push( alt );
+
+ // Whether this one fails or not, forwards it to
+ // the 'done' (resolve) callback of the alternative promise.
+ arg.always( alt.resolve );
+ });
+
+ return $.when.apply( $, altPromises );
+};
+
/**
* Add-on assertion helpers
*/
@@ -149,12 +183,12 @@ addons = {
// Expect boolean true
assertTrue: function ( actual, message ) {
- strictEqual( actual, true, message );
+ QUnit.push( actual === true, actual, true, message );
},
// Expect boolean false
assertFalse: function ( actual, message ) {
- strictEqual( actual, false, message );
+ QUnit.push( actual === false, actual, false, message );
},
// Expect numerical value less than X
@@ -175,14 +209,58 @@ addons = {
// Expect numerical value greater than or equal to X
gtOrEq: function ( actual, expected, message ) {
QUnit.push( actual >= expected, actual, 'greater than or equal to ' + expected, message );
+ }
+};
+
+$.extend( QUnit.assert, addons );
+
+/**
+ * Small test suite to confirm proper functionality of the utilities and
+ * initializations in this file.
+ */
+var envExecCount = 0;
+QUnit.module( 'mediawiki.tests.qunit.testrunner', QUnit.newMwEnvironment({
+ setup: function () {
+ envExecCount += 1;
+ this.mwHtmlLive = mw.html;
+ mw.html = {
+ escape: function () {
+ return 'mocked-' + envExecCount;
+ }
+ };
+ },
+ teardown: function () {
+ mw.html = this.mwHtmlLive;
+ },
+ config: {
+ testVar: 'foo'
},
+ messages: {
+ testMsg: 'Foo.'
+ }
+}) );
- // Backwards compatible with new verions of QUnit
- equals: window.equal,
- same: window.deepEqual
-};
+QUnit.test( 'Setup', 3, function ( assert ) {
+ assert.equal( mw.html.escape( 'foo' ), 'mocked-1', 'extra setup() callback was ran.' );
+ assert.equal( mw.config.get( 'testVar' ), 'foo', 'config object applied' );
+ assert.equal( mw.messages.get( 'testMsg' ), 'Foo.', 'messages object applied' );
+
+ mw.config.set( 'testVar', 'bar' );
+ mw.messages.set( 'testMsg', 'Bar.' );
+});
+
+QUnit.test( 'Teardown', 3, function ( assert ) {
+ assert.equal( mw.html.escape( 'foo' ), 'mocked-2', 'extra setup() callback was re-ran.' );
+ assert.equal( mw.config.get( 'testVar' ), 'foo', 'config object restored and re-applied after test()' );
+ assert.equal( mw.messages.get( 'testMsg' ), 'Foo.', 'messages object restored and re-applied after test()' );
+});
+
+QUnit.module( 'mediawiki.tests.qunit.testrunner-after', QUnit.newMwEnvironment() );
-$.extend( QUnit, addons );
-$.extend( window, addons );
+QUnit.test( 'Teardown', 3, function ( assert ) {
+ assert.equal( mw.html.escape( '<' ), '&lt;', 'extra teardown() callback was ran.' );
+ assert.equal( mw.config.get( 'testVar' ), null, 'config object restored to live in next module()' );
+ assert.equal( mw.messages.get( 'testMsg' ), null, 'messages object restored to live in next module()' );
+});
-})( jQuery, mediaWiki, QUnit );
+}( jQuery, mediaWiki, QUnit ) );
diff --git a/tests/qunit/data/testwarm.inject.js b/tests/qunit/data/testwarm.inject.js
deleted file mode 100644
index 14ee8f93..00000000
--- a/tests/qunit/data/testwarm.inject.js
+++ /dev/null
@@ -1,349 +0,0 @@
-/*
- Copyright (c) 2009 John Resig
-
- Permission is hereby granted, free of charge, to any person
- obtaining a copy of this software and associated documentation
- files (the "Software"), to deal in the Software without
- restriction, including without limitation the rights to use,
- copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the
- Software is furnished to do so, subject to the following
- conditions:
-
- The above copyright notice and this permission notice shall be
- included in all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
- OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
- HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- OTHER DEALINGS IN THE SOFTWARE.
-
-*/
-(function(){
-
- var DEBUG = false;
-
- var doPost = false;
-
- try {
- doPost = !!window.top.postMessage;
- } catch(e){}
-
- var search = window.location.search,
- url, index;
- if( ( index = search.indexOf( "swarmURL=" ) ) != -1 )
- url = decodeURIComponent( search.slice( index + 9 ) );
-
- if ( !DEBUG && (!url || url.indexOf("http") !== 0) ) {
- return;
- }
-
- var submitTimeout = 5;
-
- var curHeartbeat;
- var beatRate = 20;
-
- // Expose the TestSwarm API
- window.TestSwarm = {
- submit: submit,
- heartbeat: function(){
- if ( curHeartbeat ) {
- clearTimeout( curHeartbeat );
- }
-
- curHeartbeat = setTimeout(function(){
- submit({ fail: -1, total: -1 });
- }, beatRate * 1000);
- },
- serialize: function(){
- return trimSerialize();
- }
- };
-
- // Prevent careless things from executing
- window.print = window.confirm = window.alert = window.open = function(){};
-
- window.onerror = function(e){
- document.body.appendChild( document.createTextNode( "ERROR: " + e ));
- submit({ fail: 0, error: 1, total: 1 });
- return false;
- };
-
- // QUnit (jQuery)
- // http://docs.jquery.com/QUnit
- if ( typeof QUnit !== "undefined" ) {
- QUnit.done = function(results){
- submit({
- fail: results.failed,
- error: 0,
- total: results.total
- });
- };
-
- QUnit.log = window.TestSwarm.heartbeat;
- window.TestSwarm.heartbeat();
-
- window.TestSwarm.serialize = function(){
- // Clean up the HTML (remove any un-needed test markup)
- remove("nothiddendiv");
- remove("loadediframe");
- remove("dl");
- remove("main");
-
- // Show any collapsed results
- var ol = document.getElementsByTagName("ol");
- for ( var i = 0; i < ol.length; i++ ) {
- ol[i].style.display = "block";
- }
-
- return trimSerialize();
- };
-
- // UnitTestJS (Prototype, Scriptaculous)
- // http://github.com/tobie/unittest_js/tree/master
- } else if ( typeof Test !== "undefined" && Test && Test.Unit && Test.Unit.runners ) {
- var total_runners = Test.Unit.runners.length, cur_runners = 0;
- var total = 0, fail = 0, error = 0;
-
- for (var i = 0; i < Test.Unit.runners.length; i++) (function(i){
- var finish = Test.Unit.runners[i].finish;
- Test.Unit.runners[i].finish = function(){
- finish.call( this );
-
- var results = this.getResult();
- total += results.assertions;
- fail += results.failures;
- error += results.errors;
-
- if ( ++cur_runners === total_runners ) {
- submit({
- fail: fail,
- error: error,
- total: total
- });
- }
- };
- })(i);
-
- // JSSpec (MooTools)
- // http://jania.pe.kr/aw/moin.cgi/JSSpec
- } else if ( typeof JSSpec !== "undefined" && JSSpec && JSSpec.Logger ) {
- var onRunnerEnd = JSSpec.Logger.prototype.onRunnerEnd;
- JSSpec.Logger.prototype.onRunnerEnd = function(){
- onRunnerEnd.call(this);
-
- // Show any collapsed results
- var ul = document.getElementsByTagName("ul");
- for ( var i = 0; i < ul.length; i++ ) {
- ul[i].style.display = "block";
- }
-
- submit({
- fail: JSSpec.runner.getTotalFailures(),
- error: JSSpec.runner.getTotalErrors(),
- total: JSSpec.runner.totalExamples
- });
- };
-
- window.TestSwarm.serialize = function(){
- // Show any collapsed results
- var ul = document.getElementsByTagName("ul");
- for ( var i = 0; i < ul.length; i++ ) {
- ul[i].style.display = "block";
- }
-
- return trimSerialize();
- };
-
- // JSUnit
- // http://www.jsunit.net/
- // Note: Injection file must be included before the frames
- // are document.write()d into the page.
- } else if ( typeof JsUnitTestManager !== "undefined" ) {
- var _done = JsUnitTestManager.prototype._done;
- JsUnitTestManager.prototype._done = function(){
- _done.call(this);
-
- submit({
- fail: this.failureCount,
- error: this.errorCount,
- total: this.totalCount
- });
- };
-
- window.TestSwarm.serialize = function(){
- return "<pre>" + this.log.join("\n") + "</pre>";
- };
-
- // Selenium Core
- // http://seleniumhq.org/projects/core/
- } else if ( typeof SeleniumTestResult !== "undefined" && typeof LOG !== "undefined" ) {
- // Completely overwrite the postback
- SeleniumTestResult.prototype.post = function(){
- submit({
- fail: this.metrics.numCommandFailures,
- error: this.metrics.numCommandErrors,
- total: this.metrics.numCommandPasses + this.metrics.numCommandFailures + this.metrics.numCommandErrors
- });
- };
-
- window.TestSwarm.serialize = function(){
- var results = [];
- while ( LOG.pendingMessages.length ) {
- var msg = LOG.pendingMessages.shift();
- results.push( msg.type + ": " + msg.msg );
- }
-
- return "<pre>" + results.join("\n") + "</pre>";
- };
-
- // Dojo Objective Harness
- // http://docs.dojocampus.org/quickstart/doh
- } else if ( typeof doh !== "undefined" && doh._report ) {
- var _report = doh._report;
- doh._report = function(){
- _report.apply(this, arguments);
-
- submit({
- fail: doh._failureCount,
- error: doh._errorCount,
- total: doh._testCount
- });
- };
-
- window.TestSwarm.serialize = function(){
- return "<pre>" + document.getElementById("logBody").innerHTML + "</pre>";
- };
- // Screw.Unit
- // git://github.com/nathansobo/screw-unit.git
- } else if ( typeof Screw !== "undefined" && typeof jQuery !== 'undefined' && Screw && Screw.Unit ) {
- $(Screw).bind("after", function() {
- var passed = $('.passed').length;
- var failed = $('.failed').length;
- submit({
- fail: failed,
- error: 0,
- total: failed + passed
- });
- });
-
- $(Screw).bind("loaded", function() {
- $('.it')
- .bind("passed", window.TestSwarm.heartbeat)
- .bind("failed", window.TestSwarm.heartbeat);
- window.TestSwarm.heartbeat();
- });
-
- window.TestSwarm.serialize = function(){
- return trimSerialize();
- };
- }
-
- function trimSerialize(doc) {
- doc = doc || document;
-
- var scripts = doc.getElementsByTagName("script");
- while ( scripts.length ) {
- remove( scripts[0] );
- }
-
- var root = window.location.href.replace(/(https?:\/\/.*?)\/.*/, "$1");
- var cur = window.location.href.replace(/[^\/]*$/, "");
-
- var links = doc.getElementsByTagName("link");
- for ( var i = 0; i < links.length; i++ ) {
- var href = links[i].href;
- if ( href.indexOf("/") === 0 ) {
- href = root + href;
- } else if ( !/^https?:\/\//.test( href ) ) {
- href = cur + href;
- }
- links[i].href = href;
- }
-
- return ("<html>" + doc.documentElement.innerHTML + "</html>")
- .replace(/\s+/g, " ");
- }
-
- function remove(elem){
- if ( typeof elem === "string" ) {
- elem = document.getElementById( elem );
- }
-
- if ( elem ) {
- elem.parentNode.removeChild( elem );
- }
- }
-
- function submit(params){
- if ( curHeartbeat ) {
- clearTimeout( curHeartbeat );
- }
-
- var paramItems = (url.split("?")[1] || "").split("&");
-
- for ( var i = 0; i < paramItems.length; i++ ) {
- if ( paramItems[i] ) {
- var parts = paramItems[i].split("=");
- if ( !params[ parts[0] ] ) {
- params[ parts[0] ] = parts[1];
- }
- }
- }
-
- if ( !params.state ) {
- params.state = "saverun";
- }
-
- if ( !params.results ) {
- params.results = window.TestSwarm.serialize();
- }
-
- if ( doPost ) {
- // Build Query String
- var query = "";
-
- for ( var i in params ) {
- query += ( query ? "&" : "" ) + i + "=" +
- encodeURIComponent(params[i]);
- }
-
- if ( DEBUG ) {
- alert( query );
- } else {
- window.top.postMessage( query, "*" );
- }
-
- } else {
- var form = document.createElement("form");
- form.action = url;
- form.method = "POST";
-
- for ( var i in params ) {
- var input = document.createElement("input");
- input.type = "hidden";
- input.name = i;
- input.value = params[i];
- form.appendChild( input );
- }
-
- if ( DEBUG ) {
- alert( form.innerHTML );
- } else {
-
- // Watch for the result submission timing out
- setTimeout(function(){
- submit( params );
- }, submitTimeout * 1000);
-
- document.body.appendChild( form );
- form.submit();
- }
- }
- }
-
-})();