OLD | NEW |
| (Empty) |
1 <script> | |
2 | |
3 // FIXME: This really could be trimmed down from all the generic and commonjs cr
ap. | |
4 | |
5 ;(function(){ | |
6 | |
7 // CommonJS require() | |
8 | |
9 function require(p){ | |
10 var path = require.resolve(p) | |
11 , mod = require.modules[path]; | |
12 if (!mod) throw new Error('failed to require "' + p + '"'); | |
13 if (!mod.exports) { | |
14 mod.exports = {}; | |
15 mod.call(mod.exports, mod, mod.exports, require.relative(path)); | |
16 } | |
17 return mod.exports; | |
18 } | |
19 | |
20 require.modules = {}; | |
21 | |
22 require.resolve = function (path){ | |
23 var orig = path | |
24 , reg = path + '.js' | |
25 , index = path + '/index.js'; | |
26 return require.modules[reg] && reg | |
27 || require.modules[index] && index | |
28 || orig; | |
29 }; | |
30 | |
31 require.register = function (path, fn){ | |
32 require.modules[path] = fn; | |
33 }; | |
34 | |
35 require.relative = function (parent) { | |
36 return function(p){ | |
37 if ('.' != p.charAt(0)) return require(p); | |
38 | |
39 var path = parent.split('/') | |
40 , segs = p.split('/'); | |
41 path.pop(); | |
42 | |
43 for (var i = 0; i < segs.length; i++) { | |
44 var seg = segs[i]; | |
45 if ('..' == seg) path.pop(); | |
46 else if ('.' != seg) path.push(seg); | |
47 } | |
48 | |
49 return require(path.join('/')); | |
50 }; | |
51 }; | |
52 | |
53 | |
54 require.register("browser/debug.js", function(module, exports, require){ | |
55 | |
56 module.exports = function(type){ | |
57 return function(){ | |
58 } | |
59 }; | |
60 | |
61 }); // module: browser/debug.js | |
62 | |
63 require.register("browser/events.js", function(module, exports, require){ | |
64 | |
65 /** | |
66 * Module exports. | |
67 */ | |
68 | |
69 exports.EventEmitter = EventEmitter; | |
70 | |
71 /** | |
72 * Check if `obj` is an array. | |
73 */ | |
74 | |
75 function isArray(obj) { | |
76 return '[object Array]' == {}.toString.call(obj); | |
77 } | |
78 | |
79 /** | |
80 * Event emitter constructor. | |
81 * | |
82 * @api public | |
83 */ | |
84 | |
85 function EventEmitter(){}; | |
86 | |
87 /** | |
88 * Adds a listener. | |
89 * | |
90 * @api public | |
91 */ | |
92 | |
93 EventEmitter.prototype.on = function (name, fn) { | |
94 if (!this.$events) { | |
95 this.$events = {}; | |
96 } | |
97 | |
98 if (!this.$events[name]) { | |
99 this.$events[name] = fn; | |
100 } else if (isArray(this.$events[name])) { | |
101 this.$events[name].push(fn); | |
102 } else { | |
103 this.$events[name] = [this.$events[name], fn]; | |
104 } | |
105 | |
106 return this; | |
107 }; | |
108 | |
109 EventEmitter.prototype.addListener = EventEmitter.prototype.on; | |
110 | |
111 /** | |
112 * Adds a volatile listener. | |
113 * | |
114 * @api public | |
115 */ | |
116 | |
117 EventEmitter.prototype.once = function (name, fn) { | |
118 var self = this; | |
119 | |
120 function on () { | |
121 self.removeListener(name, on); | |
122 fn.apply(this, arguments); | |
123 }; | |
124 | |
125 on.listener = fn; | |
126 this.on(name, on); | |
127 | |
128 return this; | |
129 }; | |
130 | |
131 /** | |
132 * Removes a listener. | |
133 * | |
134 * @api public | |
135 */ | |
136 | |
137 EventEmitter.prototype.removeListener = function (name, fn) { | |
138 if (this.$events && this.$events[name]) { | |
139 var list = this.$events[name]; | |
140 | |
141 if (isArray(list)) { | |
142 var pos = -1; | |
143 | |
144 for (var i = 0, l = list.length; i < l; i++) { | |
145 if (list[i] === fn || (list[i].listener && list[i].listener === fn)) { | |
146 pos = i; | |
147 break; | |
148 } | |
149 } | |
150 | |
151 if (pos < 0) { | |
152 return this; | |
153 } | |
154 | |
155 list.splice(pos, 1); | |
156 | |
157 if (!list.length) { | |
158 delete this.$events[name]; | |
159 } | |
160 } else if (list === fn || (list.listener && list.listener === fn)) { | |
161 delete this.$events[name]; | |
162 } | |
163 } | |
164 | |
165 return this; | |
166 }; | |
167 | |
168 /** | |
169 * Removes all listeners for an event. | |
170 * | |
171 * @api public | |
172 */ | |
173 | |
174 EventEmitter.prototype.removeAllListeners = function (name) { | |
175 if (name === undefined) { | |
176 this.$events = {}; | |
177 return this; | |
178 } | |
179 | |
180 if (this.$events && this.$events[name]) { | |
181 this.$events[name] = null; | |
182 } | |
183 | |
184 return this; | |
185 }; | |
186 | |
187 /** | |
188 * Gets all listeners for a certain event. | |
189 * | |
190 * @api public | |
191 */ | |
192 | |
193 EventEmitter.prototype.listeners = function (name) { | |
194 if (!this.$events) { | |
195 this.$events = {}; | |
196 } | |
197 | |
198 if (!this.$events[name]) { | |
199 this.$events[name] = []; | |
200 } | |
201 | |
202 if (!isArray(this.$events[name])) { | |
203 this.$events[name] = [this.$events[name]]; | |
204 } | |
205 | |
206 return this.$events[name]; | |
207 }; | |
208 | |
209 /** | |
210 * Emits an event. | |
211 * | |
212 * @api public | |
213 */ | |
214 | |
215 EventEmitter.prototype.emit = function (name) { | |
216 if (!this.$events) { | |
217 return false; | |
218 } | |
219 | |
220 var handler = this.$events[name]; | |
221 | |
222 if (!handler) { | |
223 return false; | |
224 } | |
225 | |
226 var args = [].slice.call(arguments, 1); | |
227 | |
228 if ('function' == typeof handler) { | |
229 handler.apply(this, args); | |
230 } else if (isArray(handler)) { | |
231 var listeners = handler.slice(); | |
232 | |
233 for (var i = 0, l = listeners.length; i < l; i++) { | |
234 listeners[i].apply(this, args); | |
235 } | |
236 } else { | |
237 return false; | |
238 } | |
239 | |
240 return true; | |
241 }; | |
242 }); // module: browser/events.js | |
243 | |
244 require.register("browser/path.js", function(module, exports, require){ | |
245 | |
246 }); // module: browser/path.js | |
247 | |
248 require.register("context.js", function(module, exports, require){ | |
249 | |
250 /** | |
251 * Expose `Context`. | |
252 */ | |
253 | |
254 module.exports = Context; | |
255 | |
256 /** | |
257 * Initialize a new `Context`. | |
258 * | |
259 * @api private | |
260 */ | |
261 | |
262 function Context(){} | |
263 | |
264 /** | |
265 * Set or get the context `Runnable` to `runnable`. | |
266 * | |
267 * @param {Runnable} runnable | |
268 * @return {Context} | |
269 * @api private | |
270 */ | |
271 | |
272 Context.prototype.runnable = function(runnable){ | |
273 if (0 == arguments.length) return this._runnable; | |
274 this.test = this._runnable = runnable; | |
275 return this; | |
276 }; | |
277 | |
278 /** | |
279 * Set test timeout `ms`. | |
280 * | |
281 * @param {Number} ms | |
282 * @return {Context} self | |
283 * @api private | |
284 */ | |
285 | |
286 Context.prototype.timeout = function(ms){ | |
287 if (arguments.length === 0) return this.runnable().timeout(); | |
288 this.runnable().timeout(ms); | |
289 return this; | |
290 }; | |
291 | |
292 /** | |
293 * Set test timeout `enabled`. | |
294 * | |
295 * @param {Boolean} enabled | |
296 * @return {Context} self | |
297 * @api private | |
298 */ | |
299 | |
300 Context.prototype.enableTimeouts = function (enabled) { | |
301 this.runnable().enableTimeouts(enabled); | |
302 return this; | |
303 }; | |
304 | |
305 | |
306 /** | |
307 * Set test slowness threshold `ms`. | |
308 * | |
309 * @param {Number} ms | |
310 * @return {Context} self | |
311 * @api private | |
312 */ | |
313 | |
314 Context.prototype.slow = function(ms){ | |
315 this.runnable().slow(ms); | |
316 return this; | |
317 }; | |
318 | |
319 /** | |
320 * Inspect the context void of `._runnable`. | |
321 * | |
322 * @return {String} | |
323 * @api private | |
324 */ | |
325 | |
326 Context.prototype.inspect = function(){ | |
327 return JSON.stringify(this, function(key, val){ | |
328 if ('_runnable' == key) return; | |
329 if ('test' == key) return; | |
330 return val; | |
331 }, 2); | |
332 }; | |
333 | |
334 }); // module: context.js | |
335 | |
336 require.register("hook.js", function(module, exports, require){ | |
337 | |
338 /** | |
339 * Module dependencies. | |
340 */ | |
341 | |
342 var Runnable = require('./runnable'); | |
343 | |
344 /** | |
345 * Expose `Hook`. | |
346 */ | |
347 | |
348 module.exports = Hook; | |
349 | |
350 /** | |
351 * Initialize a new `Hook` with the given `title` and callback `fn`. | |
352 * | |
353 * @param {String} title | |
354 * @param {Function} fn | |
355 * @api private | |
356 */ | |
357 | |
358 function Hook(title, fn) { | |
359 Runnable.call(this, title, fn); | |
360 this.type = 'hook'; | |
361 } | |
362 | |
363 /** | |
364 * Inherit from `Runnable.prototype`. | |
365 */ | |
366 | |
367 function F(){}; | |
368 F.prototype = Runnable.prototype; | |
369 Hook.prototype = new F; | |
370 Hook.prototype.constructor = Hook; | |
371 | |
372 | |
373 /** | |
374 * Get or set the test `err`. | |
375 * | |
376 * @param {Error} err | |
377 * @return {Error} | |
378 * @api public | |
379 */ | |
380 | |
381 Hook.prototype.error = function(err){ | |
382 if (0 == arguments.length) { | |
383 var err = this._error; | |
384 this._error = null; | |
385 return err; | |
386 } | |
387 | |
388 this._error = err; | |
389 }; | |
390 | |
391 }); // module: hook.js | |
392 | |
393 require.register("interfaces/bdd.js", function(module, exports, require){ | |
394 | |
395 /** | |
396 * Module dependencies. | |
397 */ | |
398 | |
399 var Suite = require('../suite') | |
400 , Test = require('../test') | |
401 , utils = require('../utils'); | |
402 | |
403 /** | |
404 * BDD-style interface: | |
405 * | |
406 * describe('Array', function(){ | |
407 * describe('#indexOf()', function(){ | |
408 * it('should return -1 when not present', function(){ | |
409 * | |
410 * }); | |
411 * | |
412 * it('should return the index when present', function(){ | |
413 * | |
414 * }); | |
415 * }); | |
416 * }); | |
417 * | |
418 */ | |
419 | |
420 module.exports = function(suite){ | |
421 var suites = [suite]; | |
422 | |
423 suite.on('pre-require', function(context, file, mocha){ | |
424 | |
425 /** | |
426 * Execute before running tests. | |
427 */ | |
428 | |
429 context.before = function(name, fn){ | |
430 suites[0].beforeAll(name, fn); | |
431 }; | |
432 | |
433 /** | |
434 * Execute after running tests. | |
435 */ | |
436 | |
437 context.after = function(name, fn){ | |
438 suites[0].afterAll(name, fn); | |
439 }; | |
440 | |
441 /** | |
442 * Execute before each test case. | |
443 */ | |
444 | |
445 context.beforeEach = function(name, fn){ | |
446 suites[0].beforeEach(name, fn); | |
447 }; | |
448 | |
449 /** | |
450 * Execute after each test case. | |
451 */ | |
452 | |
453 context.afterEach = function(name, fn){ | |
454 suites[0].afterEach(name, fn); | |
455 }; | |
456 | |
457 /** | |
458 * Describe a "suite" with the given `title` | |
459 * and callback `fn` containing nested suites | |
460 * and/or tests. | |
461 */ | |
462 | |
463 context.describe = context.context = function(title, fn){ | |
464 var suite = Suite.create(suites[0], title); | |
465 suite.file = file; | |
466 suites.unshift(suite); | |
467 fn.call(suite); | |
468 suites.shift(); | |
469 return suite; | |
470 }; | |
471 | |
472 /** | |
473 * Pending describe. | |
474 */ | |
475 | |
476 context.describe.skip = function(title, fn){ | |
477 var suite = Suite.create(suites[0], title); | |
478 suite.pending = true; | |
479 suites.unshift(suite); | |
480 fn.call(suite); | |
481 suites.shift(); | |
482 }; | |
483 | |
484 context.describe.only = function(title, fn){ | |
485 var suite = context.describe(title, fn); | |
486 mocha.grep(suite.fullTitle()); | |
487 return suite; | |
488 }; | |
489 | |
490 | |
491 /** | |
492 * Describe a specification or test-case | |
493 * with the given `title` and callback `fn` | |
494 * acting as a thunk. | |
495 */ | |
496 | |
497 context.it = function(title, fn){ | |
498 var suite = suites[0]; | |
499 if (suite.pending) var fn = null; | |
500 var test = new Test(title, fn); | |
501 test.file = file; | |
502 suite.addTest(test); | |
503 return test; | |
504 }; | |
505 | |
506 context.it.only = function(title, fn){ | |
507 var test = context.it(title, fn); | |
508 var reString = '^' + utils.escapeRegexp(test.fullTitle()) + '$'; | |
509 mocha.grep(new RegExp(reString)); | |
510 return test; | |
511 }; | |
512 | |
513 | |
514 /** | |
515 * Pending test case. | |
516 */ | |
517 | |
518 context.it.skip = function(title){ | |
519 context.it(title); | |
520 }; | |
521 }); | |
522 }; | |
523 | |
524 }); // module: interfaces/bdd.js | |
525 | |
526 require.register("interfaces/exports.js", function(module, exports, require){ | |
527 | |
528 /** | |
529 * Module dependencies. | |
530 SGMcan */ | |
531 | |
532 var Suite = require('../suite') | |
533 , Test = require('../test'); | |
534 | |
535 /** | |
536 * TDD-style interface: | |
537 * | |
538 * exports.Array = { | |
539 * '#indexOf()': { | |
540 * 'should return -1 when the value is not present': function(){ | |
541 * | |
542 * }, | |
543 * | |
544 * 'should return the correct index when the value is present': function
(){ | |
545 * | |
546 * } | |
547 * } | |
548 * }; | |
549 * | |
550 */ | |
551 | |
552 module.exports = function(suite){ | |
553 var suites = [suite]; | |
554 | |
555 suite.on('require', visit); | |
556 | |
557 function visit(obj, file) { | |
558 var suite; | |
559 for (var key in obj) { | |
560 if ('function' == typeof obj[key]) { | |
561 var fn = obj[key]; | |
562 switch (key) { | |
563 case 'before': | |
564 suites[0].beforeAll(fn); | |
565 break; | |
566 case 'after': | |
567 suites[0].afterAll(fn); | |
568 break; | |
569 case 'beforeEach': | |
570 suites[0].beforeEach(fn); | |
571 break; | |
572 case 'afterEach': | |
573 suites[0].afterEach(fn); | |
574 break; | |
575 default: | |
576 var test = new Test(key, fn); | |
577 test.file = file; | |
578 suites[0].addTest(test); | |
579 } | |
580 } else { | |
581 var suite = Suite.create(suites[0], key); | |
582 suites.unshift(suite); | |
583 visit(obj[key]); | |
584 suites.shift(); | |
585 } | |
586 } | |
587 } | |
588 }; | |
589 | |
590 }); // module: interfaces/exports.js | |
591 | |
592 require.register("interfaces/index.js", function(module, exports, require){ | |
593 | |
594 exports.bdd = require('./bdd'); | |
595 exports.exports = require('./exports'); | |
596 | |
597 }); // module: interfaces/index.js | |
598 | |
599 require.register("mocha.js", function(module, exports, require){ | |
600 /*! | |
601 * mocha | |
602 * Copyright(c) 2011 TJ Holowaychuk <tj@vision-media.ca> | |
603 * MIT Licensed | |
604 */ | |
605 | |
606 /** | |
607 * Module dependencies. | |
608 */ | |
609 | |
610 var path = require('browser/path') | |
611 , utils = require('./utils'); | |
612 | |
613 /** | |
614 * Expose `Mocha`. | |
615 */ | |
616 | |
617 exports = module.exports = Mocha; | |
618 | |
619 /** | |
620 * To require local UIs and reporters when running in node. | |
621 */ | |
622 | |
623 if (typeof process !== 'undefined' && typeof process.cwd === 'function') { | |
624 var join = path.join | |
625 , cwd = process.cwd(); | |
626 module.paths.push(cwd, join(cwd, 'node_modules')); | |
627 } | |
628 | |
629 /** | |
630 * Expose internals. | |
631 */ | |
632 | |
633 exports.utils = utils; | |
634 exports.interfaces = require('./interfaces'); | |
635 exports.reporters = require('./reporters'); | |
636 exports.Runnable = require('./runnable'); | |
637 exports.Context = require('./context'); | |
638 exports.Runner = require('./runner'); | |
639 exports.Suite = require('./suite'); | |
640 exports.Hook = require('./hook'); | |
641 exports.Test = require('./test'); | |
642 | |
643 /** | |
644 * Setup mocha with `options`. | |
645 * | |
646 * Options: | |
647 * | |
648 * - `ui` name "bdd", "tdd", "exports" etc | |
649 * - `reporter` reporter instance, defaults to `mocha.reporters.spec` | |
650 * - `timeout` timeout in milliseconds | |
651 * - `bail` bail on the first test failure | |
652 * - `slow` milliseconds to wait before considering a test slow | |
653 * | |
654 * @param {Object} options | |
655 * @api public | |
656 */ | |
657 | |
658 function Mocha(options) { | |
659 options = options || {}; | |
660 this.files = []; | |
661 this.options = options; | |
662 this.grep(options.grep); | |
663 this.suite = new exports.Suite('', new exports.Context); | |
664 this.ui(options.ui); | |
665 this.bail(options.bail); | |
666 this.reporter(); | |
667 if (null != options.timeout) this.timeout(options.timeout); | |
668 if (options.enableTimeouts !== null) this.enableTimeouts(options.enableTimeout
s); | |
669 if (options.slow) this.slow(options.slow); | |
670 | |
671 this.suite.on('pre-require', function (context) { | |
672 exports.afterEach = context.afterEach; | |
673 exports.after = context.after; | |
674 exports.beforeEach = context.beforeEach; | |
675 exports.before = context.before; | |
676 exports.describe = context.describe; | |
677 exports.it = context.it; | |
678 }); | |
679 } | |
680 | |
681 /** | |
682 * Enable or disable bailing on the first failure. | |
683 * | |
684 * @param {Boolean} [bail] | |
685 * @api public | |
686 */ | |
687 | |
688 Mocha.prototype.bail = function(bail){ | |
689 if (0 == arguments.length) bail = true; | |
690 this.suite.bail(bail); | |
691 return this; | |
692 }; | |
693 | |
694 /** | |
695 * Set reporter to `reporter`, defaults to "spec". | |
696 * | |
697 * @param {String|Function} reporter name or constructor | |
698 * @api public | |
699 */ | |
700 | |
701 Mocha.prototype.reporter = function(){ | |
702 var _reporter = require('./reporters/tap'); | |
703 this._reporter = _reporter; | |
704 }; | |
705 | |
706 /** | |
707 * Set test UI `name`, defaults to "bdd". | |
708 * | |
709 * @param {String} bdd | |
710 * @api public | |
711 */ | |
712 | |
713 Mocha.prototype.ui = function(name){ | |
714 name = name || 'bdd'; | |
715 this._ui = exports.interfaces[name]; | |
716 if (!this._ui) try { this._ui = require(name); } catch (err) {}; | |
717 if (!this._ui) throw new Error('invalid interface "' + name + '"'); | |
718 this._ui = this._ui(this.suite); | |
719 return this; | |
720 }; | |
721 | |
722 Mocha.prototype.grep = function(re){ | |
723 this.options.grep = 'string' == typeof re | |
724 ? new RegExp(utils.escapeRegexp(re)) | |
725 : re; | |
726 return this; | |
727 }; | |
728 | |
729 /** | |
730 * Set the timeout in milliseconds. | |
731 * | |
732 * @param {Number} timeout | |
733 * @return {Mocha} | |
734 * @api public | |
735 */ | |
736 | |
737 Mocha.prototype.timeout = function(timeout){ | |
738 this.suite.timeout(timeout); | |
739 return this; | |
740 }; | |
741 | |
742 /** | |
743 * Set slowness threshold in milliseconds. | |
744 * | |
745 * @param {Number} slow | |
746 * @return {Mocha} | |
747 * @api public | |
748 */ | |
749 | |
750 Mocha.prototype.slow = function(slow){ | |
751 this.suite.slow(slow); | |
752 return this; | |
753 }; | |
754 | |
755 /** | |
756 * Enable timeouts. | |
757 * | |
758 * @param {Boolean} enabled | |
759 * @return {Mocha} | |
760 * @api public | |
761 */ | |
762 | |
763 Mocha.prototype.enableTimeouts = function(enabled) { | |
764 this.suite.enableTimeouts(arguments.length && enabled !== undefined | |
765 ? enabled | |
766 : true); | |
767 return this | |
768 }; | |
769 | |
770 /** | |
771 * Makes all tests async (accepting a callback) | |
772 * | |
773 * @return {Mocha} | |
774 * @api public | |
775 */ | |
776 | |
777 Mocha.prototype.asyncOnly = function(){ | |
778 this.options.asyncOnly = true; | |
779 return this; | |
780 }; | |
781 | |
782 /** | |
783 * Run tests and invoke `fn()` when complete. | |
784 * | |
785 * @param {Function} fn | |
786 * @return {Runner} | |
787 * @api public | |
788 */ | |
789 | |
790 Mocha.prototype.run = function(fn){ | |
791 var suite = this.suite; | |
792 var options = this.options; | |
793 options.files = this.files; | |
794 var runner = new exports.Runner(suite); | |
795 var reporter = new this._reporter(runner, options); | |
796 if (options.grep) runner.grep(options.grep); | |
797 return runner.run(fn); | |
798 }; | |
799 | |
800 }); // module: mocha.js | |
801 | |
802 require.register("ms.js", function(module, exports, require){ | |
803 /** | |
804 * Helpers. | |
805 */ | |
806 | |
807 var s = 1000; | |
808 var m = s * 60; | |
809 var h = m * 60; | |
810 var d = h * 24; | |
811 var y = d * 365.25; | |
812 | |
813 /** | |
814 * Parse or format the given `val`. | |
815 * | |
816 * Options: | |
817 * | |
818 * - `long` verbose formatting [false] | |
819 * | |
820 * @param {String|Number} val | |
821 * @param {Object} options | |
822 * @return {String|Number} | |
823 * @api public | |
824 */ | |
825 | |
826 module.exports = function(val, options){ | |
827 options = options || {}; | |
828 if ('string' == typeof val) return parse(val); | |
829 return options.long ? longFormat(val) : shortFormat(val); | |
830 }; | |
831 | |
832 /** | |
833 * Parse the given `str` and return milliseconds. | |
834 * | |
835 * @param {String} str | |
836 * @return {Number} | |
837 * @api private | |
838 */ | |
839 | |
840 function parse(str) { | |
841 var match = /^((?:\d+)?\.?\d+) *(ms|seconds?|s|minutes?|m|hours?|h|days?|d|yea
rs?|y)?$/i.exec(str); | |
842 if (!match) return; | |
843 var n = parseFloat(match[1]); | |
844 var type = (match[2] || 'ms').toLowerCase(); | |
845 switch (type) { | |
846 case 'years': | |
847 case 'year': | |
848 case 'y': | |
849 return n * y; | |
850 case 'days': | |
851 case 'day': | |
852 case 'd': | |
853 return n * d; | |
854 case 'hours': | |
855 case 'hour': | |
856 case 'h': | |
857 return n * h; | |
858 case 'minutes': | |
859 case 'minute': | |
860 case 'm': | |
861 return n * m; | |
862 case 'seconds': | |
863 case 'second': | |
864 case 's': | |
865 return n * s; | |
866 case 'ms': | |
867 return n; | |
868 } | |
869 } | |
870 | |
871 /** | |
872 * Short format for `ms`. | |
873 * | |
874 * @param {Number} ms | |
875 * @return {String} | |
876 * @api private | |
877 */ | |
878 | |
879 function shortFormat(ms) { | |
880 if (ms >= d) return Math.round(ms / d) + 'd'; | |
881 if (ms >= h) return Math.round(ms / h) + 'h'; | |
882 if (ms >= m) return Math.round(ms / m) + 'm'; | |
883 if (ms >= s) return Math.round(ms / s) + 's'; | |
884 return ms + 'ms'; | |
885 } | |
886 | |
887 /** | |
888 * Long format for `ms`. | |
889 * | |
890 * @param {Number} ms | |
891 * @return {String} | |
892 * @api private | |
893 */ | |
894 | |
895 function longFormat(ms) { | |
896 return plural(ms, d, 'day') | |
897 || plural(ms, h, 'hour') | |
898 || plural(ms, m, 'minute') | |
899 || plural(ms, s, 'second') | |
900 || ms + ' ms'; | |
901 } | |
902 | |
903 /** | |
904 * Pluralization helper. | |
905 */ | |
906 | |
907 function plural(ms, n, name) { | |
908 if (ms < n) return; | |
909 if (ms < n * 1.5) return Math.floor(ms / n) + ' ' + name; | |
910 return Math.ceil(ms / n) + ' ' + name + 's'; | |
911 } | |
912 | |
913 }); // module: ms.js | |
914 | |
915 require.register("reporters/base.js", function(module, exports, require){ | |
916 | |
917 /** | |
918 * Module dependencies. | |
919 */ | |
920 | |
921 var ms = require('../ms') | |
922 , utils = require('../utils'); | |
923 | |
924 | |
925 /** | |
926 * Expose `Base`. | |
927 */ | |
928 | |
929 exports = module.exports = Base; | |
930 | |
931 /** | |
932 * Enable coloring by default. | |
933 */ | |
934 | |
935 exports.useColors = false; | |
936 | |
937 /** | |
938 * Inline diffs instead of +/- | |
939 */ | |
940 | |
941 exports.inlineDiffs = false; | |
942 | |
943 /** | |
944 * Default symbol map. | |
945 */ | |
946 | |
947 exports.symbols = { | |
948 ok: '✓', | |
949 err: '✖', | |
950 dot: '․' | |
951 }; | |
952 | |
953 /** | |
954 * Expose term window size, with some | |
955 * defaults for when stderr is not a tty. | |
956 */ | |
957 | |
958 exports.window = { | |
959 width: 75 | |
960 }; | |
961 | |
962 | |
963 /** | |
964 * Outut the given `failures` as a list. | |
965 * | |
966 * @param {Array} failures | |
967 * @api public | |
968 */ | |
969 | |
970 exports.list = function(failures){ | |
971 | |
972 }; | |
973 | |
974 /** | |
975 * Initialize a new `Base` reporter. | |
976 * | |
977 * All other reporters generally | |
978 * inherit from this reporter, providing | |
979 * stats such as test duration, number | |
980 * of tests passed / failed etc. | |
981 * | |
982 * @param {Runner} runner | |
983 * @api public | |
984 */ | |
985 | |
986 function Base(runner) { | |
987 if (!runner) return; | |
988 this.runner = runner; | |
989 } | |
990 | |
991 | |
992 }); // module: reporters/base.js | |
993 | |
994 require.register("reporters/index.js", function(module, exports, require){ | |
995 | |
996 exports.Base = require('./base'); | |
997 exports.TAP = require('./tap'); | |
998 | |
999 }); // module: reporters/index.js | |
1000 | |
1001 require.register("reporters/tap.js", function(module, exports, require){ | |
1002 | |
1003 /** | |
1004 * Module dependencies. | |
1005 */ | |
1006 | |
1007 var Base = require('./base') | |
1008 , color = Base.color; | |
1009 | |
1010 | |
1011 function Logger() { | |
1012 this.items = []; | |
1013 } | |
1014 | |
1015 Logger.prototype.log = function(message) { | |
1016 this.items.push(message); | |
1017 } | |
1018 | |
1019 Logger.prototype.flush = function() { | |
1020 var body = document.documentElement; | |
1021 body.textContent = ''; | |
1022 body.appendChild(document.createElement('style')).textContent = 'item { displa
y: block; }'; | |
1023 this.items.forEach(function(item) { | |
1024 body.appendChild(document.createElement('item')).textContent = item; | |
1025 }); | |
1026 } | |
1027 | |
1028 /** | |
1029 * Expose `TAP`. | |
1030 */ | |
1031 | |
1032 exports = module.exports = TAP; | |
1033 | |
1034 /** | |
1035 * Initialize a new `TAP` reporter. | |
1036 * | |
1037 * @param {Runner} runner | |
1038 * @api public | |
1039 */ | |
1040 | |
1041 function TAP(runner) { | |
1042 Base.call(this, runner); | |
1043 var logger = new Logger(); | |
1044 | |
1045 var self = this | |
1046 , stats = this.stats | |
1047 , n = 1 | |
1048 , passes = 0 | |
1049 , failures = 0; | |
1050 | |
1051 runner.on('start', function(){ | |
1052 var total = runner.grepTotal(runner.suite); | |
1053 logger.log('Running ' + total + ' tests'); | |
1054 }); | |
1055 | |
1056 runner.on('test end', function(){ | |
1057 ++n; | |
1058 }); | |
1059 | |
1060 runner.on('pending', function(test){ | |
1061 logger.log('ok ' + n + ' ' + title(test) + ' # SKIP -'); | |
1062 }); | |
1063 | |
1064 runner.on('pass', function(test){ | |
1065 passes++; | |
1066 logger.log('ok ' + n + ' ' + title(test)); | |
1067 }); | |
1068 | |
1069 runner.on('fail', function(test, err){ | |
1070 failures++; | |
1071 logger.log('not ok ' + n + ' ' + title(test)); | |
1072 if (err.stack) logger.log(err.stack.replace(/^/gm, ' ')); | |
1073 }); | |
1074 | |
1075 runner.on('end', function(){ | |
1076 logger.log((passes + failures) + ' tests'); | |
1077 logger.log(passes + ' pass'); | |
1078 logger.log(failures + ' fail'); | |
1079 logger.flush(); | |
1080 window.internals && window.internals.notifyTestComplete(internals.contentAsT
ext()); | |
1081 }); | |
1082 } | |
1083 | |
1084 /** | |
1085 * Return a TAP-safe title of `test` | |
1086 * | |
1087 * @param {Object} test | |
1088 * @return {String} | |
1089 * @api private | |
1090 */ | |
1091 | |
1092 function title(test) { | |
1093 return test.fullTitle().replace(/#/g, ''); | |
1094 } | |
1095 | |
1096 }); // module: reporters/tap.js | |
1097 | |
1098 require.register("runnable.js", function(module, exports, require){ | |
1099 | |
1100 /** | |
1101 * Module dependencies. | |
1102 */ | |
1103 | |
1104 var EventEmitter = require('browser/events').EventEmitter | |
1105 , debug = require('browser/debug')('mocha:runnable') | |
1106 , milliseconds = require('./ms'); | |
1107 | |
1108 /** | |
1109 * Object#toString(). | |
1110 */ | |
1111 | |
1112 var toString = Object.prototype.toString; | |
1113 | |
1114 /** | |
1115 * Expose `Runnable`. | |
1116 */ | |
1117 | |
1118 module.exports = Runnable; | |
1119 | |
1120 /** | |
1121 * Initialize a new `Runnable` with the given `title` and callback `fn`. | |
1122 * | |
1123 * @param {String} title | |
1124 * @param {Function} fn | |
1125 * @api private | |
1126 */ | |
1127 | |
1128 function Runnable(title, fn) { | |
1129 this.title = title; | |
1130 this.fn = fn; | |
1131 this.async = fn && fn.length; | |
1132 this.sync = ! this.async; | |
1133 this._timeout = 2000; | |
1134 this._slow = 75; | |
1135 this._enableTimeouts = true; | |
1136 this.timedOut = false; | |
1137 } | |
1138 | |
1139 /** | |
1140 * Inherit from `EventEmitter.prototype`. | |
1141 */ | |
1142 | |
1143 function F(){}; | |
1144 F.prototype = EventEmitter.prototype; | |
1145 Runnable.prototype = new F; | |
1146 Runnable.prototype.constructor = Runnable; | |
1147 | |
1148 | |
1149 /** | |
1150 * Set & get timeout `ms`. | |
1151 * | |
1152 * @param {Number|String} ms | |
1153 * @return {Runnable|Number} ms or self | |
1154 * @api private | |
1155 */ | |
1156 | |
1157 Runnable.prototype.timeout = function(ms){ | |
1158 if (0 == arguments.length) return this._timeout; | |
1159 if ('string' == typeof ms) ms = milliseconds(ms); | |
1160 debug('timeout %d', ms); | |
1161 this._timeout = ms; | |
1162 if (this.timer) this.resetTimeout(); | |
1163 return this; | |
1164 }; | |
1165 | |
1166 /** | |
1167 * Set & get slow `ms`. | |
1168 * | |
1169 * @param {Number|String} ms | |
1170 * @return {Runnable|Number} ms or self | |
1171 * @api private | |
1172 */ | |
1173 | |
1174 Runnable.prototype.slow = function(ms){ | |
1175 if (0 === arguments.length) return this._slow; | |
1176 if ('string' == typeof ms) ms = milliseconds(ms); | |
1177 debug('timeout %d', ms); | |
1178 this._slow = ms; | |
1179 return this; | |
1180 }; | |
1181 | |
1182 /** | |
1183 * Set and & get timeout `enabled`. | |
1184 * | |
1185 * @param {Boolean} enabled | |
1186 * @return {Runnable|Boolean} enabled or self | |
1187 * @api private | |
1188 */ | |
1189 | |
1190 Runnable.prototype.enableTimeouts = function(enabled){ | |
1191 if (arguments.length === 0) return this._enableTimeouts; | |
1192 debug('enableTimeouts %s', enabled); | |
1193 this._enableTimeouts = enabled; | |
1194 return this; | |
1195 }; | |
1196 | |
1197 /** | |
1198 * Return the full title generated by recursively | |
1199 * concatenating the parent's full title. | |
1200 * | |
1201 * @return {String} | |
1202 * @api public | |
1203 */ | |
1204 | |
1205 Runnable.prototype.fullTitle = function(){ | |
1206 return this.parent.fullTitle() + ' ' + this.title; | |
1207 }; | |
1208 | |
1209 /** | |
1210 * Clear the timeout. | |
1211 * | |
1212 * @api private | |
1213 */ | |
1214 | |
1215 Runnable.prototype.clearTimeout = function(){ | |
1216 clearTimeout(this.timer); | |
1217 }; | |
1218 | |
1219 /** | |
1220 * Inspect the runnable void of private properties. | |
1221 * | |
1222 * @return {String} | |
1223 * @api private | |
1224 */ | |
1225 | |
1226 Runnable.prototype.inspect = function(){ | |
1227 return JSON.stringify(this, function(key, val){ | |
1228 if ('_' == key[0]) return; | |
1229 if ('parent' == key) return '#<Suite>'; | |
1230 if ('ctx' == key) return '#<Context>'; | |
1231 return val; | |
1232 }, 2); | |
1233 }; | |
1234 | |
1235 /** | |
1236 * Reset the timeout. | |
1237 * | |
1238 * @api private | |
1239 */ | |
1240 | |
1241 Runnable.prototype.resetTimeout = function(){ | |
1242 var self = this; | |
1243 var ms = this.timeout() || 1e9; | |
1244 | |
1245 if (!this._enableTimeouts) return; | |
1246 this.clearTimeout(); | |
1247 this.timer = setTimeout(function(){ | |
1248 self.callback(new Error('timeout of ' + ms + 'ms exceeded')); | |
1249 self.timedOut = true; | |
1250 }, ms); | |
1251 }; | |
1252 | |
1253 /** | |
1254 * Run the test and invoke `fn(err)`. | |
1255 * | |
1256 * @param {Function} fn | |
1257 * @api private | |
1258 */ | |
1259 | |
1260 Runnable.prototype.run = function(fn){ | |
1261 var self = this | |
1262 , start = new Date | |
1263 , ctx = this.ctx | |
1264 , finished | |
1265 , emitted; | |
1266 | |
1267 // Some times the ctx exists but it is not runnable | |
1268 if (ctx && ctx.runnable) ctx.runnable(this); | |
1269 | |
1270 // called multiple times | |
1271 function multiple(err) { | |
1272 if (emitted) return; | |
1273 emitted = true; | |
1274 self.emit('error', err || new Error('done() called multiple times')); | |
1275 } | |
1276 | |
1277 // finished | |
1278 function done(err) { | |
1279 var ms = self.timeout(); | |
1280 if (self.timedOut) return; | |
1281 if (finished) return multiple(err); | |
1282 self.clearTimeout(); | |
1283 self.duration = new Date - start; | |
1284 finished = true; | |
1285 if (!err && self.duration > ms && self._enableTimeouts) err = new Error('tim
eout of ' + ms + 'ms exceeded'); | |
1286 fn(err); | |
1287 } | |
1288 | |
1289 // for .resetTimeout() | |
1290 this.callback = done; | |
1291 | |
1292 // explicit async with `done` argument | |
1293 if (this.async) { | |
1294 this.resetTimeout(); | |
1295 | |
1296 try { | |
1297 this.fn.call(ctx, function(err){ | |
1298 if (err instanceof Error || toString.call(err) === "[object Error]") ret
urn done(err); | |
1299 if (null != err) { | |
1300 if (Object.prototype.toString.call(err) === '[object Object]') { | |
1301 return done(new Error('done() invoked with non-Error: ' + JSON.strin
gify(err))); | |
1302 } else { | |
1303 return done(new Error('done() invoked with non-Error: ' + err)); | |
1304 } | |
1305 } | |
1306 done(); | |
1307 }); | |
1308 } catch (err) { | |
1309 done(err); | |
1310 } | |
1311 return; | |
1312 } | |
1313 | |
1314 if (this.asyncOnly) { | |
1315 return done(new Error('--async-only option in use without declaring `done()`
')); | |
1316 } | |
1317 | |
1318 // sync or promise-returning | |
1319 try { | |
1320 if (this.pending) { | |
1321 done(); | |
1322 } else { | |
1323 callFn(this.fn); | |
1324 } | |
1325 } catch (err) { | |
1326 done(err); | |
1327 } | |
1328 | |
1329 function callFn(fn) { | |
1330 var result = fn.call(ctx); | |
1331 if (result && typeof result.then === 'function') { | |
1332 self.resetTimeout(); | |
1333 result | |
1334 .then(function() { | |
1335 done() | |
1336 }, | |
1337 function(reason) { | |
1338 done(reason || new Error('Promise rejected with no or falsy reason')) | |
1339 }); | |
1340 } else { | |
1341 done(); | |
1342 } | |
1343 } | |
1344 }; | |
1345 | |
1346 }); // module: runnable.js | |
1347 | |
1348 require.register("runner.js", function(module, exports, require){ | |
1349 /** | |
1350 * Module dependencies. | |
1351 */ | |
1352 | |
1353 var EventEmitter = require('browser/events').EventEmitter | |
1354 , debug = require('browser/debug')('mocha:runner') | |
1355 , Test = require('./test') | |
1356 , utils = require('./utils') | |
1357 , filter = utils.filter | |
1358 , keys = utils.keys; | |
1359 | |
1360 /** | |
1361 * Expose `Runner`. | |
1362 */ | |
1363 | |
1364 module.exports = Runner; | |
1365 | |
1366 /** | |
1367 * Initialize a `Runner` for the given `suite`. | |
1368 * | |
1369 * Events: | |
1370 * | |
1371 * - `start` execution started | |
1372 * - `end` execution complete | |
1373 * - `suite` (suite) test suite execution started | |
1374 * - `suite end` (suite) all tests (and sub-suites) have finished | |
1375 * - `test` (test) test execution started | |
1376 * - `test end` (test) test completed | |
1377 * - `hook` (hook) hook execution started | |
1378 * - `hook end` (hook) hook complete | |
1379 * - `pass` (test) test passed | |
1380 * - `fail` (test, err) test failed | |
1381 * - `pending` (test) test pending | |
1382 * | |
1383 * @api public | |
1384 */ | |
1385 | |
1386 function Runner(suite) { | |
1387 var self = this; | |
1388 this._abort = false; | |
1389 this.suite = suite; | |
1390 this.total = suite.total(); | |
1391 this.failures = 0; | |
1392 this.grep(/.*/); | |
1393 } | |
1394 | |
1395 /** | |
1396 * Wrapper for setImmediate, process.nextTick, or browser polyfill. | |
1397 * | |
1398 * @param {Function} fn | |
1399 * @api private | |
1400 */ | |
1401 | |
1402 Runner.immediately = process.nextTick; | |
1403 | |
1404 /** | |
1405 * Inherit from `EventEmitter.prototype`. | |
1406 */ | |
1407 | |
1408 function F(){}; | |
1409 F.prototype = EventEmitter.prototype; | |
1410 Runner.prototype = new F; | |
1411 Runner.prototype.constructor = Runner; | |
1412 | |
1413 | |
1414 /** | |
1415 * Run tests with full titles matching `re`. Updates runner.total | |
1416 * with number of tests matched. | |
1417 * | |
1418 * @param {RegExp} re | |
1419 * @param {Boolean} invert | |
1420 * @return {Runner} for chaining | |
1421 * @api public | |
1422 */ | |
1423 | |
1424 Runner.prototype.grep = function(re, invert){ | |
1425 debug('grep %s', re); | |
1426 this._grep = re; | |
1427 this._invert = invert; | |
1428 this.total = this.grepTotal(this.suite); | |
1429 return this; | |
1430 }; | |
1431 | |
1432 /** | |
1433 * Returns the number of tests matching the grep search for the | |
1434 * given suite. | |
1435 * | |
1436 * @param {Suite} suite | |
1437 * @return {Number} | |
1438 * @api public | |
1439 */ | |
1440 | |
1441 Runner.prototype.grepTotal = function(suite) { | |
1442 var self = this; | |
1443 var total = 0; | |
1444 | |
1445 suite.eachTest(function(test){ | |
1446 var match = self._grep.test(test.fullTitle()); | |
1447 if (self._invert) match = !match; | |
1448 if (match) total++; | |
1449 }); | |
1450 | |
1451 return total; | |
1452 }; | |
1453 | |
1454 /** | |
1455 * Check for global variable leaks. | |
1456 * | |
1457 * @api private | |
1458 */ | |
1459 | |
1460 /** | |
1461 * Fail the given `test`. | |
1462 * | |
1463 * @param {Test} test | |
1464 * @param {Error} err | |
1465 * @api private | |
1466 */ | |
1467 | |
1468 Runner.prototype.fail = function(test, err){ | |
1469 ++this.failures; | |
1470 test.state = 'failed'; | |
1471 | |
1472 if ('string' == typeof err) { | |
1473 err = new Error('the string "' + err + '" was thrown, throw an Error :)'); | |
1474 } | |
1475 | |
1476 this.emit('fail', test, err); | |
1477 }; | |
1478 | |
1479 /** | |
1480 * Fail the given `hook` with `err`. | |
1481 * | |
1482 * Hook failures work in the following pattern: | |
1483 * - If bail, then exit | |
1484 * - Failed `before` hook skips all tests in a suite and subsuites, | |
1485 * but jumps to corresponding `after` hook | |
1486 * - Failed `before each` hook skips remaining tests in a | |
1487 * suite and jumps to corresponding `after each` hook, | |
1488 * which is run only once | |
1489 * - Failed `after` hook does not alter | |
1490 * execution order | |
1491 * - Failed `after each` hook skips remaining tests in a | |
1492 * suite and subsuites, but executes other `after each` | |
1493 * hooks | |
1494 * | |
1495 * @param {Hook} hook | |
1496 * @param {Error} err | |
1497 * @api private | |
1498 */ | |
1499 | |
1500 Runner.prototype.failHook = function(hook, err){ | |
1501 this.fail(hook, err); | |
1502 if (this.suite.bail()) { | |
1503 this.emit('end'); | |
1504 } | |
1505 }; | |
1506 | |
1507 /** | |
1508 * Run hook `name` callbacks and then invoke `fn()`. | |
1509 * | |
1510 * @param {String} name | |
1511 * @param {Function} function | |
1512 * @api private | |
1513 */ | |
1514 | |
1515 Runner.prototype.hook = function(name, fn){ | |
1516 var suite = this.suite | |
1517 , hooks = suite['_' + name] | |
1518 , self = this | |
1519 , timer; | |
1520 | |
1521 function next(i) { | |
1522 var hook = hooks[i]; | |
1523 if (!hook) return fn(); | |
1524 if (self.failures && suite.bail()) return fn(); | |
1525 self.currentRunnable = hook; | |
1526 | |
1527 hook.ctx.currentTest = self.test; | |
1528 | |
1529 self.emit('hook', hook); | |
1530 | |
1531 hook.on('error', function(err){ | |
1532 self.failHook(hook, err); | |
1533 }); | |
1534 | |
1535 hook.run(function(err){ | |
1536 hook.removeAllListeners('error'); | |
1537 var testError = hook.error(); | |
1538 if (testError) self.fail(self.test, testError); | |
1539 if (err) { | |
1540 self.failHook(hook, err); | |
1541 | |
1542 // stop executing hooks, notify callee of hook err | |
1543 return fn(err); | |
1544 } | |
1545 self.emit('hook end', hook); | |
1546 delete hook.ctx.currentTest; | |
1547 next(++i); | |
1548 }); | |
1549 } | |
1550 | |
1551 Runner.immediately(function(){ | |
1552 next(0); | |
1553 }); | |
1554 }; | |
1555 | |
1556 /** | |
1557 * Run hook `name` for the given array of `suites` | |
1558 * in order, and callback `fn(err, errSuite)`. | |
1559 * | |
1560 * @param {String} name | |
1561 * @param {Array} suites | |
1562 * @param {Function} fn | |
1563 * @api private | |
1564 */ | |
1565 | |
1566 Runner.prototype.hooks = function(name, suites, fn){ | |
1567 var self = this | |
1568 , orig = this.suite; | |
1569 | |
1570 function next(suite) { | |
1571 self.suite = suite; | |
1572 | |
1573 if (!suite) { | |
1574 self.suite = orig; | |
1575 return fn(); | |
1576 } | |
1577 | |
1578 self.hook(name, function(err){ | |
1579 if (err) { | |
1580 var errSuite = self.suite; | |
1581 self.suite = orig; | |
1582 return fn(err, errSuite); | |
1583 } | |
1584 | |
1585 next(suites.pop()); | |
1586 }); | |
1587 } | |
1588 | |
1589 next(suites.pop()); | |
1590 }; | |
1591 | |
1592 /** | |
1593 * Run hooks from the top level down. | |
1594 * | |
1595 * @param {String} name | |
1596 * @param {Function} fn | |
1597 * @api private | |
1598 */ | |
1599 | |
1600 Runner.prototype.hookUp = function(name, fn){ | |
1601 var suites = [this.suite].concat(this.parents()).reverse(); | |
1602 this.hooks(name, suites, fn); | |
1603 }; | |
1604 | |
1605 /** | |
1606 * Run hooks from the bottom up. | |
1607 * | |
1608 * @param {String} name | |
1609 * @param {Function} fn | |
1610 * @api private | |
1611 */ | |
1612 | |
1613 Runner.prototype.hookDown = function(name, fn){ | |
1614 var suites = [this.suite].concat(this.parents()); | |
1615 this.hooks(name, suites, fn); | |
1616 }; | |
1617 | |
1618 /** | |
1619 * Return an array of parent Suites from | |
1620 * closest to furthest. | |
1621 * | |
1622 * @return {Array} | |
1623 * @api private | |
1624 */ | |
1625 | |
1626 Runner.prototype.parents = function(){ | |
1627 var suite = this.suite | |
1628 , suites = []; | |
1629 while (suite = suite.parent) suites.push(suite); | |
1630 return suites; | |
1631 }; | |
1632 | |
1633 /** | |
1634 * Run the current test and callback `fn(err)`. | |
1635 * | |
1636 * @param {Function} fn | |
1637 * @api private | |
1638 */ | |
1639 | |
1640 Runner.prototype.runTest = function(fn){ | |
1641 var test = this.test | |
1642 , self = this; | |
1643 | |
1644 if (this.asyncOnly) test.asyncOnly = true; | |
1645 | |
1646 try { | |
1647 test.on('error', function(err){ | |
1648 self.fail(test, err); | |
1649 }); | |
1650 test.run(fn); | |
1651 } catch (err) { | |
1652 fn(err); | |
1653 } | |
1654 }; | |
1655 | |
1656 /** | |
1657 * Run tests in the given `suite` and invoke | |
1658 * the callback `fn()` when complete. | |
1659 * | |
1660 * @param {Suite} suite | |
1661 * @param {Function} fn | |
1662 * @api private | |
1663 */ | |
1664 | |
1665 Runner.prototype.runTests = function(suite, fn){ | |
1666 var self = this | |
1667 , tests = suite.tests.slice() | |
1668 , test; | |
1669 | |
1670 | |
1671 function hookErr(err, errSuite, after) { | |
1672 // before/after Each hook for errSuite failed: | |
1673 var orig = self.suite; | |
1674 | |
1675 // for failed 'after each' hook start from errSuite parent, | |
1676 // otherwise start from errSuite itself | |
1677 self.suite = after ? errSuite.parent : errSuite; | |
1678 | |
1679 if (self.suite) { | |
1680 // call hookUp afterEach | |
1681 self.hookUp('afterEach', function(err2, errSuite2) { | |
1682 self.suite = orig; | |
1683 // some hooks may fail even now | |
1684 if (err2) return hookErr(err2, errSuite2, true); | |
1685 // report error suite | |
1686 fn(errSuite); | |
1687 }); | |
1688 } else { | |
1689 // there is no need calling other 'after each' hooks | |
1690 self.suite = orig; | |
1691 fn(errSuite); | |
1692 } | |
1693 } | |
1694 | |
1695 function next(err, errSuite) { | |
1696 // if we bail after first err | |
1697 if (self.failures && suite._bail) return fn(); | |
1698 | |
1699 if (self._abort) return fn(); | |
1700 | |
1701 if (err) return hookErr(err, errSuite, true); | |
1702 | |
1703 // next test | |
1704 test = tests.shift(); | |
1705 | |
1706 // all done | |
1707 if (!test) return fn(); | |
1708 | |
1709 // grep | |
1710 var match = self._grep.test(test.fullTitle()); | |
1711 if (self._invert) match = !match; | |
1712 if (!match) return next(); | |
1713 | |
1714 // pending | |
1715 if (test.pending) { | |
1716 self.emit('pending', test); | |
1717 self.emit('test end', test); | |
1718 return next(); | |
1719 } | |
1720 | |
1721 // execute test and hook(s) | |
1722 self.emit('test', self.test = test); | |
1723 self.hookDown('beforeEach', function(err, errSuite){ | |
1724 | |
1725 if (err) return hookErr(err, errSuite, false); | |
1726 | |
1727 self.currentRunnable = self.test; | |
1728 self.runTest(function(err){ | |
1729 test = self.test; | |
1730 | |
1731 if (err) { | |
1732 self.fail(test, err); | |
1733 self.emit('test end', test); | |
1734 return self.hookUp('afterEach', next); | |
1735 } | |
1736 | |
1737 test.state = 'passed'; | |
1738 self.emit('pass', test); | |
1739 self.emit('test end', test); | |
1740 self.hookUp('afterEach', next); | |
1741 }); | |
1742 }); | |
1743 } | |
1744 | |
1745 this.next = next; | |
1746 next(); | |
1747 }; | |
1748 | |
1749 /** | |
1750 * Run the given `suite` and invoke the | |
1751 * callback `fn()` when complete. | |
1752 * | |
1753 * @param {Suite} suite | |
1754 * @param {Function} fn | |
1755 * @api private | |
1756 */ | |
1757 | |
1758 Runner.prototype.runSuite = function(suite, fn){ | |
1759 var total = this.grepTotal(suite) | |
1760 , self = this | |
1761 , i = 0; | |
1762 | |
1763 debug('run suite %s', suite.fullTitle()); | |
1764 | |
1765 if (!total) return fn(); | |
1766 | |
1767 this.emit('suite', this.suite = suite); | |
1768 | |
1769 function next(errSuite) { | |
1770 if (errSuite) { | |
1771 // current suite failed on a hook from errSuite | |
1772 if (errSuite == suite) { | |
1773 // if errSuite is current suite | |
1774 // continue to the next sibling suite | |
1775 return done(); | |
1776 } else { | |
1777 // errSuite is among the parents of current suite | |
1778 // stop execution of errSuite and all sub-suites | |
1779 return done(errSuite); | |
1780 } | |
1781 } | |
1782 | |
1783 if (self._abort) return done(); | |
1784 | |
1785 var curr = suite.suites[i++]; | |
1786 if (!curr) return done(); | |
1787 self.runSuite(curr, next); | |
1788 } | |
1789 | |
1790 function done(errSuite) { | |
1791 self.suite = suite; | |
1792 self.hook('afterAll', function(){ | |
1793 self.emit('suite end', suite); | |
1794 fn(errSuite); | |
1795 }); | |
1796 } | |
1797 | |
1798 this.hook('beforeAll', function(err){ | |
1799 if (err) return done(); | |
1800 self.runTests(suite, next); | |
1801 }); | |
1802 }; | |
1803 | |
1804 /** | |
1805 * Handle uncaught exceptions. | |
1806 * | |
1807 * @param {Error} err | |
1808 * @api private | |
1809 */ | |
1810 | |
1811 Runner.prototype.uncaught = function(err){ | |
1812 if (err) { | |
1813 debug('uncaught exception %s', err.message); | |
1814 } else { | |
1815 debug('uncaught undefined exception'); | |
1816 err = new Error('Catched undefined error, did you throw without specifying w
hat?'); | |
1817 } | |
1818 | |
1819 var runnable = this.currentRunnable; | |
1820 if (!runnable || 'failed' == runnable.state) return; | |
1821 runnable.clearTimeout(); | |
1822 err.uncaught = true; | |
1823 this.fail(runnable, err); | |
1824 | |
1825 // recover from test | |
1826 if ('test' == runnable.type) { | |
1827 this.emit('test end', runnable); | |
1828 this.hookUp('afterEach', this.next); | |
1829 return; | |
1830 } | |
1831 | |
1832 // bail on hooks | |
1833 this.emit('end'); | |
1834 }; | |
1835 | |
1836 /** | |
1837 * Run the root suite and invoke `fn(failures)` | |
1838 * on completion. | |
1839 * | |
1840 * @param {Function} fn | |
1841 * @return {Runner} for chaining | |
1842 * @api public | |
1843 */ | |
1844 | |
1845 Runner.prototype.run = function(fn){ | |
1846 var self = this | |
1847 , fn = fn || function(){}; | |
1848 | |
1849 function uncaught(err){ | |
1850 self.uncaught(err); | |
1851 } | |
1852 | |
1853 debug('start'); | |
1854 | |
1855 // callback | |
1856 this.on('end', function(){ | |
1857 debug('end'); | |
1858 process.removeListener('uncaughtException', uncaught); | |
1859 fn(self.failures); | |
1860 }); | |
1861 | |
1862 // run suites | |
1863 this.emit('start'); | |
1864 this.runSuite(this.suite, function(){ | |
1865 debug('finished running'); | |
1866 self.emit('end'); | |
1867 }); | |
1868 | |
1869 // uncaught exception | |
1870 process.on('uncaughtException', uncaught); | |
1871 | |
1872 return this; | |
1873 }; | |
1874 | |
1875 /** | |
1876 * Cleanly abort execution | |
1877 * | |
1878 * @return {Runner} for chaining | |
1879 * @api public | |
1880 */ | |
1881 Runner.prototype.abort = function(){ | |
1882 debug('aborting'); | |
1883 this._abort = true; | |
1884 } | |
1885 | |
1886 }); // module: runner.js | |
1887 | |
1888 require.register("suite.js", function(module, exports, require){ | |
1889 | |
1890 /** | |
1891 * Module dependencies. | |
1892 */ | |
1893 | |
1894 var EventEmitter = require('browser/events').EventEmitter | |
1895 , debug = require('browser/debug')('mocha:suite') | |
1896 , milliseconds = require('./ms') | |
1897 , Hook = require('./hook'); | |
1898 | |
1899 /** | |
1900 * Expose `Suite`. | |
1901 */ | |
1902 | |
1903 exports = module.exports = Suite; | |
1904 | |
1905 /** | |
1906 * Create a new `Suite` with the given `title` | |
1907 * and parent `Suite`. When a suite with the | |
1908 * same title is already present, that suite | |
1909 * is returned to provide nicer reporter | |
1910 * and more flexible meta-testing. | |
1911 * | |
1912 * @param {Suite} parent | |
1913 * @param {String} title | |
1914 * @return {Suite} | |
1915 * @api public | |
1916 */ | |
1917 | |
1918 exports.create = function(parent, title){ | |
1919 var suite = new Suite(title, parent.ctx); | |
1920 suite.parent = parent; | |
1921 if (parent.pending) suite.pending = true; | |
1922 title = suite.fullTitle(); | |
1923 parent.addSuite(suite); | |
1924 return suite; | |
1925 }; | |
1926 | |
1927 /** | |
1928 * Initialize a new `Suite` with the given | |
1929 * `title` and `ctx`. | |
1930 * | |
1931 * @param {String} title | |
1932 * @param {Context} ctx | |
1933 * @api private | |
1934 */ | |
1935 | |
1936 function Suite(title, parentContext) { | |
1937 this.title = title; | |
1938 var context = function() {}; | |
1939 context.prototype = parentContext; | |
1940 this.ctx = new context(); | |
1941 this.suites = []; | |
1942 this.tests = []; | |
1943 this.pending = false; | |
1944 this._beforeEach = []; | |
1945 this._beforeAll = []; | |
1946 this._afterEach = []; | |
1947 this._afterAll = []; | |
1948 this.root = !title; | |
1949 this._timeout = 2000; | |
1950 this._enableTimeouts = true; | |
1951 this._slow = 75; | |
1952 this._bail = false; | |
1953 } | |
1954 | |
1955 /** | |
1956 * Inherit from `EventEmitter.prototype`. | |
1957 */ | |
1958 | |
1959 function F(){}; | |
1960 F.prototype = EventEmitter.prototype; | |
1961 Suite.prototype = new F; | |
1962 Suite.prototype.constructor = Suite; | |
1963 | |
1964 | |
1965 /** | |
1966 * Return a clone of this `Suite`. | |
1967 * | |
1968 * @return {Suite} | |
1969 * @api private | |
1970 */ | |
1971 | |
1972 Suite.prototype.clone = function(){ | |
1973 var suite = new Suite(this.title); | |
1974 debug('clone'); | |
1975 suite.ctx = this.ctx; | |
1976 suite.timeout(this.timeout()); | |
1977 suite.enableTimeouts(this.enableTimeouts()); | |
1978 suite.slow(this.slow()); | |
1979 suite.bail(this.bail()); | |
1980 return suite; | |
1981 }; | |
1982 | |
1983 /** | |
1984 * Set timeout `ms` or short-hand such as "2s". | |
1985 * | |
1986 * @param {Number|String} ms | |
1987 * @return {Suite|Number} for chaining | |
1988 * @api private | |
1989 */ | |
1990 | |
1991 Suite.prototype.timeout = function(ms){ | |
1992 if (0 == arguments.length) return this._timeout; | |
1993 if ('string' == typeof ms) ms = milliseconds(ms); | |
1994 debug('timeout %d', ms); | |
1995 this._timeout = parseInt(ms, 10); | |
1996 return this; | |
1997 }; | |
1998 | |
1999 /** | |
2000 * Set timeout `enabled`. | |
2001 * | |
2002 * @param {Boolean} enabled | |
2003 * @return {Suite|Boolean} self or enabled | |
2004 * @api private | |
2005 */ | |
2006 | |
2007 Suite.prototype.enableTimeouts = function(enabled){ | |
2008 if (arguments.length === 0) return this._enableTimeouts; | |
2009 debug('enableTimeouts %s', enabled); | |
2010 this._enableTimeouts = enabled; | |
2011 return this; | |
2012 } | |
2013 | |
2014 /** | |
2015 * Set slow `ms` or short-hand such as "2s". | |
2016 * | |
2017 * @param {Number|String} ms | |
2018 * @return {Suite|Number} for chaining | |
2019 * @api private | |
2020 */ | |
2021 | |
2022 Suite.prototype.slow = function(ms){ | |
2023 if (0 === arguments.length) return this._slow; | |
2024 if ('string' == typeof ms) ms = milliseconds(ms); | |
2025 debug('slow %d', ms); | |
2026 this._slow = ms; | |
2027 return this; | |
2028 }; | |
2029 | |
2030 /** | |
2031 * Sets whether to bail after first error. | |
2032 * | |
2033 * @parma {Boolean} bail | |
2034 * @return {Suite|Number} for chaining | |
2035 * @api private | |
2036 */ | |
2037 | |
2038 Suite.prototype.bail = function(bail){ | |
2039 if (0 == arguments.length) return this._bail; | |
2040 debug('bail %s', bail); | |
2041 this._bail = bail; | |
2042 return this; | |
2043 }; | |
2044 | |
2045 /** | |
2046 * Run `fn(test[, done])` before running tests. | |
2047 * | |
2048 * @param {Function} fn | |
2049 * @return {Suite} for chaining | |
2050 * @api private | |
2051 */ | |
2052 | |
2053 Suite.prototype.beforeAll = function(title, fn){ | |
2054 if (this.pending) return this; | |
2055 if ('function' === typeof title) { | |
2056 fn = title; | |
2057 title = fn.name; | |
2058 } | |
2059 title = '"before all" hook' + (title ? ': ' + title : ''); | |
2060 | |
2061 var hook = new Hook(title, fn); | |
2062 hook.parent = this; | |
2063 hook.timeout(this.timeout()); | |
2064 hook.enableTimeouts(this.enableTimeouts()); | |
2065 hook.slow(this.slow()); | |
2066 hook.ctx = this.ctx; | |
2067 this._beforeAll.push(hook); | |
2068 this.emit('beforeAll', hook); | |
2069 return this; | |
2070 }; | |
2071 | |
2072 /** | |
2073 * Run `fn(test[, done])` after running tests. | |
2074 * | |
2075 * @param {Function} fn | |
2076 * @return {Suite} for chaining | |
2077 * @api private | |
2078 */ | |
2079 | |
2080 Suite.prototype.afterAll = function(title, fn){ | |
2081 if (this.pending) return this; | |
2082 if ('function' === typeof title) { | |
2083 fn = title; | |
2084 title = fn.name; | |
2085 } | |
2086 title = '"after all" hook' + (title ? ': ' + title : ''); | |
2087 | |
2088 var hook = new Hook(title, fn); | |
2089 hook.parent = this; | |
2090 hook.timeout(this.timeout()); | |
2091 hook.enableTimeouts(this.enableTimeouts()); | |
2092 hook.slow(this.slow()); | |
2093 hook.ctx = this.ctx; | |
2094 this._afterAll.push(hook); | |
2095 this.emit('afterAll', hook); | |
2096 return this; | |
2097 }; | |
2098 | |
2099 /** | |
2100 * Run `fn(test[, done])` before each test case. | |
2101 * | |
2102 * @param {Function} fn | |
2103 * @return {Suite} for chaining | |
2104 * @api private | |
2105 */ | |
2106 | |
2107 Suite.prototype.beforeEach = function(title, fn){ | |
2108 if (this.pending) return this; | |
2109 if ('function' === typeof title) { | |
2110 fn = title; | |
2111 title = fn.name; | |
2112 } | |
2113 title = '"before each" hook' + (title ? ': ' + title : ''); | |
2114 | |
2115 var hook = new Hook(title, fn); | |
2116 hook.parent = this; | |
2117 hook.timeout(this.timeout()); | |
2118 hook.enableTimeouts(this.enableTimeouts()); | |
2119 hook.slow(this.slow()); | |
2120 hook.ctx = this.ctx; | |
2121 this._beforeEach.push(hook); | |
2122 this.emit('beforeEach', hook); | |
2123 return this; | |
2124 }; | |
2125 | |
2126 /** | |
2127 * Run `fn(test[, done])` after each test case. | |
2128 * | |
2129 * @param {Function} fn | |
2130 * @return {Suite} for chaining | |
2131 * @api private | |
2132 */ | |
2133 | |
2134 Suite.prototype.afterEach = function(title, fn){ | |
2135 if (this.pending) return this; | |
2136 if ('function' === typeof title) { | |
2137 fn = title; | |
2138 title = fn.name; | |
2139 } | |
2140 title = '"after each" hook' + (title ? ': ' + title : ''); | |
2141 | |
2142 var hook = new Hook(title, fn); | |
2143 hook.parent = this; | |
2144 hook.timeout(this.timeout()); | |
2145 hook.enableTimeouts(this.enableTimeouts()); | |
2146 hook.slow(this.slow()); | |
2147 hook.ctx = this.ctx; | |
2148 this._afterEach.push(hook); | |
2149 this.emit('afterEach', hook); | |
2150 return this; | |
2151 }; | |
2152 | |
2153 /** | |
2154 * Add a test `suite`. | |
2155 * | |
2156 * @param {Suite} suite | |
2157 * @return {Suite} for chaining | |
2158 * @api private | |
2159 */ | |
2160 | |
2161 Suite.prototype.addSuite = function(suite){ | |
2162 suite.parent = this; | |
2163 suite.timeout(this.timeout()); | |
2164 suite.enableTimeouts(this.enableTimeouts()); | |
2165 suite.slow(this.slow()); | |
2166 suite.bail(this.bail()); | |
2167 this.suites.push(suite); | |
2168 this.emit('suite', suite); | |
2169 return this; | |
2170 }; | |
2171 | |
2172 /** | |
2173 * Add a `test` to this suite. | |
2174 * | |
2175 * @param {Test} test | |
2176 * @return {Suite} for chaining | |
2177 * @api private | |
2178 */ | |
2179 | |
2180 Suite.prototype.addTest = function(test){ | |
2181 test.parent = this; | |
2182 test.timeout(this.timeout()); | |
2183 test.enableTimeouts(this.enableTimeouts()); | |
2184 test.slow(this.slow()); | |
2185 test.ctx = this.ctx; | |
2186 this.tests.push(test); | |
2187 this.emit('test', test); | |
2188 return this; | |
2189 }; | |
2190 | |
2191 /** | |
2192 * Return the full title generated by recursively | |
2193 * concatenating the parent's full title. | |
2194 * | |
2195 * @return {String} | |
2196 * @api public | |
2197 */ | |
2198 | |
2199 Suite.prototype.fullTitle = function(){ | |
2200 if (this.parent) { | |
2201 var full = this.parent.fullTitle(); | |
2202 if (full) return full + ' ' + this.title; | |
2203 } | |
2204 return this.title; | |
2205 }; | |
2206 | |
2207 /** | |
2208 * Return the total number of tests. | |
2209 * | |
2210 * @return {Number} | |
2211 * @api public | |
2212 */ | |
2213 | |
2214 Suite.prototype.total = function(){ | |
2215 return this.suites.reduce(function(sum, suite){ | |
2216 return sum + suite.total(); | |
2217 }, 0) + this.tests.length; | |
2218 }; | |
2219 | |
2220 /** | |
2221 * Iterates through each suite recursively to find | |
2222 * all tests. Applies a function in the format | |
2223 * `fn(test)`. | |
2224 * | |
2225 * @param {Function} fn | |
2226 * @return {Suite} | |
2227 * @api private | |
2228 */ | |
2229 | |
2230 Suite.prototype.eachTest = function(fn){ | |
2231 this.tests.forEach(fn); | |
2232 this.suites.forEach(function(suite){ | |
2233 suite.eachTest(fn); | |
2234 }); | |
2235 return this; | |
2236 }; | |
2237 | |
2238 }); // module: suite.js | |
2239 | |
2240 require.register("test.js", function(module, exports, require){ | |
2241 | |
2242 /** | |
2243 * Module dependencies. | |
2244 */ | |
2245 | |
2246 var Runnable = require('./runnable'); | |
2247 | |
2248 /** | |
2249 * Expose `Test`. | |
2250 */ | |
2251 | |
2252 module.exports = Test; | |
2253 | |
2254 /** | |
2255 * Initialize a new `Test` with the given `title` and callback `fn`. | |
2256 * | |
2257 * @param {String} title | |
2258 * @param {Function} fn | |
2259 * @api private | |
2260 */ | |
2261 | |
2262 function Test(title, fn) { | |
2263 Runnable.call(this, title, fn); | |
2264 this.pending = !fn; | |
2265 this.type = 'test'; | |
2266 } | |
2267 | |
2268 /** | |
2269 * Inherit from `Runnable.prototype`. | |
2270 */ | |
2271 | |
2272 function F(){}; | |
2273 F.prototype = Runnable.prototype; | |
2274 Test.prototype = new F; | |
2275 Test.prototype.constructor = Test; | |
2276 | |
2277 | |
2278 }); // module: test.js | |
2279 | |
2280 require.register("utils.js", function(module, exports, require){ | |
2281 /** | |
2282 * Module dependencies. | |
2283 */ | |
2284 | |
2285 /** | |
2286 * Escape regular expression characters in `str`. | |
2287 * | |
2288 * @param {String} str | |
2289 * @return {String} | |
2290 * @api private | |
2291 */ | |
2292 | |
2293 exports.escapeRegexp = function(str){ | |
2294 return str.replace(/[-\\^$*+?.()|[\]{}]/g, "\\$&"); | |
2295 }; | |
2296 | |
2297 | |
2298 }); // module: utils.js | |
2299 | |
2300 /** | |
2301 * Save timer references to avoid Sinon interfering (see GH-237). | |
2302 */ | |
2303 | |
2304 /** | |
2305 * Node shims. | |
2306 * | |
2307 * These are meant only to allow | |
2308 * mocha.js to run untouched, not | |
2309 * to allow running node code in | |
2310 * the browser. | |
2311 */ | |
2312 | |
2313 var process = {}; | |
2314 process.exit = function(status){}; | |
2315 process.stdout = {}; | |
2316 | |
2317 var uncaughtExceptionHandlers = []; | |
2318 | |
2319 var originalOnerrorHandler = window.onerror; | |
2320 | |
2321 /** | |
2322 * Remove uncaughtException listener. | |
2323 * Revert to original onerror handler if previously defined. | |
2324 */ | |
2325 | |
2326 process.removeListener = function(e, fn){ | |
2327 if ('uncaughtException' == e) { | |
2328 if (originalOnerrorHandler) { | |
2329 window.onerror = originalOnerrorHandler; | |
2330 } else { | |
2331 window.onerror = function() {}; | |
2332 } | |
2333 var i = uncaughtExceptionHandlers.indexOf(fn); | |
2334 if (i != -1) { uncaughtExceptionHandlers.splice(i, 1); } | |
2335 } | |
2336 }; | |
2337 | |
2338 /** | |
2339 * Implements uncaughtException listener. | |
2340 */ | |
2341 | |
2342 process.on = function(e, fn){ | |
2343 if ('uncaughtException' == e) { | |
2344 window.onerror = function(err, url, line){ | |
2345 fn(new Error(err + ' (' + url + ':' + line + ')')); | |
2346 return true; | |
2347 }; | |
2348 uncaughtExceptionHandlers.push(fn); | |
2349 } | |
2350 }; | |
2351 | |
2352 /** | |
2353 * Expose mocha. | |
2354 */ | |
2355 | |
2356 var Mocha = window.Mocha = require('mocha'), | |
2357 mocha = window.mocha = new Mocha(); | |
2358 | |
2359 // The BDD UI is registered by default, but no UI will be functional in the | |
2360 // browser without an explicit call to the overridden `mocha.ui` (see below). | |
2361 // Ensure that this default UI does not expose its methods to the global scope. | |
2362 mocha.suite.removeAllListeners('pre-require'); | |
2363 | |
2364 var immediateQueue = [] | |
2365 , immediateTimeout; | |
2366 | |
2367 function timeslice() { | |
2368 var immediateStart = new Date().getTime(); | |
2369 while (immediateQueue.length && (new Date().getTime() - immediateStart) < 100)
{ | |
2370 immediateQueue.shift()(); | |
2371 } | |
2372 if (immediateQueue.length) { | |
2373 immediateTimeout = setTimeout(timeslice, 0); | |
2374 } else { | |
2375 immediateTimeout = null; | |
2376 } | |
2377 } | |
2378 | |
2379 /** | |
2380 * High-performance override of Runner.immediately. | |
2381 */ | |
2382 | |
2383 Mocha.Runner.immediately = function(callback) { | |
2384 immediateQueue.push(callback); | |
2385 if (!immediateTimeout) { | |
2386 immediateTimeout = setTimeout(timeslice, 0); | |
2387 } | |
2388 }; | |
2389 | |
2390 /** | |
2391 * Function to allow assertion libraries to throw errors directly into mocha. | |
2392 * This is useful when running tests in a browser because window.onerror will | |
2393 * only receive the 'message' attribute of the Error. | |
2394 */ | |
2395 mocha.throwError = function(err) { | |
2396 uncaughtExceptionHandlers.forEach(function (fn) { | |
2397 fn(err); | |
2398 }); | |
2399 throw err; | |
2400 }; | |
2401 | |
2402 /** | |
2403 * Override ui to ensure that the ui functions are initialized. | |
2404 * Normally this would happen in Mocha.prototype.loadFiles. | |
2405 */ | |
2406 | |
2407 mocha.ui = function(ui){ | |
2408 Mocha.prototype.ui.call(this, ui); | |
2409 this.suite.emit('pre-require', window, null, this); | |
2410 return this; | |
2411 }; | |
2412 | |
2413 /** | |
2414 * Setup mocha with the given setting options. | |
2415 */ | |
2416 | |
2417 mocha.setup = function(opts){ | |
2418 this.ui(); | |
2419 }; | |
2420 | |
2421 /** | |
2422 * Run mocha, returning the Runner. | |
2423 */ | |
2424 | |
2425 mocha.run = function(fn){ | |
2426 return Mocha.prototype.run.call(mocha, function(err){ | |
2427 if (fn) fn(err); | |
2428 }); | |
2429 }; | |
2430 | |
2431 /** | |
2432 * Expose the process shim. | |
2433 */ | |
2434 | |
2435 Mocha.process = process; | |
2436 })(); | |
2437 | |
2438 </script> | |
2439 <script> | |
2440 | |
2441 mocha.setup(); | |
2442 | |
2443 window.addEventListener('load', function() { | |
2444 requestAnimationFrame(function() { | |
2445 mocha.run(); | |
2446 }); | |
2447 }) | |
2448 | |
2449 </script> | |
OLD | NEW |