Tizen 2.1 base
[platform/framework/web/web-ui-fw.git] / libs / js / jquery-mobile-1.2.0 / node_modules / grunt / node_modules / connect / node_modules / qs / test / browser / mocha.js
1 ;(function(){
2
3
4 // CommonJS require()
5
6 function require(p){
7     var path = require.resolve(p)
8       , mod = require.modules[path];
9     if (!mod) throw new Error('failed to require "' + p + '"');
10     if (!mod.exports) {
11       mod.exports = {};
12       mod.call(mod.exports, mod, mod.exports, require.relative(path));
13     }
14     return mod.exports;
15   }
16
17 require.modules = {};
18
19 require.resolve = function (path){
20     var orig = path
21       , reg = path + '.js'
22       , index = path + '/index.js';
23     return require.modules[reg] && reg
24       || require.modules[index] && index
25       || orig;
26   };
27
28 require.register = function (path, fn){
29     require.modules[path] = fn;
30   };
31
32 require.relative = function (parent) {
33     return function(p){
34       if ('.' != p.charAt(0)) return require(p);
35       
36       var path = parent.split('/')
37         , segs = p.split('/');
38       path.pop();
39       
40       for (var i = 0; i < segs.length; i++) {
41         var seg = segs[i];
42         if ('..' == seg) path.pop();
43         else if ('.' != seg) path.push(seg);
44       }
45
46       return require(path.join('/'));
47     };
48   };
49
50
51 require.register("browser/debug.js", function(module, exports, require){
52
53 module.exports = function(type){
54   return function(){
55     
56   }
57 };
58 }); // module: browser/debug.js
59
60 require.register("browser/diff.js", function(module, exports, require){
61
62 }); // module: browser/diff.js
63
64 require.register("browser/events.js", function(module, exports, require){
65
66 /**
67  * Module exports.
68  */
69
70 exports.EventEmitter = EventEmitter;
71
72 /**
73  * Check if `obj` is an array.
74  */
75
76 function isArray(obj) {
77   return '[object Array]' == {}.toString.call(obj);
78 }
79
80 /**
81  * Event emitter constructor.
82  *
83  * @api public.
84  */
85
86 function EventEmitter(){};
87
88 /**
89  * Adds a listener.
90  *
91  * @api public
92  */
93
94 EventEmitter.prototype.on = function (name, fn) {
95   if (!this.$events) {
96     this.$events = {};
97   }
98
99   if (!this.$events[name]) {
100     this.$events[name] = fn;
101   } else if (isArray(this.$events[name])) {
102     this.$events[name].push(fn);
103   } else {
104     this.$events[name] = [this.$events[name], fn];
105   }
106
107   return this;
108 };
109
110 EventEmitter.prototype.addListener = EventEmitter.prototype.on;
111
112 /**
113  * Adds a volatile listener.
114  *
115  * @api public
116  */
117
118 EventEmitter.prototype.once = function (name, fn) {
119   var self = this;
120
121   function on () {
122     self.removeListener(name, on);
123     fn.apply(this, arguments);
124   };
125
126   on.listener = fn;
127   this.on(name, on);
128
129   return this;
130 };
131
132 /**
133  * Removes a listener.
134  *
135  * @api public
136  */
137
138 EventEmitter.prototype.removeListener = function (name, fn) {
139   if (this.$events && this.$events[name]) {
140     var list = this.$events[name];
141
142     if (isArray(list)) {
143       var pos = -1;
144
145       for (var i = 0, l = list.length; i < l; i++) {
146         if (list[i] === fn || (list[i].listener && list[i].listener === fn)) {
147           pos = i;
148           break;
149         }
150       }
151
152       if (pos < 0) {
153         return this;
154       }
155
156       list.splice(pos, 1);
157
158       if (!list.length) {
159         delete this.$events[name];
160       }
161     } else if (list === fn || (list.listener && list.listener === fn)) {
162       delete this.$events[name];
163     }
164   }
165
166   return this;
167 };
168
169 /**
170  * Removes all listeners for an event.
171  *
172  * @api public
173  */
174
175 EventEmitter.prototype.removeAllListeners = function (name) {
176   if (name === undefined) {
177     this.$events = {};
178     return this;
179   }
180
181   if (this.$events && this.$events[name]) {
182     this.$events[name] = null;
183   }
184
185   return this;
186 };
187
188 /**
189  * Gets all listeners for a certain event.
190  *
191  * @api publci
192  */
193
194 EventEmitter.prototype.listeners = function (name) {
195   if (!this.$events) {
196     this.$events = {};
197   }
198
199   if (!this.$events[name]) {
200     this.$events[name] = [];
201   }
202
203   if (!isArray(this.$events[name])) {
204     this.$events[name] = [this.$events[name]];
205   }
206
207   return this.$events[name];
208 };
209
210 /**
211  * Emits an event.
212  *
213  * @api public
214  */
215
216 EventEmitter.prototype.emit = function (name) {
217   if (!this.$events) {
218     return false;
219   }
220
221   var handler = this.$events[name];
222
223   if (!handler) {
224     return false;
225   }
226
227   var args = [].slice.call(arguments, 1);
228
229   if ('function' == typeof handler) {
230     handler.apply(this, args);
231   } else if (isArray(handler)) {
232     var listeners = handler.slice();
233
234     for (var i = 0, l = listeners.length; i < l; i++) {
235       listeners[i].apply(this, args);
236     }
237   } else {
238     return false;
239   }
240
241   return true;
242 };
243 }); // module: browser/events.js
244
245 require.register("browser/fs.js", function(module, exports, require){
246
247 }); // module: browser/fs.js
248
249 require.register("browser/path.js", function(module, exports, require){
250
251 }); // module: browser/path.js
252
253 require.register("browser/progress.js", function(module, exports, require){
254
255 /**
256  * Expose `Progress`.
257  */
258
259 module.exports = Progress;
260
261 /**
262  * Initialize a new `Progress` indicator.
263  */
264
265 function Progress() {
266   this.percent = 0;
267   this.size(0);
268   this.fontSize(11);
269   this.font('helvetica, arial, sans-serif');
270 }
271
272 /**
273  * Set progress size to `n`.
274  *
275  * @param {Number} n
276  * @return {Progress} for chaining
277  * @api public
278  */
279
280 Progress.prototype.size = function(n){
281   this._size = n;
282   return this;
283 };
284
285 /**
286  * Set text to `str`.
287  *
288  * @param {String} str
289  * @return {Progress} for chaining
290  * @api public
291  */
292
293 Progress.prototype.text = function(str){
294   this._text = str;
295   return this;
296 };
297
298 /**
299  * Set font size to `n`.
300  *
301  * @param {Number} n
302  * @return {Progress} for chaining
303  * @api public
304  */
305
306 Progress.prototype.fontSize = function(n){
307   this._fontSize = n;
308   return this;
309 };
310
311 /**
312  * Set font `family`.
313  *
314  * @param {String} family
315  * @return {Progress} for chaining
316  */
317
318 Progress.prototype.font = function(family){
319   this._font = family;
320   return this;
321 };
322
323 /**
324  * Update percentage to `n`.
325  *
326  * @param {Number} n
327  * @return {Progress} for chaining
328  */
329
330 Progress.prototype.update = function(n){
331   this.percent = n;
332   return this;
333 };
334
335 /**
336  * Draw on `ctx`.
337  *
338  * @param {CanvasRenderingContext2d} ctx
339  * @return {Progress} for chaining
340  */
341
342 Progress.prototype.draw = function(ctx){
343   var percent = Math.min(this.percent, 100)
344     , size = this._size
345     , half = size / 2
346     , x = half
347     , y = half
348     , rad = half - 1
349     , fontSize = this._fontSize;
350
351   ctx.font = fontSize + 'px ' + this._font;
352
353   var angle = Math.PI * 2 * (percent / 100);
354   ctx.clearRect(0, 0, size, size);
355
356   // outer circle
357   ctx.strokeStyle = '#9f9f9f';
358   ctx.beginPath();
359   ctx.arc(x, y, rad, 0, angle, false);
360   ctx.stroke();
361
362   // inner circle
363   ctx.strokeStyle = '#eee';
364   ctx.beginPath();
365   ctx.arc(x, y, rad - 1, 0, angle, true);
366   ctx.stroke();
367
368   // text
369   var text = this._text || (percent | 0) + '%'
370     , w = ctx.measureText(text).width;
371
372   ctx.fillText(
373       text
374     , x - w / 2 + 1
375     , y + fontSize / 2 - 1);
376
377   return this;
378 };
379
380 }); // module: browser/progress.js
381
382 require.register("browser/tty.js", function(module, exports, require){
383
384 exports.isatty = function(){
385   return true;
386 };
387
388 exports.getWindowSize = function(){
389   return [window.innerHeight, window.innerWidth];
390 };
391 }); // module: browser/tty.js
392
393 require.register("context.js", function(module, exports, require){
394
395 /**
396  * Expose `Context`.
397  */
398
399 module.exports = Context;
400
401 /**
402  * Initialize a new `Context`.
403  *
404  * @api private
405  */
406
407 function Context(){}
408
409 /**
410  * Set the context `Runnable` to `runnable`.
411  *
412  * @param {Runnable} runnable
413  * @return {Context}
414  * @api private
415  */
416
417 Context.prototype.runnable = function(runnable){
418   this._runnable = runnable;
419   return this;
420 };
421
422 /**
423  * Set test timeout `ms`.
424  *
425  * @param {Number} ms
426  * @return {Context} self
427  * @api private
428  */
429
430 Context.prototype.timeout = function(ms){
431   this._runnable.timeout(ms);
432   return this;
433 };
434
435 /**
436  * Inspect the context void of `._runnable`.
437  *
438  * @return {String}
439  * @api private
440  */
441
442 Context.prototype.inspect = function(){
443   return JSON.stringify(this, function(key, val){
444     return '_runnable' == key
445       ? undefined
446       : val;
447   }, 2);
448 };
449
450 }); // module: context.js
451
452 require.register("hook.js", function(module, exports, require){
453
454 /**
455  * Module dependencies.
456  */
457
458 var Runnable = require('./runnable');
459
460 /**
461  * Expose `Hook`.
462  */
463
464 module.exports = Hook;
465
466 /**
467  * Initialize a new `Hook` with the given `title` and callback `fn`.
468  *
469  * @param {String} title
470  * @param {Function} fn
471  * @api private
472  */
473
474 function Hook(title, fn) {
475   Runnable.call(this, title, fn);
476   this.type = 'hook';
477 }
478
479 /**
480  * Inherit from `Runnable.prototype`.
481  */
482
483 Hook.prototype = new Runnable;
484 Hook.prototype.constructor = Hook;
485
486
487 }); // module: hook.js
488
489 require.register("interfaces/bdd.js", function(module, exports, require){
490
491 /**
492  * Module dependencies.
493  */
494
495 var Suite = require('../suite')
496   , Test = require('../test');
497
498 /**
499  * BDD-style interface:
500  * 
501  *      describe('Array', function(){
502  *        describe('#indexOf()', function(){
503  *          it('should return -1 when not present', function(){
504  *
505  *          });
506  *
507  *          it('should return the index when present', function(){
508  *
509  *          });
510  *        });
511  *      });
512  * 
513  */
514
515 module.exports = function(suite){
516   var suites = [suite];
517
518   suite.on('pre-require', function(context){
519
520     // noop variants
521
522     context.xdescribe = function(){};
523     context.xit = function(){};
524
525     /**
526      * Execute before running tests.
527      */
528
529     context.before = function(fn){
530       suites[0].beforeAll(fn);
531     };
532
533     /**
534      * Execute after running tests.
535      */
536
537     context.after = function(fn){
538       suites[0].afterAll(fn);
539     };
540
541     /**
542      * Execute before each test case.
543      */
544
545     context.beforeEach = function(fn){
546       suites[0].beforeEach(fn);
547     };
548
549     /**
550      * Execute after each test case.
551      */
552
553     context.afterEach = function(fn){
554       suites[0].afterEach(fn);
555     };
556
557     /**
558      * Describe a "suite" with the given `title`
559      * and callback `fn` containing nested suites
560      * and/or tests.
561      */
562   
563     context.describe = function(title, fn){
564       var suite = Suite.create(suites[0], title);
565       suites.unshift(suite);
566       fn();
567       suites.shift();
568     };
569
570     /**
571      * Describe a specification or test-case
572      * with the given `title` and callback `fn`
573      * acting as a thunk.
574      */
575
576     context.it = function(title, fn){
577       suites[0].addTest(new Test(title, fn));
578     };
579   });
580 };
581
582 }); // module: interfaces/bdd.js
583
584 require.register("interfaces/exports.js", function(module, exports, require){
585
586 /**
587  * Module dependencies.
588  */
589
590 var Suite = require('../suite')
591   , Test = require('../test');
592
593 /**
594  * TDD-style interface:
595  * 
596  *     exports.Array = {
597  *       '#indexOf()': {
598  *         'should return -1 when the value is not present': function(){
599  *           
600  *         },
601  *
602  *         'should return the correct index when the value is present': function(){
603  *           
604  *         }
605  *       }
606  *     };
607  * 
608  */
609
610 module.exports = function(suite){
611   var suites = [suite];
612
613   suite.on('require', visit);
614
615   function visit(obj) {
616     var suite;
617     for (var key in obj) {
618       if ('function' == typeof obj[key]) {
619         var fn = obj[key];
620         switch (key) {
621           case 'before':
622             suites[0].beforeAll(fn);
623             break;
624           case 'after':
625             suites[0].afterAll(fn);
626             break;
627           case 'beforeEach':
628             suites[0].beforeEach(fn);
629             break;
630           case 'afterEach':
631             suites[0].afterEach(fn);
632             break;
633           default:
634             suites[0].addTest(new Test(key, fn));
635         }
636       } else {
637         var suite = Suite.create(suites[0], key);
638         suites.unshift(suite);
639         visit(obj[key]);
640         suites.shift();
641       }
642     }
643   }
644 };
645 }); // module: interfaces/exports.js
646
647 require.register("interfaces/index.js", function(module, exports, require){
648
649 exports.bdd = require('./bdd');
650 exports.tdd = require('./tdd');
651 exports.qunit = require('./qunit');
652 exports.exports = require('./exports');
653
654 }); // module: interfaces/index.js
655
656 require.register("interfaces/qunit.js", function(module, exports, require){
657
658 /**
659  * Module dependencies.
660  */
661
662 var Suite = require('../suite')
663   , Test = require('../test');
664
665 /**
666  * QUnit-style interface:
667  * 
668  *     suite('Array');
669  *     
670  *     test('#length', function(){
671  *       var arr = [1,2,3];
672  *       ok(arr.length == 3);
673  *     });
674  *     
675  *     test('#indexOf()', function(){
676  *       var arr = [1,2,3];
677  *       ok(arr.indexOf(1) == 0);
678  *       ok(arr.indexOf(2) == 1);
679  *       ok(arr.indexOf(3) == 2);
680  *     });
681  *     
682  *     suite('String');
683  *     
684  *     test('#length', function(){
685  *       ok('foo'.length == 3);
686  *     });
687  * 
688  */
689
690 module.exports = function(suite){
691   var suites = [suite];
692
693   suite.on('pre-require', function(context){
694
695     /**
696      * Execute before running tests.
697      */
698
699     context.before = function(fn){
700       suites[0].beforeAll(fn);
701     };
702
703     /**
704      * Execute after running tests.
705      */
706
707     context.after = function(fn){
708       suites[0].afterAll(fn);
709     };
710
711     /**
712      * Execute before each test case.
713      */
714
715     context.beforeEach = function(fn){
716       suites[0].beforeEach(fn);
717     };
718
719     /**
720      * Execute after each test case.
721      */
722
723     context.afterEach = function(fn){
724       suites[0].afterEach(fn);
725     };
726
727     /**
728      * Describe a "suite" with the given `title`.
729      */
730   
731     context.suite = function(title){
732       if (suites.length > 1) suites.shift();
733       var suite = Suite.create(suites[0], title);
734       suites.unshift(suite);
735     };
736
737     /**
738      * Describe a specification or test-case
739      * with the given `title` and callback `fn`
740      * acting as a thunk.
741      */
742
743     context.test = function(title, fn){
744       suites[0].addTest(new Test(title, fn));
745     };
746   });
747 };
748
749 }); // module: interfaces/qunit.js
750
751 require.register("interfaces/tdd.js", function(module, exports, require){
752
753 /**
754  * Module dependencies.
755  */
756
757 var Suite = require('../suite')
758   , Test = require('../test');
759
760 /**
761  * TDD-style interface:
762  *
763  *      suite('Array', function(){
764  *        suite('#indexOf()', function(){
765  *          suiteSetup(function(){
766  *
767  *          });
768  *          
769  *          test('should return -1 when not present', function(){
770  *
771  *          });
772  *
773  *          test('should return the index when present', function(){
774  *
775  *          });
776  *
777  *          suiteTeardown(function(){
778  *
779  *          });
780  *        });
781  *      });
782  *
783  */
784
785 module.exports = function(suite){
786   var suites = [suite];
787
788   suite.on('pre-require', function(context){
789
790     /**
791      * Execute before each test case.
792      */
793
794     context.setup = function(fn){
795       suites[0].beforeEach(fn);
796     };
797
798     /**
799      * Execute after each test case.
800      */
801
802     context.teardown = function(fn){
803       suites[0].afterEach(fn);
804     };
805
806     /**
807      * Execute before the suite.
808      */
809
810     context.suiteSetup = function(fn){
811       suites[0].beforeAll(fn);
812     };
813
814     /**
815      * Execute after the suite.
816      */
817
818     context.suiteTeardown = function(fn){
819       suites[0].afterAll(fn);
820     };
821
822     /**
823      * Describe a "suite" with the given `title`
824      * and callback `fn` containing nested suites
825      * and/or tests.
826      */
827
828     context.suite = function(title, fn){
829       var suite = Suite.create(suites[0], title);
830       suites.unshift(suite);
831       fn();
832       suites.shift();
833     };
834
835     /**
836      * Describe a specification or test-case
837      * with the given `title` and callback `fn`
838      * acting as a thunk.
839      */
840
841     context.test = function(title, fn){
842       suites[0].addTest(new Test(title, fn));
843     };
844   });
845 };
846
847 }); // module: interfaces/tdd.js
848
849 require.register("mocha.js", function(module, exports, require){
850
851 /*!
852  * mocha
853  * Copyright(c) 2011 TJ Holowaychuk <tj@vision-media.ca>
854  * MIT Licensed
855  */
856
857 /**
858  * Module dependencies.
859  */
860
861 var path = require('browser/path');
862
863 /**
864  * Expose `Mocha`.
865  */
866
867 exports = module.exports = Mocha;
868
869 /**
870  * Library version.
871  */
872
873 exports.version = '1.0.3';
874
875 /**
876  * Expose internals.
877  */
878
879 exports.utils = require('./utils');
880 exports.interfaces = require('./interfaces');
881 exports.reporters = require('./reporters');
882 exports.Runnable = require('./runnable');
883 exports.Context = require('./context');
884 exports.Runner = require('./runner');
885 exports.Suite = require('./suite');
886 exports.Hook = require('./hook');
887 exports.Test = require('./test');
888
889 /**
890  * Return image `name` path.
891  *
892  * @param {String} name
893  * @return {String}
894  * @api private
895  */
896
897 function image(name) {
898   return __dirname + '/../images/' + name + '.png';
899 }
900
901 /**
902  * Setup mocha with `options`.
903  *
904  * Options:
905  *
906  *   - `ui` name "bdd", "tdd", "exports" etc
907  *   - `reporter` reporter instance, defaults to `mocha.reporters.Dot`
908  *   - `globals` array of accepted globals
909  *   - `timeout` timeout in milliseconds
910  *   - `ignoreLeaks` ignore global leaks
911  *   - `grep` string or regexp to filter tests with
912  *
913  * @param {Object} options
914  * @api public
915  */
916
917 function Mocha(options) {
918   options = options || {};
919   options.grep = 'string' == typeof options.grep
920     ? new RegExp(options.grep)
921     : options.grep;
922   this.files = [];
923   this.options = options;
924   this.suite = new exports.Suite('', new exports.Context);
925   this.ui(options.ui);
926   this.reporter(options.reporter);
927   if (options.timeout) this.suite.timeout(options.timeout);
928 }
929
930 /**
931  * Add test `file`.
932  *
933  * @param {String} file
934  * @api public
935  */
936
937 Mocha.prototype.addFile = function(file){
938   this.files.push(file);
939   return this;
940 };
941
942 /**
943  * Set reporter to `name`, defaults to "dot".
944  *
945  * @param {String} name
946  * @api public
947  */
948
949 Mocha.prototype.reporter = function(name){
950   name = name || 'dot';
951   this._reporter = require('./reporters/' + name);
952   if (!this._reporter) throw new Error('invalid reporter "' + name + '"');
953   return this;
954 };
955
956 /**
957  * Set test UI `name`, defaults to "bdd".
958  *
959  * @param {String} bdd
960  * @api public
961  */
962
963 Mocha.prototype.ui = function(name){
964   name = name || 'bdd';
965   this._ui = exports.interfaces[name];
966   if (!this._ui) throw new Error('invalid interface "' + name + '"');
967   this._ui = this._ui(this.suite);
968   return this;
969 };
970
971 /**
972  * Load registered files.
973  *
974  * @api private
975  */
976
977 Mocha.prototype.loadFiles = function(){
978   var suite = this.suite;
979   this.files.forEach(function(file){
980     file = path.resolve(file);
981     suite.emit('pre-require', global, file);
982     suite.emit('require', require(file), file);
983     suite.emit('post-require', global, file);
984   });
985 };
986
987 /**
988  * Enable growl support.
989  *
990  * @api private
991  */
992
993 Mocha.prototype.growl = function(runner, reporter) {
994   var notify = require('growl');
995
996   runner.on('end', function(){
997     var stats = reporter.stats;
998     if (stats.failures) {
999       var msg = stats.failures + ' of ' + runner.total + ' tests failed';
1000       notify(msg, { title: 'Failed', image: image('fail') });
1001     } else {
1002       notify(stats.passes + ' tests passed in ' + stats.duration + 'ms', {
1003           title: 'Passed'
1004         , image: image('pass')
1005       });
1006     }
1007   });
1008 };
1009
1010 /**
1011  * Add regexp to grep for to the options object
1012  *
1013  * @param {RegExp} or {String} re
1014  * @return {Mocha}
1015  * @api public
1016  */
1017
1018 Mocha.prototype.grep = function(re){
1019   this.options.grep = 'string' == typeof re
1020     ? new RegExp(re)
1021     : re;
1022   return this;
1023 };
1024
1025 /**
1026  * Run tests and invoke `fn()` when complete.
1027  *
1028  * @param {Function} fn
1029  * @return {Runner}
1030  * @api public
1031  */
1032
1033 Mocha.prototype.run = function(fn){
1034   this.loadFiles();
1035   var suite = this.suite;
1036   var options = this.options;
1037   var runner = new exports.Runner(suite);
1038   var reporter = new this._reporter(runner);
1039   runner.ignoreLeaks = options.ignoreLeaks;
1040   if (options.grep) runner.grep(options.grep);
1041   if (options.globals) runner.globals(options.globals);
1042   if (options.growl) this.growl(runner, reporter);
1043   return runner.run(fn);
1044 };
1045
1046 }); // module: mocha.js
1047
1048 require.register("reporters/base.js", function(module, exports, require){
1049
1050 /**
1051  * Module dependencies.
1052  */
1053
1054 var tty = require('browser/tty')
1055   , diff = require('browser/diff');
1056
1057 /**
1058  * Save timer references to avoid Sinon interfering (see GH-237).
1059  */
1060
1061 var Date = global.Date
1062   , setTimeout = global.setTimeout
1063   , setInterval = global.setInterval
1064   , clearTimeout = global.clearTimeout
1065   , clearInterval = global.clearInterval;
1066
1067 /**
1068  * Check if both stdio streams are associated with a tty.
1069  */
1070
1071 var isatty = tty.isatty(1) && tty.isatty(2);
1072
1073 /**
1074  * Expose `Base`.
1075  */
1076
1077 exports = module.exports = Base;
1078
1079 /**
1080  * Enable coloring by default.
1081  */
1082
1083 exports.useColors = isatty;
1084
1085 /**
1086  * Default color map.
1087  */
1088
1089 exports.colors = {
1090     'pass': 90
1091   , 'fail': 31
1092   , 'bright pass': 92
1093   , 'bright fail': 91
1094   , 'bright yellow': 93
1095   , 'pending': 36
1096   , 'suite': 0
1097   , 'error title': 0
1098   , 'error message': 31
1099   , 'error stack': 90
1100   , 'checkmark': 32
1101   , 'fast': 90
1102   , 'medium': 33
1103   , 'slow': 31
1104   , 'green': 32
1105   , 'light': 90
1106   , 'diff gutter': 90
1107   , 'diff added': 42
1108   , 'diff removed': 41
1109 };
1110
1111 /**
1112  * Color `str` with the given `type`,
1113  * allowing colors to be disabled,
1114  * as well as user-defined color
1115  * schemes.
1116  *
1117  * @param {String} type
1118  * @param {String} str
1119  * @return {String}
1120  * @api private
1121  */
1122
1123 var color = exports.color = function(type, str) {
1124   if (!exports.useColors) return str;
1125   return '\033[' + exports.colors[type] + 'm' + str + '\033[0m';
1126 };
1127
1128 /**
1129  * Expose term window size, with some
1130  * defaults for when stderr is not a tty.
1131  */
1132
1133 exports.window = {
1134   width: isatty
1135     ? process.stdout.getWindowSize
1136       ? process.stdout.getWindowSize(1)[0]
1137       : tty.getWindowSize()[1]
1138     : 75
1139 };
1140
1141 /**
1142  * Expose some basic cursor interactions
1143  * that are common among reporters.
1144  */
1145
1146 exports.cursor = {
1147   hide: function(){
1148     process.stdout.write('\033[?25l');
1149   },
1150
1151   show: function(){
1152     process.stdout.write('\033[?25h');
1153   },
1154
1155   deleteLine: function(){
1156     process.stdout.write('\033[2K');
1157   },
1158
1159   beginningOfLine: function(){
1160     process.stdout.write('\033[0G');
1161   },
1162
1163   CR: function(){
1164     exports.cursor.deleteLine();
1165     exports.cursor.beginningOfLine();
1166   }
1167 };
1168
1169 /**
1170  * A test is considered slow if it
1171  * exceeds the following value in milliseconds.
1172  */
1173
1174 exports.slow = 75;
1175
1176 /**
1177  * Outut the given `failures` as a list.
1178  *
1179  * @param {Array} failures
1180  * @api public
1181  */
1182
1183 exports.list = function(failures){
1184   console.error();
1185   failures.forEach(function(test, i){
1186     // format
1187     var fmt = color('error title', '  %s) %s:\n')
1188       + color('error message', '     %s')
1189       + color('error stack', '\n%s\n');
1190
1191     // msg
1192     var err = test.err
1193       , message = err.message || ''
1194       , stack = err.stack || message
1195       , index = stack.indexOf(message) + message.length
1196       , msg = stack.slice(0, index)
1197       , actual = err.actual
1198       , expected = err.expected;
1199
1200     // actual / expected diff
1201     if ('string' == typeof actual && 'string' == typeof expected) {
1202       var len = Math.max(actual.length, expected.length);
1203
1204       if (len < 20) msg = errorDiff(err, 'Chars');
1205       else msg = errorDiff(err, 'Words');
1206
1207       // linenos
1208       var lines = msg.split('\n');
1209       if (lines.length > 4) {
1210         var width = String(lines.length).length;
1211         msg = lines.map(function(str, i){
1212           return pad(++i, width) + ' |' + ' ' + str;
1213         }).join('\n');
1214       }
1215
1216       // legend
1217       msg = '\n'
1218         + color('diff removed', 'actual')
1219         + ' '
1220         + color('diff added', 'expected')
1221         + '\n\n'
1222         + msg
1223         + '\n';
1224
1225       // indent
1226       msg = msg.replace(/^/gm, '      ');
1227
1228       fmt = color('error title', '  %s) %s:\n%s')
1229         + color('error stack', '\n%s\n');
1230     }
1231
1232     // indent stack trace without msg
1233     stack = stack.slice(index ? index + 1 : index)
1234       .replace(/^/gm, '  ');
1235
1236     console.error(fmt, (i + 1), test.fullTitle(), msg, stack);
1237   });
1238 };
1239
1240 /**
1241  * Initialize a new `Base` reporter.
1242  *
1243  * All other reporters generally
1244  * inherit from this reporter, providing
1245  * stats such as test duration, number
1246  * of tests passed / failed etc.
1247  *
1248  * @param {Runner} runner
1249  * @api public
1250  */
1251
1252 function Base(runner) {
1253   var self = this
1254     , stats = this.stats = { suites: 0, tests: 0, passes: 0, pending: 0, failures: 0 }
1255     , failures = this.failures = [];
1256
1257   if (!runner) return;
1258   this.runner = runner;
1259
1260   runner.on('start', function(){
1261     stats.start = new Date;
1262   });
1263
1264   runner.on('suite', function(suite){
1265     stats.suites = stats.suites || 0;
1266     suite.root || stats.suites++;
1267   });
1268
1269   runner.on('test end', function(test){
1270     stats.tests = stats.tests || 0;
1271     stats.tests++;
1272   });
1273
1274   runner.on('pass', function(test){
1275     stats.passes = stats.passes || 0;
1276
1277     var medium = exports.slow / 2;
1278     test.speed = test.duration > exports.slow
1279       ? 'slow'
1280       : test.duration > medium
1281         ? 'medium'
1282         : 'fast';
1283
1284     stats.passes++;
1285   });
1286
1287   runner.on('fail', function(test, err){
1288     stats.failures = stats.failures || 0;
1289     stats.failures++;
1290     test.err = err;
1291     failures.push(test);
1292   });
1293
1294   runner.on('end', function(){
1295     stats.end = new Date;
1296     stats.duration = new Date - stats.start;
1297   });
1298
1299   runner.on('pending', function(){
1300     stats.pending++;
1301   });
1302 }
1303
1304 /**
1305  * Output common epilogue used by many of
1306  * the bundled reporters.
1307  *
1308  * @api public
1309  */
1310
1311 Base.prototype.epilogue = function(){
1312   var stats = this.stats
1313     , fmt
1314     , tests;
1315
1316   console.log();
1317
1318   function pluralize(n) {
1319     return 1 == n ? 'test' : 'tests';
1320   }
1321
1322   // failure
1323   if (stats.failures) {
1324     fmt = color('bright fail', '  âœ–')
1325       + color('fail', ' %d of %d %s failed')
1326       + color('light', ':')
1327
1328     console.error(fmt,
1329       stats.failures,
1330       this.runner.total,
1331       pluralize(this.runner.total));
1332
1333     Base.list(this.failures);
1334     console.error();
1335     return;
1336   }
1337
1338   // pass
1339   fmt = color('bright pass', '  âœ”')
1340     + color('green', ' %d %s complete')
1341     + color('light', ' (%dms)');
1342
1343   console.log(fmt,
1344     stats.tests || 0,
1345     pluralize(stats.tests),
1346     stats.duration);
1347
1348   // pending
1349   if (stats.pending) {
1350     fmt = color('pending', '  â€¢')
1351       + color('pending', ' %d %s pending');
1352
1353     console.log(fmt, stats.pending, pluralize(stats.pending));
1354   }
1355
1356   console.log();
1357 };
1358
1359 /**
1360  * Pad the given `str` to `len`.
1361  *
1362  * @param {String} str
1363  * @param {String} len
1364  * @return {String}
1365  * @api private
1366  */
1367
1368 function pad(str, len) {
1369   str = String(str);
1370   return Array(len - str.length + 1).join(' ') + str;
1371 }
1372
1373 /**
1374  * Return a character diff for `err`.
1375  *
1376  * @param {Error} err
1377  * @return {String}
1378  * @api private
1379  */
1380
1381 function errorDiff(err, type) {
1382   return diff['diff' + type](err.actual, err.expected).map(function(str){
1383     if (/^(\n+)$/.test(str.value)) str.value = Array(++RegExp.$1.length).join('<newline>');
1384     if (str.added) return colorLines('diff added', str.value);
1385     if (str.removed) return colorLines('diff removed', str.value);
1386     return str.value;
1387   }).join('');
1388 }
1389
1390 /**
1391  * Color lines for `str`, using the color `name`.
1392  *
1393  * @param {String} name
1394  * @param {String} str
1395  * @return {String}
1396  * @api private
1397  */
1398
1399 function colorLines(name, str) {
1400   return str.split('\n').map(function(str){
1401     return color(name, str);
1402   }).join('\n');
1403 }
1404
1405 }); // module: reporters/base.js
1406
1407 require.register("reporters/doc.js", function(module, exports, require){
1408
1409 /**
1410  * Module dependencies.
1411  */
1412
1413 var Base = require('./base')
1414   , utils = require('../utils');
1415
1416 /**
1417  * Expose `Doc`.
1418  */
1419
1420 exports = module.exports = Doc;
1421
1422 /**
1423  * Initialize a new `Doc` reporter.
1424  *
1425  * @param {Runner} runner
1426  * @api public
1427  */
1428
1429 function Doc(runner) {
1430   Base.call(this, runner);
1431
1432   var self = this
1433     , stats = this.stats
1434     , total = runner.total
1435     , indents = 2;
1436
1437   function indent() {
1438     return Array(indents).join('  ');
1439   }
1440
1441   runner.on('suite', function(suite){
1442     if (suite.root) return;
1443     ++indents;
1444     console.log('%s<section class="suite">', indent());
1445     ++indents;
1446     console.log('%s<h1>%s</h1>', indent(), suite.title);
1447     console.log('%s<dl>', indent());
1448   });
1449
1450   runner.on('suite end', function(suite){
1451     if (suite.root) return;
1452     console.log('%s</dl>', indent());
1453     --indents;
1454     console.log('%s</section>', indent());
1455     --indents;
1456   });
1457
1458   runner.on('pass', function(test){
1459     console.log('%s  <dt>%s</dt>', indent(), test.title);
1460     var code = utils.escape(clean(test.fn.toString()));
1461     console.log('%s  <dd><pre><code>%s</code></pre></dd>', indent(), code);
1462   });
1463 }
1464
1465 /**
1466  * Strip the function definition from `str`,
1467  * and re-indent for pre whitespace.
1468  */
1469
1470 function clean(str) {
1471   str = str
1472     .replace(/^function *\(.*\) *{/, '')
1473     .replace(/\s+\}$/, '');
1474
1475   var spaces = str.match(/^\n?( *)/)[1].length
1476     , re = new RegExp('^ {' + spaces + '}', 'gm');
1477
1478   str = str.replace(re, '');
1479
1480   return str;
1481 }
1482 }); // module: reporters/doc.js
1483
1484 require.register("reporters/dot.js", function(module, exports, require){
1485
1486 /**
1487  * Module dependencies.
1488  */
1489
1490 var Base = require('./base')
1491   , color = Base.color;
1492
1493 /**
1494  * Expose `Dot`.
1495  */
1496
1497 exports = module.exports = Dot;
1498
1499 /**
1500  * Initialize a new `Dot` matrix test reporter.
1501  *
1502  * @param {Runner} runner
1503  * @api public
1504  */
1505
1506 function Dot(runner) {
1507   Base.call(this, runner);
1508
1509   var self = this
1510     , stats = this.stats
1511     , width = Base.window.width * .75 | 0
1512     , n = 0;
1513
1514   runner.on('start', function(){
1515     process.stdout.write('\n  ');
1516   });
1517
1518   runner.on('pending', function(test){
1519     process.stdout.write(color('pending', '.'));
1520   });
1521
1522   runner.on('pass', function(test){
1523     if (++n % width == 0) process.stdout.write('\n  ');
1524     if ('slow' == test.speed) {
1525       process.stdout.write(color('bright yellow', '.'));
1526     } else {
1527       process.stdout.write(color(test.speed, '.'));
1528     }
1529   });
1530
1531   runner.on('fail', function(test, err){
1532     if (++n % width == 0) process.stdout.write('\n  ');
1533     process.stdout.write(color('fail', '.'));
1534   });
1535
1536   runner.on('end', function(){
1537     console.log();
1538     self.epilogue();
1539   });
1540 }
1541
1542 /**
1543  * Inherit from `Base.prototype`.
1544  */
1545
1546 Dot.prototype = new Base;
1547 Dot.prototype.constructor = Dot;
1548
1549 }); // module: reporters/dot.js
1550
1551 require.register("reporters/html-cov.js", function(module, exports, require){
1552
1553 /**
1554  * Module dependencies.
1555  */
1556
1557 var JSONCov = require('./json-cov')
1558   , fs = require('browser/fs');
1559
1560 /**
1561  * Expose `HTMLCov`.
1562  */
1563
1564 exports = module.exports = HTMLCov;
1565
1566 /**
1567  * Initialize a new `JsCoverage` reporter.
1568  *
1569  * @param {Runner} runner
1570  * @api public
1571  */
1572
1573 function HTMLCov(runner) {
1574   var jade = require('jade')
1575     , file = __dirname + '/templates/coverage.jade'
1576     , str = fs.readFileSync(file, 'utf8')
1577     , fn = jade.compile(str, { filename: file })
1578     , self = this;
1579
1580   JSONCov.call(this, runner, false);
1581
1582   runner.on('end', function(){
1583     process.stdout.write(fn({
1584         cov: self.cov
1585       , coverageClass: coverageClass
1586     }));
1587   });
1588 }
1589
1590 function coverageClass(n) {
1591   if (n >= 75) return 'high';
1592   if (n >= 50) return 'medium';
1593   if (n >= 25) return 'low';
1594   return 'terrible';
1595 }
1596 }); // module: reporters/html-cov.js
1597
1598 require.register("reporters/html.js", function(module, exports, require){
1599
1600 /**
1601  * Module dependencies.
1602  */
1603
1604 var Base = require('./base')
1605   , utils = require('../utils')
1606   , Progress = require('../browser/progress')
1607   , escape = utils.escape;
1608
1609 /**
1610  * Save timer references to avoid Sinon interfering (see GH-237).
1611  */
1612
1613 var Date = global.Date
1614   , setTimeout = global.setTimeout
1615   , setInterval = global.setInterval
1616   , clearTimeout = global.clearTimeout
1617   , clearInterval = global.clearInterval;
1618
1619 /**
1620  * Expose `Doc`.
1621  */
1622
1623 exports = module.exports = HTML;
1624
1625 /**
1626  * Stats template.
1627  */
1628
1629 var statsTemplate = '<ul id="stats">'
1630   + '<li class="progress"><canvas width="40" height="40"></canvas></li>'
1631   + '<li class="passes">passes: <em>0</em></li>'
1632   + '<li class="failures">failures: <em>0</em></li>'
1633   + '<li class="duration">duration: <em>0</em>s</li>'
1634   + '</ul>';
1635
1636 /**
1637  * Initialize a new `Doc` reporter.
1638  *
1639  * @param {Runner} runner
1640  * @api public
1641  */
1642
1643 function HTML(runner) {
1644   Base.call(this, runner);
1645
1646   var self = this
1647     , stats = this.stats
1648     , total = runner.total
1649     , root = document.getElementById('mocha')
1650     , stat = fragment(statsTemplate)
1651     , items = stat.getElementsByTagName('li')
1652     , passes = items[1].getElementsByTagName('em')[0]
1653     , failures = items[2].getElementsByTagName('em')[0]
1654     , duration = items[3].getElementsByTagName('em')[0]
1655     , canvas = stat.getElementsByTagName('canvas')[0]
1656     , stack = [root]
1657     , progress
1658     , ctx
1659
1660   if (canvas.getContext) {
1661     ctx = canvas.getContext('2d');
1662     progress = new Progress;
1663   }
1664
1665   if (!root) return error('#mocha div missing, add it to your document');
1666
1667   root.appendChild(stat);
1668
1669   if (progress) progress.size(40);
1670
1671   runner.on('suite', function(suite){
1672     if (suite.root) return;
1673
1674     // suite
1675     var el = fragment('<div class="suite"><h1>%s</h1></div>', suite.title);
1676
1677     // container
1678     stack[0].appendChild(el);
1679     stack.unshift(document.createElement('div'));
1680     el.appendChild(stack[0]);
1681   });
1682
1683   runner.on('suite end', function(suite){
1684     if (suite.root) return;
1685     stack.shift();
1686   });
1687
1688   runner.on('fail', function(test, err){
1689     if ('hook' == test.type || err.uncaught) runner.emit('test end', test);
1690   });
1691
1692   runner.on('test end', function(test){
1693     // TODO: add to stats
1694     var percent = stats.tests / total * 100 | 0;
1695     if (progress) progress.update(percent).draw(ctx);
1696
1697     // update stats
1698     var ms = new Date - stats.start;
1699     text(passes, stats.passes);
1700     text(failures, stats.failures);
1701     text(duration, (ms / 1000).toFixed(2));
1702
1703     // test
1704     if ('passed' == test.state) {
1705       var el = fragment('<div class="test pass %e"><h2>%e<span class="duration">%ems</span></h2></div>', test.speed, test.title, test.duration);
1706     } else if (test.pending) {
1707       var el = fragment('<div class="test pass pending"><h2>%e</h2></div>', test.title);
1708     } else {
1709       var el = fragment('<div class="test fail"><h2>%e</h2></div>', test.title);
1710       var str = test.err.stack || test.err.toString();
1711
1712       // FF / Opera do not add the message
1713       if (!~str.indexOf(test.err.message)) {
1714         str = test.err.message + '\n' + str;
1715       }
1716
1717       // <=IE7 stringifies to [Object Error]. Since it can be overloaded, we
1718       // check for the result of the stringifying.
1719       if ('[object Error]' == str) str = test.err.message;
1720
1721       // Safari doesn't give you a stack. Let's at least provide a source line.
1722       if (!test.err.stack && test.err.sourceURL && test.err.line !== undefined) {
1723         str += "\n(" + test.err.sourceURL + ":" + test.err.line + ")";
1724       }
1725
1726       el.appendChild(fragment('<pre class="error">%e</pre>', str));
1727     }
1728
1729     // toggle code
1730     var h2 = el.getElementsByTagName('h2')[0];
1731
1732     on(h2, 'click', function(){
1733       pre.style.display = 'none' == pre.style.display
1734         ? 'block'
1735         : 'none';
1736     });
1737
1738     // code
1739     // TODO: defer
1740     if (!test.pending) {
1741       var pre = fragment('<pre><code>%e</code></pre>', clean(test.fn.toString()));
1742       el.appendChild(pre);
1743       pre.style.display = 'none';
1744     }
1745
1746     stack[0].appendChild(el);
1747   });
1748 }
1749
1750 /**
1751  * Display error `msg`.
1752  */
1753
1754 function error(msg) {
1755   document.body.appendChild(fragment('<div id="error">%s</div>', msg));
1756 }
1757
1758 /**
1759  * Return a DOM fragment from `html`.
1760  */
1761
1762 function fragment(html) {
1763   var args = arguments
1764     , div = document.createElement('div')
1765     , i = 1;
1766
1767   div.innerHTML = html.replace(/%([se])/g, function(_, type){
1768     switch (type) {
1769       case 's': return String(args[i++]);
1770       case 'e': return escape(args[i++]);
1771     }
1772   });
1773
1774   return div.firstChild;
1775 }
1776
1777 /**
1778  * Set `el` text to `str`.
1779  */
1780
1781 function text(el, str) {
1782   if (el.textContent) {
1783     el.textContent = str;
1784   } else {
1785     el.innerText = str;
1786   }
1787 }
1788
1789 /**
1790  * Listen on `event` with callback `fn`.
1791  */
1792
1793 function on(el, event, fn) {
1794   if (el.addEventListener) {
1795     el.addEventListener(event, fn, false);
1796   } else {
1797     el.attachEvent('on' + event, fn);
1798   }
1799 }
1800
1801 /**
1802  * Strip the function definition from `str`,
1803  * and re-indent for pre whitespace.
1804  */
1805
1806 function clean(str) {
1807   str = str
1808     .replace(/^function *\(.*\) *{/, '')
1809     .replace(/\s+\}$/, '');
1810
1811   var spaces = str.match(/^\n?( *)/)[1].length
1812     , re = new RegExp('^ {' + spaces + '}', 'gm');
1813
1814   str = str
1815     .replace(re, '')
1816     .replace(/^\s+/, '');
1817
1818   return str;
1819 }
1820
1821 }); // module: reporters/html.js
1822
1823 require.register("reporters/index.js", function(module, exports, require){
1824
1825 exports.Base = require('./base');
1826 exports.Dot = require('./dot');
1827 exports.Doc = require('./doc');
1828 exports.TAP = require('./tap');
1829 exports.JSON = require('./json');
1830 exports.HTML = require('./html');
1831 exports.List = require('./list');
1832 exports.Min = require('./min');
1833 exports.Spec = require('./spec');
1834 exports.Progress = require('./progress');
1835 exports.Landing = require('./landing');
1836 exports.JSONCov = require('./json-cov');
1837 exports.HTMLCov = require('./html-cov');
1838 exports.JSONStream = require('./json-stream');
1839 exports.XUnit = require('./xunit')
1840 exports.Teamcity = require('./teamcity')
1841
1842 }); // module: reporters/index.js
1843
1844 require.register("reporters/json-cov.js", function(module, exports, require){
1845
1846 /**
1847  * Module dependencies.
1848  */
1849
1850 var Base = require('./base');
1851
1852 /**
1853  * Expose `JSONCov`.
1854  */
1855
1856 exports = module.exports = JSONCov;
1857
1858 /**
1859  * Initialize a new `JsCoverage` reporter.
1860  *
1861  * @param {Runner} runner
1862  * @param {Boolean} output
1863  * @api public
1864  */
1865
1866 function JSONCov(runner, output) {
1867   var self = this
1868     , output = 1 == arguments.length ? true : output;
1869
1870   Base.call(this, runner);
1871
1872   var tests = []
1873     , failures = []
1874     , passes = [];
1875
1876   runner.on('test end', function(test){
1877     tests.push(test);
1878   });
1879
1880   runner.on('pass', function(test){
1881     passes.push(test);
1882   });
1883
1884   runner.on('fail', function(test){
1885     failures.push(test);
1886   });
1887
1888   runner.on('end', function(){
1889     var cov = global._$jscoverage || {};
1890     var result = self.cov = map(cov);
1891     result.stats = self.stats;
1892     result.tests = tests.map(clean);
1893     result.failures = failures.map(clean);
1894     result.passes = passes.map(clean);
1895     if (!output) return;
1896     process.stdout.write(JSON.stringify(result, null, 2 ));
1897   });
1898 }
1899
1900 /**
1901  * Map jscoverage data to a JSON structure
1902  * suitable for reporting.
1903  *
1904  * @param {Object} cov
1905  * @return {Object}
1906  * @api private
1907  */
1908
1909 function map(cov) {
1910   var ret = {
1911       instrumentation: 'node-jscoverage'
1912     , sloc: 0
1913     , hits: 0
1914     , misses: 0
1915     , coverage: 0
1916     , files: []
1917   };
1918
1919   for (var filename in cov) {
1920     var data = coverage(filename, cov[filename]);
1921     ret.files.push(data);
1922     ret.hits += data.hits;
1923     ret.misses += data.misses;
1924     ret.sloc += data.sloc;
1925   }
1926
1927   if (ret.sloc > 0) {
1928     ret.coverage = (ret.hits / ret.sloc) * 100;
1929   }
1930
1931   return ret;
1932 };
1933
1934 /**
1935  * Map jscoverage data for a single source file
1936  * to a JSON structure suitable for reporting.
1937  *
1938  * @param {String} filename name of the source file
1939  * @param {Object} data jscoverage coverage data
1940  * @return {Object}
1941  * @api private
1942  */
1943
1944 function coverage(filename, data) {
1945   var ret = {
1946     filename: filename,
1947     coverage: 0,
1948     hits: 0,
1949     misses: 0,
1950     sloc: 0,
1951     source: {}
1952   };
1953
1954   data.source.forEach(function(line, num){
1955     num++;
1956
1957     if (data[num] === 0) {
1958       ret.misses++;
1959       ret.sloc++;
1960     } else if (data[num] !== undefined) {
1961       ret.hits++;
1962       ret.sloc++;
1963     }
1964
1965     ret.source[num] = {
1966         source: line
1967       , coverage: data[num] === undefined
1968         ? ''
1969         : data[num]
1970     };
1971   });
1972
1973   ret.coverage = ret.hits / ret.sloc * 100;
1974
1975   return ret;
1976 }
1977
1978 /**
1979  * Return a plain-object representation of `test`
1980  * free of cyclic properties etc.
1981  *
1982  * @param {Object} test
1983  * @return {Object}
1984  * @api private
1985  */
1986
1987 function clean(test) {
1988   return {
1989       title: test.title
1990     , fullTitle: test.fullTitle()
1991     , duration: test.duration
1992   }
1993 }
1994
1995 }); // module: reporters/json-cov.js
1996
1997 require.register("reporters/json-stream.js", function(module, exports, require){
1998
1999 /**
2000  * Module dependencies.
2001  */
2002
2003 var Base = require('./base')
2004   , color = Base.color;
2005
2006 /**
2007  * Expose `List`.
2008  */
2009
2010 exports = module.exports = List;
2011
2012 /**
2013  * Initialize a new `List` test reporter.
2014  *
2015  * @param {Runner} runner
2016  * @api public
2017  */
2018
2019 function List(runner) {
2020   Base.call(this, runner);
2021
2022   var self = this
2023     , stats = this.stats
2024     , total = runner.total;
2025
2026   runner.on('start', function(){
2027     console.log(JSON.stringify(['start', { total: total }]));
2028   });
2029
2030   runner.on('pass', function(test){
2031     console.log(JSON.stringify(['pass', clean(test)]));
2032   });
2033
2034   runner.on('fail', function(test, err){
2035     console.log(JSON.stringify(['fail', clean(test)]));
2036   });
2037
2038   runner.on('end', function(){
2039     process.stdout.write(JSON.stringify(['end', self.stats]));
2040   });
2041 }
2042
2043 /**
2044  * Return a plain-object representation of `test`
2045  * free of cyclic properties etc.
2046  *
2047  * @param {Object} test
2048  * @return {Object}
2049  * @api private
2050  */
2051
2052 function clean(test) {
2053   return {
2054       title: test.title
2055     , fullTitle: test.fullTitle()
2056     , duration: test.duration
2057   }
2058 }
2059 }); // module: reporters/json-stream.js
2060
2061 require.register("reporters/json.js", function(module, exports, require){
2062
2063 /**
2064  * Module dependencies.
2065  */
2066
2067 var Base = require('./base')
2068   , cursor = Base.cursor
2069   , color = Base.color;
2070
2071 /**
2072  * Expose `JSON`.
2073  */
2074
2075 exports = module.exports = JSONReporter;
2076
2077 /**
2078  * Initialize a new `JSON` reporter.
2079  *
2080  * @param {Runner} runner
2081  * @api public
2082  */
2083
2084 function JSONReporter(runner) {
2085   var self = this;
2086   Base.call(this, runner);
2087
2088   var tests = []
2089     , failures = []
2090     , passes = [];
2091
2092   runner.on('test end', function(test){
2093     tests.push(test);
2094   });
2095
2096   runner.on('pass', function(test){
2097     passes.push(test);
2098   });
2099
2100   runner.on('fail', function(test){
2101     failures.push(test);
2102   });
2103
2104   runner.on('end', function(){
2105     var obj = {
2106         stats: self.stats
2107       , tests: tests.map(clean)
2108       , failures: failures.map(clean)
2109       , passes: passes.map(clean)
2110     };
2111
2112     process.stdout.write(JSON.stringify(obj, null, 2));
2113   });
2114 }
2115
2116 /**
2117  * Return a plain-object representation of `test`
2118  * free of cyclic properties etc.
2119  *
2120  * @param {Object} test
2121  * @return {Object}
2122  * @api private
2123  */
2124
2125 function clean(test) {
2126   return {
2127       title: test.title
2128     , fullTitle: test.fullTitle()
2129     , duration: test.duration
2130   }
2131 }
2132 }); // module: reporters/json.js
2133
2134 require.register("reporters/landing.js", function(module, exports, require){
2135
2136 /**
2137  * Module dependencies.
2138  */
2139
2140 var Base = require('./base')
2141   , cursor = Base.cursor
2142   , color = Base.color;
2143
2144 /**
2145  * Expose `Landing`.
2146  */
2147
2148 exports = module.exports = Landing;
2149
2150 /**
2151  * Airplane color.
2152  */
2153
2154 Base.colors.plane = 0;
2155
2156 /**
2157  * Airplane crash color.
2158  */
2159
2160 Base.colors['plane crash'] = 31;
2161
2162 /**
2163  * Runway color.
2164  */
2165
2166 Base.colors.runway = 90;
2167
2168 /**
2169  * Initialize a new `Landing` reporter.
2170  *
2171  * @param {Runner} runner
2172  * @api public
2173  */
2174
2175 function Landing(runner) {
2176   Base.call(this, runner);
2177
2178   var self = this
2179     , stats = this.stats
2180     , width = Base.window.width * .75 | 0
2181     , total = runner.total
2182     , stream = process.stdout
2183     , plane = color('plane', '✈')
2184     , crashed = -1
2185     , n = 0;
2186
2187   function runway() {
2188     var buf = Array(width).join('-');
2189     return '  ' + color('runway', buf);
2190   }
2191
2192   runner.on('start', function(){
2193     stream.write('\n  ');
2194     cursor.hide();
2195   });
2196
2197   runner.on('test end', function(test){
2198     // check if the plane crashed
2199     var col = -1 == crashed
2200       ? width * ++n / total | 0
2201       : crashed;
2202
2203     // show the crash
2204     if ('failed' == test.state) {
2205       plane = color('plane crash', '✈');
2206       crashed = col;
2207     }
2208
2209     // render landing strip
2210     stream.write('\033[4F\n\n');
2211     stream.write(runway());
2212     stream.write('\n  ');
2213     stream.write(color('runway', Array(col).join('â‹…')));
2214     stream.write(plane)
2215     stream.write(color('runway', Array(width - col).join('â‹…') + '\n'));
2216     stream.write(runway());
2217     stream.write('\033[0m');
2218   });
2219
2220   runner.on('end', function(){
2221     cursor.show();
2222     console.log();
2223     self.epilogue();
2224   });
2225 }
2226
2227 /**
2228  * Inherit from `Base.prototype`.
2229  */
2230
2231 Landing.prototype = new Base;
2232 Landing.prototype.constructor = Landing;
2233
2234 }); // module: reporters/landing.js
2235
2236 require.register("reporters/list.js", function(module, exports, require){
2237
2238 /**
2239  * Module dependencies.
2240  */
2241
2242 var Base = require('./base')
2243   , cursor = Base.cursor
2244   , color = Base.color;
2245
2246 /**
2247  * Expose `List`.
2248  */
2249
2250 exports = module.exports = List;
2251
2252 /**
2253  * Initialize a new `List` test reporter.
2254  *
2255  * @param {Runner} runner
2256  * @api public
2257  */
2258
2259 function List(runner) {
2260   Base.call(this, runner);
2261
2262   var self = this
2263     , stats = this.stats
2264     , n = 0;
2265
2266   runner.on('start', function(){
2267     console.log();
2268   });
2269
2270   runner.on('test', function(test){
2271     process.stdout.write(color('pass', '    ' + test.fullTitle() + ': '));
2272   });
2273
2274   runner.on('pending', function(test){
2275     var fmt = color('checkmark', '  -')
2276       + color('pending', ' %s');
2277     console.log(fmt, test.fullTitle());
2278   });
2279
2280   runner.on('pass', function(test){
2281     var fmt = color('checkmark', '  âœ“')
2282       + color('pass', ' %s: ')
2283       + color(test.speed, '%dms');
2284     cursor.CR();
2285     console.log(fmt, test.fullTitle(), test.duration);
2286   });
2287
2288   runner.on('fail', function(test, err){
2289     cursor.CR();
2290     console.log(color('fail', '  %d) %s'), ++n, test.fullTitle());
2291   });
2292
2293   runner.on('end', self.epilogue.bind(self));
2294 }
2295
2296 /**
2297  * Inherit from `Base.prototype`.
2298  */
2299
2300 List.prototype = new Base;
2301 List.prototype.constructor = List;
2302
2303
2304 }); // module: reporters/list.js
2305
2306 require.register("reporters/markdown.js", function(module, exports, require){
2307
2308 /**
2309  * Module dependencies.
2310  */
2311
2312 var Base = require('./base')
2313   , utils = require('../utils');
2314
2315 /**
2316  * Expose `Markdown`.
2317  */
2318
2319 exports = module.exports = Markdown;
2320
2321 /**
2322  * Initialize a new `Markdown` reporter.
2323  *
2324  * @param {Runner} runner
2325  * @api public
2326  */
2327
2328 function Markdown(runner) {
2329   Base.call(this, runner);
2330
2331   var self = this
2332     , stats = this.stats
2333     , total = runner.total
2334     , level = 0
2335     , buf = '';
2336
2337   function title(str) {
2338     return Array(level).join('#') + ' ' + str;
2339   }
2340
2341   function indent() {
2342     return Array(level).join('  ');
2343   }
2344
2345   function mapTOC(suite, obj) {
2346     var ret = obj;
2347     obj = obj[suite.title] = obj[suite.title] || { suite: suite };
2348     suite.suites.forEach(function(suite){
2349       mapTOC(suite, obj);
2350     });
2351     return ret;
2352   }
2353
2354   function stringifyTOC(obj, level) {
2355     ++level;
2356     var buf = '';
2357     var link;
2358     for (var key in obj) {
2359       if ('suite' == key) continue;
2360       if (key) link = ' - [' + key + '](#' + utils.slug(obj[key].suite.fullTitle()) + ')\n';
2361       if (key) buf += Array(level).join('  ') + link;
2362       buf += stringifyTOC(obj[key], level);
2363     }
2364     --level;
2365     return buf;
2366   }
2367
2368   function generateTOC(suite) {
2369     var obj = mapTOC(suite, {});
2370     return stringifyTOC(obj, 0);
2371   }
2372
2373   generateTOC(runner.suite);
2374
2375   runner.on('suite', function(suite){
2376     ++level;
2377     var slug = utils.slug(suite.fullTitle());
2378     buf += '<a name="' + slug + '" />' + '\n';
2379     buf += title(suite.title) + '\n';
2380   });
2381
2382   runner.on('suite end', function(suite){
2383     --level;
2384   });
2385
2386   runner.on('pass', function(test){
2387     var code = clean(test.fn.toString());
2388     buf += test.title + '.\n';
2389     buf += '\n```js';
2390     buf += code + '\n';
2391     buf += '```\n\n';
2392   });
2393
2394   runner.on('end', function(){
2395     process.stdout.write('# TOC\n');
2396     process.stdout.write(generateTOC(runner.suite));
2397     process.stdout.write(buf);
2398   });
2399 }
2400
2401 /**
2402  * Strip the function definition from `str`,
2403  * and re-indent for pre whitespace.
2404  */
2405
2406 function clean(str) {
2407   str = str
2408     .replace(/^function *\(.*\) *{/, '')
2409     .replace(/\s+\}$/, '');
2410
2411   var spaces = str.match(/^\n?( *)/)[1].length
2412     , re = new RegExp('^ {' + spaces + '}', 'gm');
2413
2414   str = str.replace(re, '');
2415
2416   return str;
2417 }
2418 }); // module: reporters/markdown.js
2419
2420 require.register("reporters/min.js", function(module, exports, require){
2421 /**
2422  * Module dependencies.
2423  */
2424
2425 var Base = require('./base');
2426
2427 /**
2428  * Expose `Min`.
2429  */
2430
2431 exports = module.exports = Min;
2432
2433 /**
2434  * Initialize a new `Min` minimal test reporter (best used with --watch).
2435  *
2436  * @param {Runner} runner
2437  * @api public
2438  */
2439
2440 function Min(runner) {
2441   Base.call(this, runner);
2442   
2443   runner.on('start', function(){
2444     // clear screen
2445     process.stdout.write('\033[2J');
2446     // set cursor position
2447     process.stdout.write('\033[1;3H');
2448   });
2449
2450   runner.on('end', this.epilogue.bind(this));
2451 }
2452
2453 /**
2454  * Inherit from `Base.prototype`.
2455  */
2456
2457 Min.prototype = new Base;
2458 Min.prototype.constructor = Min;
2459
2460 }); // module: reporters/min.js
2461
2462 require.register("reporters/progress.js", function(module, exports, require){
2463
2464 /**
2465  * Module dependencies.
2466  */
2467
2468 var Base = require('./base')
2469   , cursor = Base.cursor
2470   , color = Base.color;
2471
2472 /**
2473  * Expose `Progress`.
2474  */
2475
2476 exports = module.exports = Progress;
2477
2478 /**
2479  * General progress bar color.
2480  */
2481
2482 Base.colors.progress = 90;
2483
2484 /**
2485  * Initialize a new `Progress` bar test reporter.
2486  *
2487  * @param {Runner} runner
2488  * @param {Object} options
2489  * @api public
2490  */
2491
2492 function Progress(runner, options) {
2493   Base.call(this, runner);
2494
2495   var self = this
2496     , options = options || {}
2497     , stats = this.stats
2498     , width = Base.window.width * .50 | 0
2499     , total = runner.total
2500     , complete = 0
2501     , max = Math.max;
2502
2503   // default chars
2504   options.open = options.open || '[';
2505   options.complete = options.complete || 'â–¬';
2506   options.incomplete = options.incomplete || 'â‹…';
2507   options.close = options.close || ']';
2508   options.verbose = false;
2509
2510   // tests started
2511   runner.on('start', function(){
2512     console.log();
2513     cursor.hide();
2514   });
2515
2516   // tests complete
2517   runner.on('test end', function(){
2518     complete++;
2519     var incomplete = total - complete
2520       , percent = complete / total
2521       , n = width * percent | 0
2522       , i = width - n;
2523
2524     cursor.CR();
2525     process.stdout.write('\033[J');
2526     process.stdout.write(color('progress', '  ' + options.open));
2527     process.stdout.write(Array(n).join(options.complete));
2528     process.stdout.write(Array(i).join(options.incomplete));
2529     process.stdout.write(color('progress', options.close));
2530     if (options.verbose) {
2531       process.stdout.write(color('progress', ' ' + complete + ' of ' + total));
2532     }
2533   });
2534
2535   // tests are complete, output some stats
2536   // and the failures if any
2537   runner.on('end', function(){
2538     cursor.show();
2539     console.log();
2540     self.epilogue();
2541   });
2542 }
2543
2544 /**
2545  * Inherit from `Base.prototype`.
2546  */
2547
2548 Progress.prototype = new Base;
2549 Progress.prototype.constructor = Progress;
2550
2551
2552 }); // module: reporters/progress.js
2553
2554 require.register("reporters/spec.js", function(module, exports, require){
2555
2556 /**
2557  * Module dependencies.
2558  */
2559
2560 var Base = require('./base')
2561   , cursor = Base.cursor
2562   , color = Base.color;
2563
2564 /**
2565  * Expose `Spec`.
2566  */
2567
2568 exports = module.exports = Spec;
2569
2570 /**
2571  * Initialize a new `Spec` test reporter.
2572  *
2573  * @param {Runner} runner
2574  * @api public
2575  */
2576
2577 function Spec(runner) {
2578   Base.call(this, runner);
2579
2580   var self = this
2581     , stats = this.stats
2582     , indents = 0
2583     , n = 0;
2584
2585   function indent() {
2586     return Array(indents).join('  ')
2587   }
2588
2589   runner.on('start', function(){
2590     console.log();
2591   });
2592
2593   runner.on('suite', function(suite){
2594     ++indents;
2595     console.log(color('suite', '%s%s'), indent(), suite.title);
2596   });
2597
2598   runner.on('suite end', function(suite){
2599     --indents;
2600     if (1 == indents) console.log();
2601   });
2602
2603   runner.on('test', function(test){
2604     process.stdout.write(indent() + color('pass', '  â—¦ ' + test.title + ': '));
2605   });
2606
2607   runner.on('pending', function(test){
2608     var fmt = indent() + color('pending', '  - %s');
2609     console.log(fmt, test.title);
2610   });
2611
2612   runner.on('pass', function(test){
2613     if ('fast' == test.speed) {
2614       var fmt = indent()
2615         + color('checkmark', '  âœ“')
2616         + color('pass', ' %s ');
2617       cursor.CR();
2618       console.log(fmt, test.title);
2619     } else {
2620       var fmt = indent()
2621         + color('checkmark', '  âœ“')
2622         + color('pass', ' %s ')
2623         + color(test.speed, '(%dms)');
2624       cursor.CR();
2625       console.log(fmt, test.title, test.duration);
2626     }
2627   });
2628
2629   runner.on('fail', function(test, err){
2630     cursor.CR();
2631     console.log(indent() + color('fail', '  %d) %s'), ++n, test.title);
2632   });
2633
2634   runner.on('end', self.epilogue.bind(self));
2635 }
2636
2637 /**
2638  * Inherit from `Base.prototype`.
2639  */
2640
2641 Spec.prototype = new Base;
2642 Spec.prototype.constructor = Spec;
2643
2644
2645 }); // module: reporters/spec.js
2646
2647 require.register("reporters/tap.js", function(module, exports, require){
2648
2649 /**
2650  * Module dependencies.
2651  */
2652
2653 var Base = require('./base')
2654   , cursor = Base.cursor
2655   , color = Base.color;
2656
2657 /**
2658  * Expose `TAP`.
2659  */
2660
2661 exports = module.exports = TAP;
2662
2663 /**
2664  * Initialize a new `TAP` reporter.
2665  *
2666  * @param {Runner} runner
2667  * @api public
2668  */
2669
2670 function TAP(runner) {
2671   Base.call(this, runner);
2672
2673   var self = this
2674     , stats = this.stats
2675     , total = runner.total
2676     , n = 1;
2677
2678   runner.on('start', function(){
2679     console.log('%d..%d', 1, total);
2680   });
2681
2682   runner.on('test end', function(){
2683     ++n;
2684   });
2685
2686   runner.on('pending', function(test){
2687     console.log('ok %d %s # SKIP -', n, title(test));
2688   });
2689
2690   runner.on('pass', function(test){
2691     console.log('ok %d %s', n, title(test));
2692   });
2693
2694   runner.on('fail', function(test, err){
2695     console.log('not ok %d %s', n, title(test));
2696     console.log(err.stack.replace(/^/gm, '  '));
2697   });
2698 }
2699
2700 /**
2701  * Return a TAP-safe title of `test`
2702  *
2703  * @param {Object} test
2704  * @return {String}
2705  * @api private
2706  */
2707
2708 function title(test) {
2709   return test.fullTitle().replace(/#/g, '');
2710 }
2711
2712 }); // module: reporters/tap.js
2713
2714 require.register("reporters/teamcity.js", function(module, exports, require){
2715
2716 /**
2717  * Module dependencies.
2718  */
2719
2720 var Base = require('./base');
2721
2722 /**
2723  * Expose `Teamcity`.
2724  */
2725
2726 exports = module.exports = Teamcity;
2727
2728 /**
2729  * Initialize a new `Teamcity` reporter.
2730  *
2731  * @param {Runner} runner
2732  * @api public
2733  */
2734
2735 function Teamcity(runner) {
2736   Base.call(this, runner);
2737   var stats = this.stats;
2738
2739   runner.on('start', function() {
2740     console.log("##teamcity[testSuiteStarted name='mocha.suite']");
2741   });
2742
2743   runner.on('test', function(test) {
2744     console.log("##teamcity[testStarted name='" + escape(test.fullTitle()) + "']");
2745   });
2746
2747   runner.on('fail', function(test, err) {
2748     console.log("##teamcity[testFailed name='" + escape(test.fullTitle()) + "' message='" + escape(err.message) + "']");
2749   });
2750
2751   runner.on('pending', function(test) {
2752     console.log("##teamcity[testIgnored name='" + escape(test.fullTitle()) + "' message='pending']");
2753   });
2754
2755   runner.on('test end', function(test) {
2756     console.log("##teamcity[testFinished name='" + escape(test.fullTitle()) + "' duration='" + test.duration + "']");
2757   });
2758
2759   runner.on('end', function() {
2760     console.log("##teamcity[testSuiteFinished name='mocha.suite' duration='" + stats.duration + "']");
2761   });
2762 }
2763
2764 /**
2765  * Escape the given `str`.
2766  */
2767
2768 function escape(str) {
2769   return str.replace(/'/g, "|'");
2770 }
2771 }); // module: reporters/teamcity.js
2772
2773 require.register("reporters/xunit.js", function(module, exports, require){
2774
2775 /**
2776  * Module dependencies.
2777  */
2778
2779 var Base = require('./base')
2780   , utils = require('../utils')
2781   , escape = utils.escape;
2782
2783 /**
2784  * Save timer references to avoid Sinon interfering (see GH-237).
2785  */
2786
2787 var Date = global.Date
2788   , setTimeout = global.setTimeout
2789   , setInterval = global.setInterval
2790   , clearTimeout = global.clearTimeout
2791   , clearInterval = global.clearInterval;
2792
2793 /**
2794  * Expose `XUnit`.
2795  */
2796
2797 exports = module.exports = XUnit;
2798
2799 /**
2800  * Initialize a new `XUnit` reporter.
2801  *
2802  * @param {Runner} runner
2803  * @api public
2804  */
2805
2806 function XUnit(runner) {
2807   Base.call(this, runner);
2808   var stats = this.stats
2809     , tests = []
2810     , self = this;
2811
2812   runner.on('test end', function(test){
2813     tests.push(test);
2814   });
2815
2816   runner.on('end', function(){
2817     console.log(tag('testsuite', {
2818         name: 'Mocha Tests'
2819       , tests: stats.tests
2820       , failures: stats.failures
2821       , errors: stats.failures
2822       , skip: stats.tests - stats.failures - stats.passes
2823       , timestamp: (new Date).toUTCString()
2824       , time: stats.duration / 1000
2825     }, false));
2826
2827     tests.forEach(test);
2828     console.log('</testsuite>');    
2829   });
2830 }
2831
2832 /**
2833  * Inherit from `Base.prototype`.
2834  */
2835
2836 XUnit.prototype = new Base;
2837 XUnit.prototype.constructor = XUnit;
2838
2839
2840 /**
2841  * Output tag for the given `test.`
2842  */
2843
2844 function test(test) {
2845   var attrs = {
2846       classname: test.parent.fullTitle()
2847     , name: test.title
2848     , time: test.duration / 1000
2849   };
2850
2851   if ('failed' == test.state) {
2852     var err = test.err;
2853     attrs.message = escape(err.message);
2854     console.log(tag('testcase', attrs, false, tag('failure', attrs, false, cdata(err.stack))));
2855   } else if (test.pending) {
2856     console.log(tag('testcase', attrs, false, tag('skipped', {}, true)));
2857   } else {
2858     console.log(tag('testcase', attrs, true) );
2859   }
2860 }
2861
2862 /**
2863  * HTML tag helper.
2864  */
2865
2866 function tag(name, attrs, close, content) {
2867   var end = close ? '/>' : '>'
2868     , pairs = []
2869     , tag;
2870
2871   for (var key in attrs) {
2872     pairs.push(key + '="' + escape(attrs[key]) + '"');
2873   }
2874
2875   tag = '<' + name + (pairs.length ? ' ' + pairs.join(' ') : '') + end;
2876   if (content) tag += content + '</' + name + end;
2877   return tag;
2878 }
2879
2880 /**
2881  * Return cdata escaped CDATA `str`.
2882  */
2883
2884 function cdata(str) {
2885   return '<![CDATA[' + escape(str) + ']]>';
2886 }
2887
2888 }); // module: reporters/xunit.js
2889
2890 require.register("runnable.js", function(module, exports, require){
2891
2892 /**
2893  * Module dependencies.
2894  */
2895
2896 var EventEmitter = require('browser/events').EventEmitter
2897   , debug = require('browser/debug')('runnable');
2898
2899 /**
2900  * Save timer references to avoid Sinon interfering (see GH-237).
2901  */
2902
2903 var Date = global.Date
2904   , setTimeout = global.setTimeout
2905   , setInterval = global.setInterval
2906   , clearTimeout = global.clearTimeout
2907   , clearInterval = global.clearInterval;
2908
2909 /**
2910  * Expose `Runnable`.
2911  */
2912
2913 module.exports = Runnable;
2914
2915 /**
2916  * Initialize a new `Runnable` with the given `title` and callback `fn`.
2917  *
2918  * @param {String} title
2919  * @param {Function} fn
2920  * @api private
2921  */
2922
2923 function Runnable(title, fn) {
2924   this.title = title;
2925   this.fn = fn;
2926   this.async = fn && fn.length;
2927   this.sync = ! this.async;
2928   this._timeout = 2000;
2929   this.timedOut = false;
2930 }
2931
2932 /**
2933  * Inherit from `EventEmitter.prototype`.
2934  */
2935
2936 Runnable.prototype = new EventEmitter;
2937 Runnable.prototype.constructor = Runnable;
2938
2939
2940 /**
2941  * Set & get timeout `ms`.
2942  *
2943  * @param {Number} ms
2944  * @return {Runnable|Number} ms or self
2945  * @api private
2946  */
2947
2948 Runnable.prototype.timeout = function(ms){
2949   if (0 == arguments.length) return this._timeout;
2950   debug('timeout %d', ms);
2951   this._timeout = ms;
2952   if (this.timer) this.resetTimeout();
2953   return this;
2954 };
2955
2956 /**
2957  * Return the full title generated by recursively
2958  * concatenating the parent's full title.
2959  *
2960  * @return {String}
2961  * @api public
2962  */
2963
2964 Runnable.prototype.fullTitle = function(){
2965   return this.parent.fullTitle() + ' ' + this.title;
2966 };
2967
2968 /**
2969  * Clear the timeout.
2970  *
2971  * @api private
2972  */
2973
2974 Runnable.prototype.clearTimeout = function(){
2975   clearTimeout(this.timer);
2976 };
2977
2978 /**
2979  * Reset the timeout.
2980  *
2981  * @api private
2982  */
2983
2984 Runnable.prototype.resetTimeout = function(){
2985   var self = this
2986     , ms = this.timeout();
2987
2988   this.clearTimeout();
2989   if (ms) {
2990     this.timer = setTimeout(function(){
2991       self.callback(new Error('timeout of ' + ms + 'ms exceeded'));
2992       self.timedOut = true;
2993     }, ms);
2994   }
2995 };
2996
2997 /**
2998  * Run the test and invoke `fn(err)`.
2999  *
3000  * @param {Function} fn
3001  * @api private
3002  */
3003
3004 Runnable.prototype.run = function(fn){
3005   var self = this
3006     , ms = this.timeout()
3007     , start = new Date
3008     , ctx = this.ctx
3009     , finished
3010     , emitted;
3011
3012   if (ctx) ctx.runnable(this);
3013
3014   // timeout
3015   if (this.async) {
3016     if (ms) {
3017       this.timer = setTimeout(function(){
3018         done(new Error('timeout of ' + ms + 'ms exceeded'));
3019         self.timedOut = true;
3020       }, ms);
3021     }
3022   }
3023
3024   // called multiple times
3025   function multiple() {
3026     if (emitted) return;
3027     emitted = true;
3028     self.emit('error', new Error('done() called multiple times'));
3029   }
3030
3031   // finished
3032   function done(err) {
3033     if (self.timedOut) return;
3034     if (finished) return multiple();
3035     self.clearTimeout();
3036     self.duration = new Date - start;
3037     finished = true;
3038     fn(err);
3039   }
3040
3041   // for .resetTimeout()
3042   this.callback = done;
3043
3044   // async
3045   if (this.async) {
3046     try {
3047       this.fn.call(ctx, function(err){
3048         if (err instanceof Error) return done(err);
3049         if (null != err) return done(new Error('done() invoked with non-Error: ' + err));
3050         done();
3051       });
3052     } catch (err) {
3053       done(err);
3054     }
3055     return;
3056   }
3057   
3058   // sync
3059   try {
3060     if (!this.pending) this.fn.call(ctx);
3061     this.duration = new Date - start;
3062     fn();
3063   } catch (err) {
3064     fn(err);
3065   }
3066 };
3067
3068 }); // module: runnable.js
3069
3070 require.register("runner.js", function(module, exports, require){
3071
3072 /**
3073  * Module dependencies.
3074  */
3075
3076 var EventEmitter = require('browser/events').EventEmitter
3077   , debug = require('browser/debug')('runner')
3078   , Test = require('./test')
3079   , utils = require('./utils')
3080   , noop = function(){};
3081
3082 /**
3083  * Expose `Runner`.
3084  */
3085
3086 module.exports = Runner;
3087
3088 /**
3089  * Initialize a `Runner` for the given `suite`.
3090  *
3091  * Events:
3092  *
3093  *   - `start`  execution started
3094  *   - `end`  execution complete
3095  *   - `suite`  (suite) test suite execution started
3096  *   - `suite end`  (suite) all tests (and sub-suites) have finished
3097  *   - `test`  (test) test execution started
3098  *   - `test end`  (test) test completed
3099  *   - `hook`  (hook) hook execution started
3100  *   - `hook end`  (hook) hook complete
3101  *   - `pass`  (test) test passed
3102  *   - `fail`  (test, err) test failed
3103  *
3104  * @api public
3105  */
3106
3107 function Runner(suite) {
3108   var self = this;
3109   this._globals = [];
3110   this.suite = suite;
3111   this.total = suite.total();
3112   this.failures = 0;
3113   this.on('test end', function(test){ self.checkGlobals(test); });
3114   this.on('hook end', function(hook){ self.checkGlobals(hook); });
3115   this.grep(/.*/);
3116   this.globals(utils.keys(global).concat(['errno']));
3117 }
3118
3119 /**
3120  * Inherit from `EventEmitter.prototype`.
3121  */
3122
3123 Runner.prototype = new EventEmitter;
3124 Runner.prototype.constructor = Runner;
3125
3126
3127 /**
3128  * Run tests with full titles matching `re`. Updates runner.total
3129  * with number of tests matched.
3130  *
3131  * @param {RegExp} re
3132  * @return {Runner} for chaining
3133  * @api public
3134  */
3135
3136 Runner.prototype.grep = function(re){
3137   debug('grep %s', re);
3138   this._grep = re;
3139   this.total = this.grepTotal(this.suite);
3140   return this;
3141 };
3142
3143 /**
3144  * Returns the number of tests matching the grep search for the 
3145  * given suite.
3146  *
3147  * @param {Suite} suite
3148  * @return {Number}
3149  * @api public
3150  */
3151
3152 Runner.prototype.grepTotal = function(suite) {
3153   var self = this;
3154   var total = 0;
3155
3156   suite.eachTest(function(test){
3157     if (self._grep.test(test.fullTitle())) total++;
3158   });
3159
3160   return total;
3161 };
3162
3163 /**
3164  * Allow the given `arr` of globals.
3165  *
3166  * @param {Array} arr
3167  * @return {Runner} for chaining
3168  * @api public
3169  */
3170
3171 Runner.prototype.globals = function(arr){
3172   if (0 == arguments.length) return this._globals;
3173   debug('globals %j', arr);
3174   utils.forEach(arr, function(arr){
3175     this._globals.push(arr);
3176   }, this);
3177   return this;
3178 };
3179
3180 /**
3181  * Check for global variable leaks.
3182  *
3183  * @api private
3184  */
3185
3186 Runner.prototype.checkGlobals = function(test){
3187   if (this.ignoreLeaks) return;
3188
3189   var leaks = utils.filter(utils.keys(global), function(key){
3190     return !~utils.indexOf(this._globals, key) && (!global.navigator || 'onerror' !== key);
3191   }, this);
3192
3193   this._globals = this._globals.concat(leaks);
3194
3195   if (leaks.length > 1) {
3196     this.fail(test, new Error('global leaks detected: ' + leaks.join(', ') + ''));
3197   } else if (leaks.length) {
3198     this.fail(test, new Error('global leak detected: ' + leaks[0]));
3199   }
3200 };
3201
3202 /**
3203  * Fail the given `test`.
3204  *
3205  * @param {Test} test
3206  * @param {Error} err
3207  * @api private
3208  */
3209
3210 Runner.prototype.fail = function(test, err){
3211   ++this.failures;
3212   test.state = 'failed';
3213   if ('string' == typeof err) {
3214     err = new Error('the string "' + err + '" was thrown, throw an Error :)');
3215   }
3216   this.emit('fail', test, err);
3217 };
3218
3219 /**
3220  * Fail the given `hook` with `err`.
3221  *
3222  * Hook failures (currently) hard-end due
3223  * to that fact that a failing hook will
3224  * surely cause subsequent tests to fail,
3225  * causing jumbled reporting.
3226  *
3227  * @param {Hook} hook
3228  * @param {Error} err
3229  * @api private
3230  */
3231
3232 Runner.prototype.failHook = function(hook, err){
3233   this.fail(hook, err);
3234   this.emit('end');
3235 };
3236
3237 /**
3238  * Run hook `name` callbacks and then invoke `fn()`.
3239  *
3240  * @param {String} name
3241  * @param {Function} function
3242  * @api private
3243  */
3244
3245 Runner.prototype.hook = function(name, fn){
3246   var suite = this.suite
3247     , hooks = suite['_' + name]
3248     , ms = suite._timeout
3249     , self = this
3250     , timer;
3251
3252   function next(i) {
3253     var hook = hooks[i];
3254     if (!hook) return fn();
3255     self.currentRunnable = hook;
3256
3257     self.emit('hook', hook);
3258
3259     hook.on('error', function(err){
3260       self.failHook(hook, err);
3261     });
3262
3263     hook.run(function(err){
3264       hook.removeAllListeners('error');
3265       if (err) return self.failHook(hook, err);
3266       self.emit('hook end', hook);
3267       next(++i);
3268     });
3269   }
3270
3271   process.nextTick(function(){
3272     next(0);
3273   });
3274 };
3275
3276 /**
3277  * Run hook `name` for the given array of `suites`
3278  * in order, and callback `fn(err)`.
3279  *
3280  * @param {String} name
3281  * @param {Array} suites
3282  * @param {Function} fn
3283  * @api private
3284  */
3285
3286 Runner.prototype.hooks = function(name, suites, fn){
3287   var self = this
3288     , orig = this.suite;
3289
3290   function next(suite) {
3291     self.suite = suite;
3292
3293     if (!suite) {
3294       self.suite = orig;
3295       return fn();
3296     }
3297
3298     self.hook(name, function(err){
3299       if (err) {
3300         self.suite = orig;
3301         return fn(err);
3302       }
3303
3304       next(suites.pop());
3305     });
3306   }
3307
3308   next(suites.pop());
3309 };
3310
3311 /**
3312  * Run hooks from the top level down.
3313  *
3314  * @param {String} name
3315  * @param {Function} fn
3316  * @api private
3317  */
3318
3319 Runner.prototype.hookUp = function(name, fn){
3320   var suites = [this.suite].concat(this.parents()).reverse();
3321   this.hooks(name, suites, fn);
3322 };
3323
3324 /**
3325  * Run hooks from the bottom up.
3326  *
3327  * @param {String} name
3328  * @param {Function} fn
3329  * @api private
3330  */
3331
3332 Runner.prototype.hookDown = function(name, fn){
3333   var suites = [this.suite].concat(this.parents());
3334   this.hooks(name, suites, fn);
3335 };
3336
3337 /**
3338  * Return an array of parent Suites from
3339  * closest to furthest.
3340  *
3341  * @return {Array}
3342  * @api private
3343  */
3344
3345 Runner.prototype.parents = function(){
3346   var suite = this.suite
3347     , suites = [];
3348   while (suite = suite.parent) suites.push(suite);
3349   return suites;
3350 };
3351
3352 /**
3353  * Run the current test and callback `fn(err)`.
3354  *
3355  * @param {Function} fn
3356  * @api private
3357  */
3358
3359 Runner.prototype.runTest = function(fn){
3360   var test = this.test
3361     , self = this;
3362
3363   try {
3364     test.on('error', function(err){
3365       self.fail(test, err);
3366     });
3367     test.run(fn);
3368   } catch (err) {
3369     fn(err);
3370   }
3371 };
3372
3373 /**
3374  * Run tests in the given `suite` and invoke
3375  * the callback `fn()` when complete.
3376  *
3377  * @param {Suite} suite
3378  * @param {Function} fn
3379  * @api private
3380  */
3381
3382 Runner.prototype.runTests = function(suite, fn){
3383   var self = this
3384     , tests = suite.tests
3385     , test;
3386
3387   function next(err) {
3388     // if we bail after first err
3389     if (self.failures && suite._bail) return fn();
3390
3391     // next test
3392     test = tests.shift();
3393
3394     // all done
3395     if (!test) return fn();
3396
3397     // grep
3398     if (!self._grep.test(test.fullTitle())) return next();
3399
3400     // pending
3401     if (test.pending) {
3402       self.emit('pending', test);
3403       self.emit('test end', test);
3404       return next();
3405     }
3406
3407     // execute test and hook(s)
3408     self.emit('test', self.test = test);
3409     self.hookDown('beforeEach', function(){
3410       self.currentRunnable = self.test;
3411       self.runTest(function(err){
3412         test = self.test;
3413
3414         if (err) {
3415           self.fail(test, err);
3416           self.emit('test end', test);
3417           return self.hookUp('afterEach', next);
3418         }
3419
3420         test.state = 'passed';
3421         self.emit('pass', test);
3422         self.emit('test end', test);
3423         self.hookUp('afterEach', next);
3424       });
3425     });
3426   }
3427
3428   this.next = next;
3429   next();
3430 };
3431
3432 /**
3433  * Run the given `suite` and invoke the
3434  * callback `fn()` when complete.
3435  *
3436  * @param {Suite} suite
3437  * @param {Function} fn
3438  * @api private
3439  */
3440
3441 Runner.prototype.runSuite = function(suite, fn){
3442   var total = this.grepTotal(suite)
3443     , self = this
3444     , i = 0;
3445
3446   debug('run suite %s', suite.fullTitle());
3447
3448   if (!total) return fn();
3449
3450   this.emit('suite', this.suite = suite);
3451
3452   function next() {
3453     var curr = suite.suites[i++];
3454     if (!curr) return done();
3455     self.runSuite(curr, next);
3456   }
3457
3458   function done() {
3459     self.suite = suite;
3460     self.hook('afterAll', function(){
3461       self.emit('suite end', suite);
3462       fn();
3463     });
3464   }
3465
3466   this.hook('beforeAll', function(){
3467     self.runTests(suite, next);
3468   });
3469 };
3470
3471 /**
3472  * Handle uncaught exceptions.
3473  *
3474  * @param {Error} err
3475  * @api private
3476  */
3477
3478 Runner.prototype.uncaught = function(err){
3479   debug('uncaught exception');
3480   var runnable = this.currentRunnable;
3481   if ('failed' == runnable.state) return;
3482   runnable.clearTimeout();
3483   err.uncaught = true;
3484   this.fail(runnable, err);
3485
3486   // recover from test
3487   if ('test' == runnable.type) {
3488     this.emit('test end', runnable);
3489     this.hookUp('afterEach', this.next);
3490     return;
3491   }
3492
3493   // bail on hooks
3494   this.emit('end');
3495 };
3496
3497 /**
3498  * Run the root suite and invoke `fn(failures)`
3499  * on completion.
3500  *
3501  * @param {Function} fn
3502  * @return {Runner} for chaining
3503  * @api public
3504  */
3505
3506 Runner.prototype.run = function(fn){
3507   var self = this
3508     , fn = fn || function(){};
3509
3510   debug('start');
3511
3512   // callback
3513   this.on('end', function(){
3514     debug('end');
3515     process.removeListener('uncaughtException', this.uncaught);
3516     fn(self.failures);
3517   });
3518
3519   // run suites
3520   this.emit('start');
3521   this.runSuite(this.suite, function(){
3522     debug('finished running');
3523     self.emit('end');
3524   });
3525
3526   // uncaught exception
3527   process.on('uncaughtException', function(err){
3528     self.uncaught(err);
3529   });
3530
3531   return this;
3532 };
3533
3534 }); // module: runner.js
3535
3536 require.register("suite.js", function(module, exports, require){
3537
3538 /**
3539  * Module dependencies.
3540  */
3541
3542 var EventEmitter = require('browser/events').EventEmitter
3543   , debug = require('browser/debug')('suite')
3544   , utils = require('./utils')
3545   , Hook = require('./hook');
3546
3547 /**
3548  * Expose `Suite`.
3549  */
3550
3551 exports = module.exports = Suite;
3552
3553 /**
3554  * Create a new `Suite` with the given `title`
3555  * and parent `Suite`. When a suite with the
3556  * same title is already present, that suite
3557  * is returned to provide nicer reporter
3558  * and more flexible meta-testing.
3559  *
3560  * @param {Suite} parent
3561  * @param {String} title
3562  * @return {Suite}
3563  * @api public
3564  */
3565
3566 exports.create = function(parent, title){
3567   var suite = new Suite(title, parent.ctx);
3568   suite.parent = parent;
3569   title = suite.fullTitle();
3570   parent.addSuite(suite);
3571   return suite;
3572 };
3573
3574 /**
3575  * Initialize a new `Suite` with the given
3576  * `title` and `ctx`.
3577  *
3578  * @param {String} title
3579  * @param {Context} ctx
3580  * @api private
3581  */
3582
3583 function Suite(title, ctx) {
3584   this.title = title;
3585   this.ctx = ctx;
3586   this.suites = [];
3587   this.tests = [];
3588   this._beforeEach = [];
3589   this._beforeAll = [];
3590   this._afterEach = [];
3591   this._afterAll = [];
3592   this.root = !title;
3593   this._timeout = 2000;
3594   this._bail = false;
3595 }
3596
3597 /**
3598  * Inherit from `EventEmitter.prototype`.
3599  */
3600
3601 Suite.prototype = new EventEmitter;
3602 Suite.prototype.constructor = Suite;
3603
3604
3605 /**
3606  * Return a clone of this `Suite`.
3607  *
3608  * @return {Suite}
3609  * @api private
3610  */
3611
3612 Suite.prototype.clone = function(){
3613   var suite = new Suite(this.title);
3614   debug('clone');
3615   suite.ctx = this.ctx;
3616   suite.timeout(this.timeout());
3617   suite.bail(this.bail());
3618   return suite;
3619 };
3620
3621 /**
3622  * Set timeout `ms` or short-hand such as "2s".
3623  *
3624  * @param {Number|String} ms
3625  * @return {Suite|Number} for chaining
3626  * @api private
3627  */
3628
3629 Suite.prototype.timeout = function(ms){
3630   if (0 == arguments.length) return this._timeout;
3631   if (String(ms).match(/s$/)) ms = parseFloat(ms) * 1000;
3632   debug('timeout %d', ms);
3633   this._timeout = parseInt(ms, 10);
3634   return this;
3635 };
3636
3637 /**
3638  * Sets whether to bail after first error.
3639  *
3640  * @parma {Boolean} bail
3641  * @return {Suite|Number} for chaining
3642  * @api private
3643  */
3644
3645 Suite.prototype.bail = function(bail){
3646   if (0 == arguments.length) return this._bail;
3647   debug('bail %s', bail);
3648   this._bail = bail;
3649   return this;
3650 };
3651
3652 /**
3653  * Run `fn(test[, done])` before running tests.
3654  *
3655  * @param {Function} fn
3656  * @return {Suite} for chaining
3657  * @api private
3658  */
3659
3660 Suite.prototype.beforeAll = function(fn){
3661   var hook = new Hook('"before all" hook', fn);
3662   hook.parent = this;
3663   hook.timeout(this.timeout());
3664   hook.ctx = this.ctx;
3665   this._beforeAll.push(hook);
3666   this.emit('beforeAll', hook);
3667   return this;
3668 };
3669
3670 /**
3671  * Run `fn(test[, done])` after running tests.
3672  *
3673  * @param {Function} fn
3674  * @return {Suite} for chaining
3675  * @api private
3676  */
3677
3678 Suite.prototype.afterAll = function(fn){
3679   var hook = new Hook('"after all" hook', fn);
3680   hook.parent = this;
3681   hook.timeout(this.timeout());
3682   hook.ctx = this.ctx;
3683   this._afterAll.push(hook);
3684   this.emit('afterAll', hook);
3685   return this;
3686 };
3687
3688 /**
3689  * Run `fn(test[, done])` before each test case.
3690  *
3691  * @param {Function} fn
3692  * @return {Suite} for chaining
3693  * @api private
3694  */
3695
3696 Suite.prototype.beforeEach = function(fn){
3697   var hook = new Hook('"before each" hook', fn);
3698   hook.parent = this;
3699   hook.timeout(this.timeout());
3700   hook.ctx = this.ctx;
3701   this._beforeEach.push(hook);
3702   this.emit('beforeEach', hook);
3703   return this;
3704 };
3705
3706 /**
3707  * Run `fn(test[, done])` after each test case.
3708  *
3709  * @param {Function} fn
3710  * @return {Suite} for chaining
3711  * @api private
3712  */
3713
3714 Suite.prototype.afterEach = function(fn){
3715   var hook = new Hook('"after each" hook', fn);
3716   hook.parent = this;
3717   hook.timeout(this.timeout());
3718   hook.ctx = this.ctx;
3719   this._afterEach.push(hook);
3720   this.emit('afterEach', hook);
3721   return this;
3722 };
3723
3724 /**
3725  * Add a test `suite`.
3726  *
3727  * @param {Suite} suite
3728  * @return {Suite} for chaining
3729  * @api private
3730  */
3731
3732 Suite.prototype.addSuite = function(suite){
3733   suite.parent = this;
3734   suite.timeout(this.timeout());
3735   suite.bail(this.bail());
3736   this.suites.push(suite);
3737   this.emit('suite', suite);
3738   return this;
3739 };
3740
3741 /**
3742  * Add a `test` to this suite.
3743  *
3744  * @param {Test} test
3745  * @return {Suite} for chaining
3746  * @api private
3747  */
3748
3749 Suite.prototype.addTest = function(test){
3750   test.parent = this;
3751   test.timeout(this.timeout());
3752   test.ctx = this.ctx;
3753   this.tests.push(test);
3754   this.emit('test', test);
3755   return this;
3756 };
3757
3758 /**
3759  * Return the full title generated by recursively
3760  * concatenating the parent's full title.
3761  *
3762  * @return {String}
3763  * @api public
3764  */
3765
3766 Suite.prototype.fullTitle = function(){
3767   if (this.parent) {
3768     var full = this.parent.fullTitle();
3769     if (full) return full + ' ' + this.title;
3770   }
3771   return this.title;
3772 };
3773
3774 /**
3775  * Return the total number of tests.
3776  *
3777  * @return {Number}
3778  * @api public
3779  */
3780
3781 Suite.prototype.total = function(){
3782   return utils.reduce(this.suites, function(sum, suite){
3783     return sum + suite.total();
3784   }, 0) + this.tests.length;
3785 };
3786
3787 /**
3788  * Iterates through each suite recursively to find
3789  * all tests. Applies a function in the format
3790  * `fn(test)`.
3791  *
3792  * @param {Function} fn
3793  * @return {Suite}
3794  * @api private
3795  */
3796
3797 Suite.prototype.eachTest = function(fn){
3798   utils.forEach(this.tests, fn);
3799   utils.forEach(this.suites, function(suite){
3800     suite.eachTest(fn);
3801   });
3802   return this;
3803 };
3804
3805 }); // module: suite.js
3806
3807 require.register("test.js", function(module, exports, require){
3808
3809 /**
3810  * Module dependencies.
3811  */
3812
3813 var Runnable = require('./runnable');
3814
3815 /**
3816  * Expose `Test`.
3817  */
3818
3819 module.exports = Test;
3820
3821 /**
3822  * Initialize a new `Test` with the given `title` and callback `fn`.
3823  *
3824  * @param {String} title
3825  * @param {Function} fn
3826  * @api private
3827  */
3828
3829 function Test(title, fn) {
3830   Runnable.call(this, title, fn);
3831   this.pending = !fn;
3832   this.type = 'test';
3833 }
3834
3835 /**
3836  * Inherit from `Runnable.prototype`.
3837  */
3838
3839 Test.prototype = new Runnable;
3840 Test.prototype.constructor = Test;
3841
3842
3843 /**
3844  * Inspect the context void of private properties.
3845  *
3846  * @return {String}
3847  * @api private
3848  */
3849
3850 Test.prototype.inspect = function(){
3851   return JSON.stringify(this, function(key, val){
3852     return '_' == key[0]
3853       ? undefined
3854       : 'parent' == key
3855         ? '#<Suite>'
3856         : val;
3857   }, 2);
3858 };
3859 }); // module: test.js
3860
3861 require.register("utils.js", function(module, exports, require){
3862
3863 /**
3864  * Module dependencies.
3865  */
3866
3867 var fs = require('browser/fs')
3868   , path = require('browser/path')
3869   , join = path.join
3870   , debug = require('browser/debug')('watch');
3871
3872 /**
3873  * Ignored directories.
3874  */
3875
3876 var ignore = ['node_modules', '.git'];
3877
3878 /**
3879  * Escape special characters in the given string of html.
3880  *
3881  * @param  {String} html
3882  * @return {String}
3883  * @api private
3884  */
3885
3886 exports.escape = function(html) {
3887   return String(html)
3888     .replace(/&/g, '&amp;')
3889     .replace(/"/g, '&quot;')
3890     .replace(/</g, '&lt;')
3891     .replace(/>/g, '&gt;');
3892 };
3893
3894 /**
3895  * Array#forEach (<=IE8)
3896  *
3897  * @param {Array} array
3898  * @param {Function} fn
3899  * @param {Object} scope
3900  * @api private
3901  */
3902
3903 exports.forEach = function(arr, fn, scope) {
3904   for (var i = 0, l = arr.length; i < l; i++)
3905     fn.call(scope, arr[i], i);
3906 };
3907
3908 /**
3909  * Array#indexOf (<=IE8)
3910  *
3911  * @parma {Array} arr
3912  * @param {Object} obj to find index of
3913  * @param {Number} start
3914  * @api private
3915  */
3916
3917 exports.indexOf = function (arr, obj, start) {
3918   for (var i = start || 0, l = arr.length; i < l; i++) {
3919     if (arr[i] === obj)
3920       return i;
3921   }
3922   return -1;
3923 };
3924
3925 /**
3926  * Array#reduce (<=IE8)
3927  * 
3928  * @param {Array} array
3929  * @param {Function} fn
3930  * @param {Object} initial value
3931  * @param {Object} scope
3932  * @api private
3933  */
3934
3935 exports.reduce = function(arr, fn, val, scope) {
3936   var rval = val;
3937
3938   for (var i = 0, l = arr.length; i < l; i++) {
3939     rval = fn.call(scope, rval, arr[i], i, arr);
3940   }
3941
3942   return rval;
3943 };
3944
3945 /**
3946  * Array#filter (<=IE8)
3947  *
3948  * @param {Array} array
3949  * @param {Function} fn
3950  * @param {Object} scope
3951  * @api private
3952  */
3953
3954 exports.filter = function(arr, fn, scope) {
3955   var ret = [];
3956
3957   for (var i = 0, l = arr.length; i < l; i++) {
3958     var val = arr[i];
3959     if (fn.call(scope, val, i, arr))
3960       ret.push(val);
3961   }
3962
3963   return ret;
3964 };
3965
3966 /**
3967  * Object.keys (<=IE8)
3968  *
3969  * @param {Object} obj
3970  * @return {Array} keys
3971  * @api private
3972  */
3973
3974 exports.keys = Object.keys || function(obj) {
3975   var keys = []
3976     , has = Object.prototype.hasOwnProperty // for `window` on <=IE8
3977
3978   for (var key in obj) {
3979     if (has.call(obj, key)) {
3980       keys.push(key);
3981     }
3982   }
3983
3984   return keys;
3985 };
3986
3987 /**
3988  * Watch the given `files` for changes
3989  * and invoke `fn(file)` on modification.
3990  *
3991  * @param {Array} files
3992  * @param {Function} fn
3993  * @api private
3994  */
3995
3996 exports.watch = function(files, fn){
3997   var options = { interval: 100 };
3998   files.forEach(function(file){
3999     debug('file %s', file);
4000     fs.watchFile(file, options, function(curr, prev){
4001       if (prev.mtime < curr.mtime) fn(file);
4002     });
4003   });
4004 };
4005
4006 /**
4007  * Ignored files.
4008  */
4009
4010 function ignored(path){
4011   return !~ignore.indexOf(path);
4012 }
4013
4014 /**
4015  * Lookup files in the given `dir`.
4016  *
4017  * @return {Array}
4018  * @api private
4019  */
4020
4021 exports.files = function(dir, ret){
4022   ret = ret || [];
4023
4024   fs.readdirSync(dir)
4025   .filter(ignored)
4026   .forEach(function(path){
4027     path = join(dir, path);
4028     if (fs.statSync(path).isDirectory()) {
4029       exports.files(path, ret);
4030     } else if (path.match(/\.(js|coffee)$/)) {
4031       ret.push(path);
4032     }
4033   });
4034
4035   return ret;
4036 };
4037
4038 /**
4039  * Compute a slug from the given `str`.
4040  *
4041  * @param {String} str
4042  * @return {String}
4043  */
4044
4045 exports.slug = function(str){
4046   return str
4047     .toLowerCase()
4048     .replace(/ +/g, '-')
4049     .replace(/[^-\w]/g, '');
4050 };
4051 }); // module: utils.js
4052 /**
4053  * Node shims.
4054  *
4055  * These are meant only to allow
4056  * mocha.js to run untouched, not
4057  * to allow running node code in
4058  * the browser.
4059  */
4060
4061 process = {};
4062 process.exit = function(status){};
4063 process.stdout = {};
4064 global = window;
4065
4066 /**
4067  * next tick implementation.
4068  */
4069
4070 process.nextTick = (function(){
4071   // postMessage behaves badly on IE8
4072   if (window.ActiveXObject || !window.postMessage) {
4073     return function(fn){ fn() };
4074   }
4075
4076   // based on setZeroTimeout by David Baron
4077   // - http://dbaron.org/log/20100309-faster-timeouts
4078   var timeouts = []
4079     , name = 'mocha-zero-timeout'
4080
4081   window.addEventListener('message', function(e){
4082     if (e.source == window && e.data == name) {
4083       if (e.stopPropagation) e.stopPropagation();
4084       if (timeouts.length) timeouts.shift()();
4085     }
4086   }, true);
4087
4088   return function(fn){
4089     timeouts.push(fn);
4090     window.postMessage(name, '*');
4091   }
4092 })();
4093
4094 /**
4095  * Remove uncaughtException listener.
4096  */
4097
4098 process.removeListener = function(e){
4099   if ('uncaughtException' == e) {
4100     window.onerror = null;
4101   }
4102 };
4103
4104 /**
4105  * Implements uncaughtException listener.
4106  */
4107
4108 process.on = function(e, fn){
4109   if ('uncaughtException' == e) {
4110     window.onerror = fn;
4111   }
4112 };
4113
4114 /**
4115  * Expose mocha.
4116  */
4117
4118 window.mocha = require('mocha');
4119
4120 // boot
4121 ;(function(){
4122   var suite = new mocha.Suite('', new mocha.Context)
4123     , utils = mocha.utils
4124     , options = {}
4125
4126   /**
4127    * Highlight the given string of `js`.
4128    */
4129
4130   function highlight(js) {
4131     return js
4132       .replace(/</g, '&lt;')
4133       .replace(/>/g, '&gt;')
4134       .replace(/\/\/(.*)/gm, '<span class="comment">//$1</span>')
4135       .replace(/('.*?')/gm, '<span class="string">$1</span>')
4136       .replace(/(\d+\.\d+)/gm, '<span class="number">$1</span>')
4137       .replace(/(\d+)/gm, '<span class="number">$1</span>')
4138       .replace(/\bnew *(\w+)/gm, '<span class="keyword">new</span> <span class="init">$1</span>')
4139       .replace(/\b(function|new|throw|return|var|if|else)\b/gm, '<span class="keyword">$1</span>')
4140   }
4141
4142   /**
4143    * Highlight code contents.
4144    */
4145
4146   function highlightCode() {
4147     var code = document.getElementsByTagName('code');
4148     for (var i = 0, len = code.length; i < len; ++i) {
4149       code[i].innerHTML = highlight(code[i].innerHTML);
4150     }
4151   }
4152
4153   /**
4154    * Parse the given `qs`.
4155    */
4156
4157   function parse(qs) {
4158     return utils.reduce(qs.replace('?', '').split('&'), function(obj, pair){
4159         var i = pair.indexOf('=')
4160           , key = pair.slice(0, i)
4161           , val = pair.slice(++i);
4162
4163         obj[key] = decodeURIComponent(val);
4164         return obj;
4165       }, {});
4166   }
4167
4168   /**
4169    * Setup mocha with the given setting options.
4170    */
4171
4172   mocha.setup = function(opts){
4173     if ('string' === typeof opts) options.ui = opts;
4174     else options = opts;
4175
4176     ui = mocha.interfaces[options.ui];
4177     if (!ui) throw new Error('invalid mocha interface "' + ui + '"');
4178     if (options.timeout) suite.timeout(options.timeout);
4179     ui(suite);
4180     suite.emit('pre-require', window);
4181   };
4182
4183   /**
4184    * Run mocha, returning the Runner.
4185    */
4186
4187   mocha.run = function(fn){
4188     suite.emit('run');
4189     var runner = new mocha.Runner(suite);
4190     var Reporter = options.reporter || mocha.reporters.HTML;
4191     var reporter = new Reporter(runner);
4192     var query = parse(window.location.search || "");
4193     if (query.grep) runner.grep(new RegExp(query.grep));
4194     if (options.ignoreLeaks) runner.ignoreLeaks = true;
4195     if (options.globals) runner.globals(options.globals);
4196     runner.globals(['location']);
4197     runner.on('end', highlightCode);
4198     return runner.run(fn);
4199   };
4200 })();
4201 })();