r91843 MediaWiki - Code Review archive

Repository:MediaWiki
Revision:r91842‎ | r91843 | r91844 >
Date:19:10, 10 July 2011
Author:krinkle
Status:ok
Tags:
Comment:
Centralize QUnit customizations for MediaWiki:
- Rename 'awesome.js' to 'defineTestCallback.js' (more descriptive)
- Move all runner customizations into 'testrunner.js'
- Move all customization files into /data
- Fix bug in jquery.qunit.completenesstest that sometimes caused the element to be re-created if it was ran again from the console.
- Centralize additional assertion helpers in testrunner.js
Modified paths:
  • /trunk/phase3/resources/jquery/jquery.qunit.completenessTest.js (modified) (history)
  • /trunk/phase3/tests/qunit/data (added) (history)
  • /trunk/phase3/tests/qunit/data/awesome.js (deleted) (history)
  • /trunk/phase3/tests/qunit/data/defineTestCallback.js (added) (history)
  • /trunk/phase3/tests/qunit/data/testrunner.js (added) (history)
  • /trunk/phase3/tests/qunit/data/testwarm.inject.js (added) (history)
  • /trunk/phase3/tests/qunit/index.html (modified) (history)
  • /trunk/phase3/tests/qunit/jquery.qunit.completenessTest.config.js (deleted) (history)
  • /trunk/phase3/tests/qunit/sample (deleted) (history)
  • /trunk/phase3/tests/qunit/suites/resources/jquery/jquery.autoEllipsis.js (modified) (history)
  • /trunk/phase3/tests/qunit/suites/resources/mediawiki/mediawiki.js (modified) (history)
  • /trunk/phase3/tests/qunit/testswarm.inject.js (deleted) (history)

Diff [purge]

Index: trunk/phase3/tests/qunit/testswarm.inject.js
@@ -1,349 +0,0 @@
2 -/*
3 - Copyright (c) 2009 John Resig
4 -
5 - Permission is hereby granted, free of charge, to any person
6 - obtaining a copy of this software and associated documentation
7 - files (the "Software"), to deal in the Software without
8 - restriction, including without limitation the rights to use,
9 - copy, modify, merge, publish, distribute, sublicense, and/or sell
10 - copies of the Software, and to permit persons to whom the
11 - Software is furnished to do so, subject to the following
12 - conditions:
13 -
14 - The above copyright notice and this permission notice shall be
15 - included in all copies or substantial portions of the Software.
16 -
17 - THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
18 - EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
19 - OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
20 - NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
21 - HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
22 - WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
23 - FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
24 - OTHER DEALINGS IN THE SOFTWARE.
25 -
26 -*/
27 -(function(){
28 -
29 - var DEBUG = false;
30 -
31 - var doPost = false;
32 -
33 - try {
34 - doPost = !!window.top.postMessage;
35 - } catch(e){}
36 -
37 - var search = window.location.search,
38 - url, index;
39 - if( ( index = search.indexOf( "swarmURL=" ) ) != -1 )
40 - url = decodeURIComponent( search.slice( index + 9 ) );
41 -
42 - if ( !DEBUG && (!url || url.indexOf("http") !== 0) ) {
43 - return;
44 - }
45 -
46 - var submitTimeout = 5;
47 -
48 - var curHeartbeat;
49 - var beatRate = 20;
50 -
51 - // Expose the TestSwarm API
52 - window.TestSwarm = {
53 - submit: submit,
54 - heartbeat: function(){
55 - if ( curHeartbeat ) {
56 - clearTimeout( curHeartbeat );
57 - }
58 -
59 - curHeartbeat = setTimeout(function(){
60 - submit({ fail: -1, total: -1 });
61 - }, beatRate * 1000);
62 - },
63 - serialize: function(){
64 - return trimSerialize();
65 - }
66 - };
67 -
68 - // Prevent careless things from executing
69 - window.print = window.confirm = window.alert = window.open = function(){};
70 -
71 - window.onerror = function(e){
72 - document.body.appendChild( document.createTextNode( "ERROR: " + e ));
73 - submit({ fail: 0, error: 1, total: 1 });
74 - return false;
75 - };
76 -
77 - // QUnit (jQuery)
78 - // http://docs.jquery.com/QUnit
79 - if ( typeof QUnit !== "undefined" ) {
80 - QUnit.done = function(results){
81 - submit({
82 - fail: results.failed,
83 - error: 0,
84 - total: results.total
85 - });
86 - };
87 -
88 - QUnit.log = window.TestSwarm.heartbeat;
89 - window.TestSwarm.heartbeat();
90 -
91 - window.TestSwarm.serialize = function(){
92 - // Clean up the HTML (remove any un-needed test markup)
93 - remove("nothiddendiv");
94 - remove("loadediframe");
95 - remove("dl");
96 - remove("main");
97 -
98 - // Show any collapsed results
99 - var ol = document.getElementsByTagName("ol");
100 - for ( var i = 0; i < ol.length; i++ ) {
101 - ol[i].style.display = "block";
102 - }
103 -
104 - return trimSerialize();
105 - };
106 -
107 - // UnitTestJS (Prototype, Scriptaculous)
108 - // http://github.com/tobie/unittest_js/tree/master
109 - } else if ( typeof Test !== "undefined" && Test && Test.Unit && Test.Unit.runners ) {
110 - var total_runners = Test.Unit.runners.length, cur_runners = 0;
111 - var total = 0, fail = 0, error = 0;
112 -
113 - for (var i = 0; i < Test.Unit.runners.length; i++) (function(i){
114 - var finish = Test.Unit.runners[i].finish;
115 - Test.Unit.runners[i].finish = function(){
116 - finish.call( this );
117 -
118 - var results = this.getResult();
119 - total += results.assertions;
120 - fail += results.failures;
121 - error += results.errors;
122 -
123 - if ( ++cur_runners === total_runners ) {
124 - submit({
125 - fail: fail,
126 - error: error,
127 - total: total
128 - });
129 - }
130 - };
131 - })(i);
132 -
133 - // JSSpec (MooTools)
134 - // http://jania.pe.kr/aw/moin.cgi/JSSpec
135 - } else if ( typeof JSSpec !== "undefined" && JSSpec && JSSpec.Logger ) {
136 - var onRunnerEnd = JSSpec.Logger.prototype.onRunnerEnd;
137 - JSSpec.Logger.prototype.onRunnerEnd = function(){
138 - onRunnerEnd.call(this);
139 -
140 - // Show any collapsed results
141 - var ul = document.getElementsByTagName("ul");
142 - for ( var i = 0; i < ul.length; i++ ) {
143 - ul[i].style.display = "block";
144 - }
145 -
146 - submit({
147 - fail: JSSpec.runner.getTotalFailures(),
148 - error: JSSpec.runner.getTotalErrors(),
149 - total: JSSpec.runner.totalExamples
150 - });
151 - };
152 -
153 - window.TestSwarm.serialize = function(){
154 - // Show any collapsed results
155 - var ul = document.getElementsByTagName("ul");
156 - for ( var i = 0; i < ul.length; i++ ) {
157 - ul[i].style.display = "block";
158 - }
159 -
160 - return trimSerialize();
161 - };
162 -
163 - // JSUnit
164 - // http://www.jsunit.net/
165 - // Note: Injection file must be included before the frames
166 - // are document.write()d into the page.
167 - } else if ( typeof JsUnitTestManager !== "undefined" ) {
168 - var _done = JsUnitTestManager.prototype._done;
169 - JsUnitTestManager.prototype._done = function(){
170 - _done.call(this);
171 -
172 - submit({
173 - fail: this.failureCount,
174 - error: this.errorCount,
175 - total: this.totalCount
176 - });
177 - };
178 -
179 - window.TestSwarm.serialize = function(){
180 - return "<pre>" + this.log.join("\n") + "</pre>";
181 - };
182 -
183 - // Selenium Core
184 - // http://seleniumhq.org/projects/core/
185 - } else if ( typeof SeleniumTestResult !== "undefined" && typeof LOG !== "undefined" ) {
186 - // Completely overwrite the postback
187 - SeleniumTestResult.prototype.post = function(){
188 - submit({
189 - fail: this.metrics.numCommandFailures,
190 - error: this.metrics.numCommandErrors,
191 - total: this.metrics.numCommandPasses + this.metrics.numCommandFailures + this.metrics.numCommandErrors
192 - });
193 - };
194 -
195 - window.TestSwarm.serialize = function(){
196 - var results = [];
197 - while ( LOG.pendingMessages.length ) {
198 - var msg = LOG.pendingMessages.shift();
199 - results.push( msg.type + ": " + msg.msg );
200 - }
201 -
202 - return "<pre>" + results.join("\n") + "</pre>";
203 - };
204 -
205 - // Dojo Objective Harness
206 - // http://docs.dojocampus.org/quickstart/doh
207 - } else if ( typeof doh !== "undefined" && doh._report ) {
208 - var _report = doh._report;
209 - doh._report = function(){
210 - _report.apply(this, arguments);
211 -
212 - submit({
213 - fail: doh._failureCount,
214 - error: doh._errorCount,
215 - total: doh._testCount
216 - });
217 - };
218 -
219 - window.TestSwarm.serialize = function(){
220 - return "<pre>" + document.getElementById("logBody").innerHTML + "</pre>";
221 - };
222 - // Screw.Unit
223 - // git://github.com/nathansobo/screw-unit.git
224 - } else if ( typeof Screw !== "undefined" && typeof jQuery !== 'undefined' && Screw && Screw.Unit ) {
225 - $(Screw).bind("after", function() {
226 - var passed = $('.passed').length;
227 - var failed = $('.failed').length;
228 - submit({
229 - fail: failed,
230 - error: 0,
231 - total: failed + passed
232 - });
233 - });
234 -
235 - $(Screw).bind("loaded", function() {
236 - $('.it')
237 - .bind("passed", window.TestSwarm.heartbeat)
238 - .bind("failed", window.TestSwarm.heartbeat);
239 - window.TestSwarm.heartbeat();
240 - });
241 -
242 - window.TestSwarm.serialize = function(){
243 - return trimSerialize();
244 - };
245 - }
246 -
247 - function trimSerialize(doc) {
248 - doc = doc || document;
249 -
250 - var scripts = doc.getElementsByTagName("script");
251 - while ( scripts.length ) {
252 - remove( scripts[0] );
253 - }
254 -
255 - var root = window.location.href.replace(/(https?:\/\/.*?)\/.*/, "$1");
256 - var cur = window.location.href.replace(/[^\/]*$/, "");
257 -
258 - var links = doc.getElementsByTagName("link");
259 - for ( var i = 0; i < links.length; i++ ) {
260 - var href = links[i].href;
261 - if ( href.indexOf("/") === 0 ) {
262 - href = root + href;
263 - } else if ( !/^https?:\/\//.test( href ) ) {
264 - href = cur + href;
265 - }
266 - links[i].href = href;
267 - }
268 -
269 - return ("<html>" + doc.documentElement.innerHTML + "</html>")
270 - .replace(/\s+/g, " ");
271 - }
272 -
273 - function remove(elem){
274 - if ( typeof elem === "string" ) {
275 - elem = document.getElementById( elem );
276 - }
277 -
278 - if ( elem ) {
279 - elem.parentNode.removeChild( elem );
280 - }
281 - }
282 -
283 - function submit(params){
284 - if ( curHeartbeat ) {
285 - clearTimeout( curHeartbeat );
286 - }
287 -
288 - var paramItems = (url.split("?")[1] || "").split("&");
289 -
290 - for ( var i = 0; i < paramItems.length; i++ ) {
291 - if ( paramItems[i] ) {
292 - var parts = paramItems[i].split("=");
293 - if ( !params[ parts[0] ] ) {
294 - params[ parts[0] ] = parts[1];
295 - }
296 - }
297 - }
298 -
299 - if ( !params.state ) {
300 - params.state = "saverun";
301 - }
302 -
303 - if ( !params.results ) {
304 - params.results = window.TestSwarm.serialize();
305 - }
306 -
307 - if ( doPost ) {
308 - // Build Query String
309 - var query = "";
310 -
311 - for ( var i in params ) {
312 - query += ( query ? "&" : "" ) + i + "=" +
313 - encodeURIComponent(params[i]);
314 - }
315 -
316 - if ( DEBUG ) {
317 - alert( query );
318 - } else {
319 - window.top.postMessage( query, "*" );
320 - }
321 -
322 - } else {
323 - var form = document.createElement("form");
324 - form.action = url;
325 - form.method = "POST";
326 -
327 - for ( var i in params ) {
328 - var input = document.createElement("input");
329 - input.type = "hidden";
330 - input.name = i;
331 - input.value = params[i];
332 - form.appendChild( input );
333 - }
334 -
335 - if ( DEBUG ) {
336 - alert( form.innerHTML );
337 - } else {
338 -
339 - // Watch for the result submission timing out
340 - setTimeout(function(){
341 - submit( params );
342 - }, submitTimeout * 1000);
343 -
344 - document.body.appendChild( form );
345 - form.submit();
346 - }
347 - }
348 - }
349 -
350 -})();
Index: trunk/phase3/tests/qunit/jquery.qunit.completenessTest.config.js
@@ -1,25 +0,0 @@
2 -// Return true to ignore
3 -var mwTestIgnore = function( val, tester, funcPath ) {
4 -
5 - // Don't record methods of the properties of constructors,
6 - // to avoid getting into a loop (prototype.constructor.prototype..).
7 - // Since we're therefor skipping any injection for
8 - // "new mw.Foo()", manually set it to true here.
9 - if ( val instanceof mw.Map ) {
10 - tester.methodCallTracker['Map'] = true;
11 - return true;
12 - }
13 - if ( val instanceof mw.Title ) {
14 - tester.methodCallTracker['Title'] = true;
15 - return true;
16 - }
17 -
18 - // Don't record methods of the properties of a jQuery object
19 - if ( val instanceof $ ) {
20 - return true;
21 - }
22 -
23 - return false;
24 -};
25 -
26 -var mwTester = new CompletenessTest( mw, mwTestIgnore );
Index: trunk/phase3/tests/qunit/data/defineTestCallback.js
@@ -0,0 +1,4 @@
 2+window.mw.loader.testCallback = function() {
 3+ start();
 4+ ok( true, 'Implementing a module, is the callback timed properly ?');
 5+};
Property changes on: trunk/phase3/tests/qunit/data/defineTestCallback.js
___________________________________________________________________
Added: svn:eol-style
16 + native
Index: trunk/phase3/tests/qunit/data/testrunner.js
@@ -0,0 +1,96 @@
 2+( function( $ ) {
 3+
 4+/**
 5+ * Add bogus to url to prevent IE crazy caching
 6+ *
 7+ * @param value {String} a relative path (eg. 'data/defineTestCallback.js' or 'data/test.php?foo=bar')
 8+ * @return {String} Such as 'data/defineTestCallback.js?131031765087663960'
 9+ */
 10+QUnit.fixurl = function(value) {
 11+ return value + (/\?/.test(value) ? "&" : "?") + new Date().getTime() + "" + parseInt(Math.random()*100000);
 12+};
 13+
 14+/**
 15+ * Load TestSwarm agent
 16+ */
 17+if ( QUnit.urlParams.swarmURL ) {
 18+ document.write("<scr" + "ipt src='" + QUnit.fixurl( 'data/testwarm.inject.js' ) + "'></scr" + "ipt>");
 19+}
 20+
 21+/**
 22+ * Load completenesstest
 23+ */
 24+if ( QUnit.urlParams.completenesstest ) {
 25+
 26+ // Return true to ignore
 27+ var mwTestIgnore = function( val, tester, funcPath ) {
 28+
 29+ // Don't record methods of the properties of constructors,
 30+ // to avoid getting into a loop (prototype.constructor.prototype..).
 31+ // Since we're therefor skipping any injection for
 32+ // "new mw.Foo()", manually set it to true here.
 33+ if ( val instanceof mw.Map ) {
 34+ tester.methodCallTracker['Map'] = true;
 35+ return true;
 36+ }
 37+ if ( val instanceof mw.Title ) {
 38+ tester.methodCallTracker['Title'] = true;
 39+ return true;
 40+ }
 41+
 42+ // Don't record methods of the properties of a jQuery object
 43+ if ( val instanceof $ ) {
 44+ return true;
 45+ }
 46+
 47+ return false;
 48+ };
 49+
 50+ var mwTester = new CompletenessTest( mw, mwTestIgnore );
 51+}
 52+
 53+/**
 54+ * Add-on assertion helpers
 55+ */
 56+// Define the add-ons
 57+var addons = {
 58+
 59+ // Expect boolean true
 60+ assertTrue: function( actual, message ) {
 61+ strictEqual( actual, true, message );
 62+ },
 63+
 64+ // Expect boolean false
 65+ assertFalse: function( actual, message ) {
 66+ strictEqual( actual, false, message );
 67+ },
 68+
 69+ // Expect numerical value less than X
 70+ lt: function( actual, expected, message ) {
 71+ QUnit.push( actual < expected, actual, 'less than ' + expected, message );
 72+ },
 73+
 74+ // Expect numerical value less than or equal to X
 75+ ltOrEq: function( actual, expected, message ) {
 76+ QUnit.push( actual <= expected, actual, 'less than or equal to ' + expected, message );
 77+ },
 78+
 79+ // Expect numerical value greater than X
 80+ gt: function( actual, expected, message ) {
 81+ QUnit.push( actual > expected, actual, 'greater than ' + expected, message );
 82+ },
 83+
 84+ // Expect numerical value greater than or equal to X
 85+ gtOrEq: function( actual, expected, message ) {
 86+ QUnit.push( actual >= expected, actual, 'greater than or equal to ' + expected, message );
 87+ },
 88+
 89+ // Backwards compatible with new verions of QUnit
 90+ equals: window.equal,
 91+ same: window.deepEqual
 92+};
 93+
 94+$.extend( QUnit, addons );
 95+$.extend( window, addons );
 96+
 97+})( jQuery );
Property changes on: trunk/phase3/tests/qunit/data/testrunner.js
___________________________________________________________________
Added: svn:eol-style
198 + native
Index: trunk/phase3/tests/qunit/data/testwarm.inject.js
@@ -0,0 +1,349 @@
 2+/*
 3+ Copyright (c) 2009 John Resig
 4+
 5+ Permission is hereby granted, free of charge, to any person
 6+ obtaining a copy of this software and associated documentation
 7+ files (the "Software"), to deal in the Software without
 8+ restriction, including without limitation the rights to use,
 9+ copy, modify, merge, publish, distribute, sublicense, and/or sell
 10+ copies of the Software, and to permit persons to whom the
 11+ Software is furnished to do so, subject to the following
 12+ conditions:
 13+
 14+ The above copyright notice and this permission notice shall be
 15+ included in all copies or substantial portions of the Software.
 16+
 17+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 18+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
 19+ OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 20+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 21+ HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
 22+ WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 23+ FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 24+ OTHER DEALINGS IN THE SOFTWARE.
 25+
 26+*/
 27+(function(){
 28+
 29+ var DEBUG = false;
 30+
 31+ var doPost = false;
 32+
 33+ try {
 34+ doPost = !!window.top.postMessage;
 35+ } catch(e){}
 36+
 37+ var search = window.location.search,
 38+ url, index;
 39+ if( ( index = search.indexOf( "swarmURL=" ) ) != -1 )
 40+ url = decodeURIComponent( search.slice( index + 9 ) );
 41+
 42+ if ( !DEBUG && (!url || url.indexOf("http") !== 0) ) {
 43+ return;
 44+ }
 45+
 46+ var submitTimeout = 5;
 47+
 48+ var curHeartbeat;
 49+ var beatRate = 20;
 50+
 51+ // Expose the TestSwarm API
 52+ window.TestSwarm = {
 53+ submit: submit,
 54+ heartbeat: function(){
 55+ if ( curHeartbeat ) {
 56+ clearTimeout( curHeartbeat );
 57+ }
 58+
 59+ curHeartbeat = setTimeout(function(){
 60+ submit({ fail: -1, total: -1 });
 61+ }, beatRate * 1000);
 62+ },
 63+ serialize: function(){
 64+ return trimSerialize();
 65+ }
 66+ };
 67+
 68+ // Prevent careless things from executing
 69+ window.print = window.confirm = window.alert = window.open = function(){};
 70+
 71+ window.onerror = function(e){
 72+ document.body.appendChild( document.createTextNode( "ERROR: " + e ));
 73+ submit({ fail: 0, error: 1, total: 1 });
 74+ return false;
 75+ };
 76+
 77+ // QUnit (jQuery)
 78+ // http://docs.jquery.com/QUnit
 79+ if ( typeof QUnit !== "undefined" ) {
 80+ QUnit.done = function(results){
 81+ submit({
 82+ fail: results.failed,
 83+ error: 0,
 84+ total: results.total
 85+ });
 86+ };
 87+
 88+ QUnit.log = window.TestSwarm.heartbeat;
 89+ window.TestSwarm.heartbeat();
 90+
 91+ window.TestSwarm.serialize = function(){
 92+ // Clean up the HTML (remove any un-needed test markup)
 93+ remove("nothiddendiv");
 94+ remove("loadediframe");
 95+ remove("dl");
 96+ remove("main");
 97+
 98+ // Show any collapsed results
 99+ var ol = document.getElementsByTagName("ol");
 100+ for ( var i = 0; i < ol.length; i++ ) {
 101+ ol[i].style.display = "block";
 102+ }
 103+
 104+ return trimSerialize();
 105+ };
 106+
 107+ // UnitTestJS (Prototype, Scriptaculous)
 108+ // http://github.com/tobie/unittest_js/tree/master
 109+ } else if ( typeof Test !== "undefined" && Test && Test.Unit && Test.Unit.runners ) {
 110+ var total_runners = Test.Unit.runners.length, cur_runners = 0;
 111+ var total = 0, fail = 0, error = 0;
 112+
 113+ for (var i = 0; i < Test.Unit.runners.length; i++) (function(i){
 114+ var finish = Test.Unit.runners[i].finish;
 115+ Test.Unit.runners[i].finish = function(){
 116+ finish.call( this );
 117+
 118+ var results = this.getResult();
 119+ total += results.assertions;
 120+ fail += results.failures;
 121+ error += results.errors;
 122+
 123+ if ( ++cur_runners === total_runners ) {
 124+ submit({
 125+ fail: fail,
 126+ error: error,
 127+ total: total
 128+ });
 129+ }
 130+ };
 131+ })(i);
 132+
 133+ // JSSpec (MooTools)
 134+ // http://jania.pe.kr/aw/moin.cgi/JSSpec
 135+ } else if ( typeof JSSpec !== "undefined" && JSSpec && JSSpec.Logger ) {
 136+ var onRunnerEnd = JSSpec.Logger.prototype.onRunnerEnd;
 137+ JSSpec.Logger.prototype.onRunnerEnd = function(){
 138+ onRunnerEnd.call(this);
 139+
 140+ // Show any collapsed results
 141+ var ul = document.getElementsByTagName("ul");
 142+ for ( var i = 0; i < ul.length; i++ ) {
 143+ ul[i].style.display = "block";
 144+ }
 145+
 146+ submit({
 147+ fail: JSSpec.runner.getTotalFailures(),
 148+ error: JSSpec.runner.getTotalErrors(),
 149+ total: JSSpec.runner.totalExamples
 150+ });
 151+ };
 152+
 153+ window.TestSwarm.serialize = function(){
 154+ // Show any collapsed results
 155+ var ul = document.getElementsByTagName("ul");
 156+ for ( var i = 0; i < ul.length; i++ ) {
 157+ ul[i].style.display = "block";
 158+ }
 159+
 160+ return trimSerialize();
 161+ };
 162+
 163+ // JSUnit
 164+ // http://www.jsunit.net/
 165+ // Note: Injection file must be included before the frames
 166+ // are document.write()d into the page.
 167+ } else if ( typeof JsUnitTestManager !== "undefined" ) {
 168+ var _done = JsUnitTestManager.prototype._done;
 169+ JsUnitTestManager.prototype._done = function(){
 170+ _done.call(this);
 171+
 172+ submit({
 173+ fail: this.failureCount,
 174+ error: this.errorCount,
 175+ total: this.totalCount
 176+ });
 177+ };
 178+
 179+ window.TestSwarm.serialize = function(){
 180+ return "<pre>" + this.log.join("\n") + "</pre>";
 181+ };
 182+
 183+ // Selenium Core
 184+ // http://seleniumhq.org/projects/core/
 185+ } else if ( typeof SeleniumTestResult !== "undefined" && typeof LOG !== "undefined" ) {
 186+ // Completely overwrite the postback
 187+ SeleniumTestResult.prototype.post = function(){
 188+ submit({
 189+ fail: this.metrics.numCommandFailures,
 190+ error: this.metrics.numCommandErrors,
 191+ total: this.metrics.numCommandPasses + this.metrics.numCommandFailures + this.metrics.numCommandErrors
 192+ });
 193+ };
 194+
 195+ window.TestSwarm.serialize = function(){
 196+ var results = [];
 197+ while ( LOG.pendingMessages.length ) {
 198+ var msg = LOG.pendingMessages.shift();
 199+ results.push( msg.type + ": " + msg.msg );
 200+ }
 201+
 202+ return "<pre>" + results.join("\n") + "</pre>";
 203+ };
 204+
 205+ // Dojo Objective Harness
 206+ // http://docs.dojocampus.org/quickstart/doh
 207+ } else if ( typeof doh !== "undefined" && doh._report ) {
 208+ var _report = doh._report;
 209+ doh._report = function(){
 210+ _report.apply(this, arguments);
 211+
 212+ submit({
 213+ fail: doh._failureCount,
 214+ error: doh._errorCount,
 215+ total: doh._testCount
 216+ });
 217+ };
 218+
 219+ window.TestSwarm.serialize = function(){
 220+ return "<pre>" + document.getElementById("logBody").innerHTML + "</pre>";
 221+ };
 222+ // Screw.Unit
 223+ // git://github.com/nathansobo/screw-unit.git
 224+ } else if ( typeof Screw !== "undefined" && typeof jQuery !== 'undefined' && Screw && Screw.Unit ) {
 225+ $(Screw).bind("after", function() {
 226+ var passed = $('.passed').length;
 227+ var failed = $('.failed').length;
 228+ submit({
 229+ fail: failed,
 230+ error: 0,
 231+ total: failed + passed
 232+ });
 233+ });
 234+
 235+ $(Screw).bind("loaded", function() {
 236+ $('.it')
 237+ .bind("passed", window.TestSwarm.heartbeat)
 238+ .bind("failed", window.TestSwarm.heartbeat);
 239+ window.TestSwarm.heartbeat();
 240+ });
 241+
 242+ window.TestSwarm.serialize = function(){
 243+ return trimSerialize();
 244+ };
 245+ }
 246+
 247+ function trimSerialize(doc) {
 248+ doc = doc || document;
 249+
 250+ var scripts = doc.getElementsByTagName("script");
 251+ while ( scripts.length ) {
 252+ remove( scripts[0] );
 253+ }
 254+
 255+ var root = window.location.href.replace(/(https?:\/\/.*?)\/.*/, "$1");
 256+ var cur = window.location.href.replace(/[^\/]*$/, "");
 257+
 258+ var links = doc.getElementsByTagName("link");
 259+ for ( var i = 0; i < links.length; i++ ) {
 260+ var href = links[i].href;
 261+ if ( href.indexOf("/") === 0 ) {
 262+ href = root + href;
 263+ } else if ( !/^https?:\/\//.test( href ) ) {
 264+ href = cur + href;
 265+ }
 266+ links[i].href = href;
 267+ }
 268+
 269+ return ("<html>" + doc.documentElement.innerHTML + "</html>")
 270+ .replace(/\s+/g, " ");
 271+ }
 272+
 273+ function remove(elem){
 274+ if ( typeof elem === "string" ) {
 275+ elem = document.getElementById( elem );
 276+ }
 277+
 278+ if ( elem ) {
 279+ elem.parentNode.removeChild( elem );
 280+ }
 281+ }
 282+
 283+ function submit(params){
 284+ if ( curHeartbeat ) {
 285+ clearTimeout( curHeartbeat );
 286+ }
 287+
 288+ var paramItems = (url.split("?")[1] || "").split("&");
 289+
 290+ for ( var i = 0; i < paramItems.length; i++ ) {
 291+ if ( paramItems[i] ) {
 292+ var parts = paramItems[i].split("=");
 293+ if ( !params[ parts[0] ] ) {
 294+ params[ parts[0] ] = parts[1];
 295+ }
 296+ }
 297+ }
 298+
 299+ if ( !params.state ) {
 300+ params.state = "saverun";
 301+ }
 302+
 303+ if ( !params.results ) {
 304+ params.results = window.TestSwarm.serialize();
 305+ }
 306+
 307+ if ( doPost ) {
 308+ // Build Query String
 309+ var query = "";
 310+
 311+ for ( var i in params ) {
 312+ query += ( query ? "&" : "" ) + i + "=" +
 313+ encodeURIComponent(params[i]);
 314+ }
 315+
 316+ if ( DEBUG ) {
 317+ alert( query );
 318+ } else {
 319+ window.top.postMessage( query, "*" );
 320+ }
 321+
 322+ } else {
 323+ var form = document.createElement("form");
 324+ form.action = url;
 325+ form.method = "POST";
 326+
 327+ for ( var i in params ) {
 328+ var input = document.createElement("input");
 329+ input.type = "hidden";
 330+ input.name = i;
 331+ input.value = params[i];
 332+ form.appendChild( input );
 333+ }
 334+
 335+ if ( DEBUG ) {
 336+ alert( form.innerHTML );
 337+ } else {
 338+
 339+ // Watch for the result submission timing out
 340+ setTimeout(function(){
 341+ submit( params );
 342+ }, submitTimeout * 1000);
 343+
 344+ document.body.appendChild( form );
 345+ form.submit();
 346+ }
 347+ }
 348+ }
 349+
 350+})();
Property changes on: trunk/phase3/tests/qunit/data/testwarm.inject.js
___________________________________________________________________
Added: svn:eol-style
1351 + native
Index: trunk/phase3/tests/qunit/index.html
@@ -51,6 +51,8 @@
5252 <!-- QUnit: Load framework -->
5353 <link rel="stylesheet" href="../../resources/jquery/jquery.qunit.css" />
5454 <script src="../../resources/jquery/jquery.qunit.js"></script>
 55+ <script src="../../resources/jquery/jquery.qunit.completenessTest.js"></script>
 56+ <script src="data/testrunner.js"></script>
5557
5658 <!-- QUnit: Load test suites (maintain the same order as above please) -->
5759 <script src="suites/resources/mediawiki/mediawiki.js"></script>
@@ -67,19 +69,6 @@
6870 <script src="suites/resources/jquery/jquery.tablesorter.test.js" charset="UTF-8"></script>
6971 <script src="suites/resources/mediawiki/mediawiki.Title.js"></script>
7072 <script src="suites/resources/mediawiki.special/mediawiki.special.recentchanges.js"></script>
71 -
72 - <!-- TestSwarm: If a test swarm is running this,
73 - the following script will allow it to extract the results.
74 - Harmless otherwise. -->
75 - <script src="testswarm.inject.js"></script>
76 -
77 - <!-- CompletenessTest -->
78 - <script>
79 - if ( QUnit.urlParams.completenesstest ) {
80 - document.write( '\x3Cscript src="../../resources/jquery/jquery.qunit.completenessTest.js">\x3C/script>' );
81 - document.write( '\x3Cscript src="jquery.qunit.completenessTest.config.js">\x3C/script>' );
82 - }
83 - </script>
8473 </head>
8574 <body>
8675 <h1 id="qunit-header">MediaWiki JavaScript Test Suite</h1>
Index: trunk/phase3/tests/qunit/suites/resources/jquery/jquery.autoEllipsis.js
@@ -23,27 +23,6 @@
2424 test( 'Position right', function() {
2525 expect(4);
2626
27 - /**
28 - * Extra QUnit assertions
29 - * Needed in order to include the expected and actual values in the output.
30 - * This way we end up with:
31 - * "Expected: > 100, Result: 99"
32 - * instead of:
33 - * "Expected: true, Result: false"
34 - */
35 - // Expect numerical value less than or equal to X
36 - var ltOrEq = function( actual, expected, message ) {
37 - QUnit.push( actual <= expected, actual, 'less than or equal to ' + expected, message );
38 - };
39 - // Expect numerical value greater than X
40 - var gt = function( actual, expected, message ) {
41 - QUnit.push( actual > expected, actual, 'greater than ' + expected, message );
42 - };
43 - // Expect numerical value greater than or equal to X
44 - var gtOrEq = function( actual, expected, message ) {
45 - QUnit.push( actual >= expected, actual, 'greater than or equal to ' + expected, message );
46 - };
47 -
4827 // We need this thing to be visible, so append it to the DOM
4928 var origText = 'This is a really long random string and there is no way it fits in 100 pixels.';
5029 var $wrapper = createWrappedDiv( origText, '100px' );
Index: trunk/phase3/tests/qunit/suites/resources/mediawiki/mediawiki.js
@@ -159,7 +159,7 @@
160160 // Extract path
161161 var tests_path = rePath.exec( location.href );
162162
163 - mw.loader.implement( 'is.awesome', [tests_path + 'sample/awesome.js'], {}, {} );
 163+ mw.loader.implement( 'is.awesome', [QUnit.fixurl( tests_path + 'data/defineTestCallback.js')], {}, {} );
164164
165165 mw.loader.using( 'is.awesome', function() {
166166
Index: trunk/phase3/resources/jquery/jquery.qunit.completenessTest.js
@@ -67,7 +67,9 @@
6868 html += '<br />' + mw.html.escape(key);
6969 });
7070 html += '<br /><br /><em>&mdash; CompletenessTest</em>';
71 - return $( '<div>' ).css( style ).append( html );
 71+ var $oldResult = $( '#qunit-completenesstest' ),
 72+ $result = $oldResult.length ? $oldResult : $( '<div id="qunit-completenesstest"></div>' );
 73+ return $result.css( style ).html( html );
7274 };
7375
7476 if ( $.isEmptyObject( that.missingTests ) ) {

Status & tagging log