UNPKG

114 kBJavaScriptView Raw
1/*!
2 * should - test framework agnostic BDD-style assertions
3 * @version v8.2.1
4 * @author TJ Holowaychuk <tj@vision-media.ca> and contributors
5 * @link https://github.com/shouldjs/should.js
6 * @license MIT
7 */
8(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s})({1:[function(require,module,exports){
9window.Should = require('./index');
10
11Object.defineProperty(window, 'should', {
12 enumerable: false,
13 configurable: true,
14 value: window.Should
15});
16
17},{"./index":2}],2:[function(require,module,exports){
18var should = require('./lib/should');
19
20var defaultProto = Object.prototype;
21var defaultProperty = 'should';
22
23//Expose api via `Object#should`.
24try {
25 var prevShould = should.extend(defaultProperty, defaultProto);
26 should._prevShould = prevShould;
27} catch(e) {
28 //ignore errors
29}
30
31module.exports = should;
32
33},{"./lib/should":19}],3:[function(require,module,exports){
34/*
35 * Should
36 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
37 * MIT Licensed
38 */
39
40var util = require('./util');
41
42/**
43 * should AssertionError
44 * @param {Object} options
45 * @constructor
46 * @memberOf should
47 * @static
48 */
49var AssertionError = function AssertionError(options) {
50 util.merge(this, options);
51
52 if(!options.message) {
53 Object.defineProperty(this, 'message', {
54 get: function() {
55 if(!this._message) {
56 this._message = this.generateMessage();
57 this.generatedMessage = true;
58 }
59 return this._message;
60 },
61 configurable: true,
62 enumerable: false
63 }
64 );
65 }
66
67 if(Error.captureStackTrace) {
68 Error.captureStackTrace(this, this.stackStartFunction);
69 } else {
70 // non v8 browsers so we can have a stacktrace
71 var err = new Error();
72 if(err.stack) {
73 var out = err.stack;
74
75 if(this.stackStartFunction) {
76 // try to strip useless frames
77 var fn_name = util.functionName(this.stackStartFunction);
78 var idx = out.indexOf('\n' + fn_name);
79 if(idx >= 0) {
80 // once we have located the function frame
81 // we need to strip out everything before it (and its line)
82 var next_line = out.indexOf('\n', idx + 1);
83 out = out.substring(next_line + 1);
84 }
85 }
86
87 this.stack = out;
88 }
89 }
90};
91
92
93var indent = ' ';
94function prependIndent(line) {
95 return indent + line;
96}
97
98function indentLines(text) {
99 return text.split('\n').map(prependIndent).join('\n');
100}
101
102
103// assert.AssertionError instanceof Error
104AssertionError.prototype = Object.create(Error.prototype, {
105 name: {
106 value: 'AssertionError'
107 },
108
109 generateMessage: {
110 value: function() {
111 if(!this.operator && this.previous) {
112 return this.previous.message;
113 }
114 var actual = util.format(this.actual);
115 var expected = 'expected' in this ? ' ' + util.format(this.expected) : '';
116 var details = 'details' in this && this.details ? ' (' + this.details + ')' : '';
117
118 var previous = this.previous ? '\n' + indentLines(this.previous.message) : '';
119
120 return 'expected ' + actual + (this.negate ? ' not ' : ' ') + this.operator + expected + details + previous;
121 }
122 }
123});
124
125module.exports = AssertionError;
126
127},{"./util":20}],4:[function(require,module,exports){
128/*
129 * Should
130 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
131 * MIT Licensed
132 */
133
134var AssertionError = require('./assertion-error');
135
136/**
137 * should Assertion
138 * @param {*} obj Given object for assertion
139 * @constructor
140 * @memberOf should
141 * @static
142 */
143function Assertion(obj) {
144 this.obj = obj;
145
146 this.anyOne = false;
147 this.negate = false;
148
149 this.params = {actual: obj};
150}
151
152Assertion.prototype = {
153 constructor: Assertion,
154
155 /**
156 * Base method for assertions.
157 *
158 * Before calling this method need to fill Assertion#params object. This method usually called from other assertion methods.
159 * `Assertion#params` can contain such properties:
160 * * `operator` - required string containing description of this assertion
161 * * `obj` - optional replacement for this.obj, it usefull if you prepare more clear object then given
162 * * `message` - if this property filled with string any others will be ignored and this one used as assertion message
163 * * `expected` - any object used when you need to assert relation between given object and expected. Like given == expected (== is a relation)
164 * * `details` - additional string with details to generated message
165 *
166 * @memberOf Assertion
167 * @category assertion
168 * @param {*} expr Any expression that will be used as a condition for asserting.
169 * @example
170 *
171 * var a = new should.Assertion(42);
172 *
173 * a.params = {
174 * operator: 'to be magic number',
175 * }
176 *
177 * a.assert(false);
178 * //throws AssertionError: expected 42 to be magic number
179 */
180 assert: function(expr) {
181 if(expr) {
182 return this;
183 }
184
185 var params = this.params;
186
187 if('obj' in params && !('actual' in params)) {
188 params.actual = params.obj;
189 } else if(!('obj' in params) && !('actual' in params)) {
190 params.actual = this.obj;
191 }
192
193 params.stackStartFunction = params.stackStartFunction || this.assert;
194 params.negate = this.negate;
195
196 params.assertion = this;
197
198 throw new AssertionError(params);
199 },
200
201 /**
202 * Shortcut for `Assertion#assert(false)`.
203 *
204 * @memberOf Assertion
205 * @category assertion
206 * @example
207 *
208 * var a = new should.Assertion(42);
209 *
210 * a.params = {
211 * operator: 'to be magic number',
212 * }
213 *
214 * a.fail();
215 * //throws AssertionError: expected 42 to be magic number
216 */
217 fail: function() {
218 return this.assert(false);
219 }
220};
221
222
223
224/**
225 * Assertion used to delegate calls of Assertion methods inside of Promise.
226 * It has almost all methods of Assertion.prototype
227 *
228 * @param {Promise} obj
229 */
230function PromisedAssertion(/* obj */) {
231 Assertion.apply(this, arguments);
232}
233
234/**
235 * Make PromisedAssertion to look like promise. Delegate resolve and reject to given promise.
236 *
237 * @private
238 * @returns {Promise}
239 */
240PromisedAssertion.prototype.then = function(resolve, reject) {
241 return this.obj.then(resolve, reject);
242};
243
244/**
245 * Way to extend Assertion function. It uses some logic
246 * to define only positive assertions and itself rule with negative assertion.
247 *
248 * All actions happen in subcontext and this method take care about negation.
249 * Potentially we can add some more modifiers that does not depends from state of assertion.
250 *
251 * @memberOf Assertion
252 * @static
253 * @param {String} name Name of assertion. It will be used for defining method or getter on Assertion.prototype
254 * @param {Function} func Function that will be called on executing assertion
255 * @example
256 *
257 * Assertion.add('asset', function() {
258 * this.params = { operator: 'to be asset' }
259 *
260 * this.obj.should.have.property('id').which.is.a.Number()
261 * this.obj.should.have.property('path')
262 * })
263 */
264Assertion.add = function(name, func) {
265 Object.defineProperty(Assertion.prototype, name, {
266 enumerable: true,
267 configurable: true,
268 value: function() {
269 var context = new Assertion(this.obj, this, name);
270 context.anyOne = this.anyOne;
271
272 try {
273 func.apply(context, arguments);
274 } catch (e) {
275 // check for fail
276 if (e instanceof AssertionError) {
277 // negative fail
278 if (this.negate) {
279 this.obj = context.obj;
280 this.negate = false;
281 return this;
282 }
283
284 if (context !== e.assertion) {
285 context.params.previous = e;
286 }
287
288 // positive fail
289 context.negate = false;
290 context.fail();
291 }
292 // throw if it is another exception
293 throw e;
294 }
295
296 // negative pass
297 if (this.negate) {
298 context.negate = true; // because .fail will set negate
299 context.params.details = 'false negative fail';
300 context.fail();
301 }
302
303 // positive pass
304 if (!this.params.operator) {
305 this.params = context.params; // shortcut
306 }
307 this.obj = context.obj;
308 this.negate = false;
309 return this;
310 }
311 });
312
313 Object.defineProperty(PromisedAssertion.prototype, name, {
314 enumerable: true,
315 configurable: true,
316 value: function() {
317 var args = arguments;
318 this.obj = this.obj.then(function(a) {
319 return a[name].apply(a, args);
320 });
321
322 return this;
323 }
324 });
325};
326
327/**
328 * Add chaining getter to Assertion like .a, .which etc
329 *
330 * @memberOf Assertion
331 * @static
332 * @param {string} name name of getter
333 * @param {function} [onCall] optional function to call
334 */
335Assertion.addChain = function(name, onCall) {
336 onCall = onCall || function() {};
337 Object.defineProperty(Assertion.prototype, name, {
338 get: function() {
339 onCall.call(this);
340 return this;
341 },
342 enumerable: true
343 });
344
345 Object.defineProperty(PromisedAssertion.prototype, name, {
346 enumerable: true,
347 configurable: true,
348 get: function() {
349 this.obj = this.obj.then(function(a) {
350 return a[name];
351 });
352
353 return this;
354 }
355 });
356};
357
358/**
359 * Create alias for some `Assertion` property
360 *
361 * @memberOf Assertion
362 * @static
363 * @param {String} from Name of to map
364 * @param {String} to Name of alias
365 * @example
366 *
367 * Assertion.alias('true', 'True')
368 */
369Assertion.alias = function(from, to) {
370 var desc = Object.getOwnPropertyDescriptor(Assertion.prototype, from);
371 if (!desc) throw new Error('Alias ' + from + ' -> ' + to + ' could not be created as ' + from + ' not defined');
372 Object.defineProperty(Assertion.prototype, to, desc);
373
374 var desc2 = Object.getOwnPropertyDescriptor(PromisedAssertion.prototype, from);
375 if (desc2) {
376 Object.defineProperty(PromisedAssertion.prototype, to, desc2);
377 }
378};
379/**
380 * Negation modifier. Current assertion chain become negated. Each call invert negation on current assertion.
381 *
382 * @name not
383 * @property
384 * @memberOf Assertion
385 * @category assertion
386 */
387Assertion.addChain('not', function() {
388 this.negate = !this.negate;
389});
390
391/**
392 * Any modifier - it affect on execution of sequenced assertion to do not `check all`, but `check any of`.
393 *
394 * @name any
395 * @property
396 * @memberOf Assertion
397 * @category assertion
398 */
399Assertion.addChain('any', function() {
400 this.anyOne = true;
401});
402
403module.exports = Assertion;
404module.exports.PromisedAssertion = PromisedAssertion;
405
406},{"./assertion-error":3}],5:[function(require,module,exports){
407/*
408 * Should
409 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
410 * MIT Licensed
411 */
412
413var Formatter = require('should-format').Formatter;
414
415var config = {
416 checkProtoEql: false,
417
418 getFormatter: function(opts) {
419 return new Formatter(opts || config);
420 }
421};
422
423module.exports = config;
424
425},{"should-format":23}],6:[function(require,module,exports){
426// implement assert interface using already written peaces of should.js
427
428// http://wiki.commonjs.org/wiki/Unit_Testing/1.0
429//
430// THIS IS NOT TESTED NOR LIKELY TO WORK OUTSIDE V8!
431//
432// Originally from narwhal.js (http://narwhaljs.org)
433// Copyright (c) 2009 Thomas Robinson <280north.com>
434//
435// Permission is hereby granted, free of charge, to any person obtaining a copy
436// of this software and associated documentation files (the 'Software'), to
437// deal in the Software without restriction, including without limitation the
438// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
439// sell copies of the Software, and to permit persons to whom the Software is
440// furnished to do so, subject to the following conditions:
441//
442// The above copyright notice and this permission notice shall be included in
443// all copies or substantial portions of the Software.
444//
445// THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
446// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
447// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
448// AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
449// ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
450// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
451
452// when used in node, this will actually load the util module we depend on
453// versus loading the builtin util module as happens otherwise
454// this is a bug in node module loading as far as I am concerned
455var Assertion = require('./../assertion');
456
457var _deepEqual = require('should-equal');
458
459var pSlice = Array.prototype.slice;
460
461// 1. The assert module provides functions that throw
462// AssertionError's when particular conditions are not met. The
463// assert module must conform to the following interface.
464
465var assert = module.exports = ok;
466
467// 3. All of the following functions must throw an AssertionError
468// when a corresponding condition is not met, with a message that
469// may be undefined if not provided. All assertion methods provide
470// both the actual and expected values to the assertion error for
471// display purposes.
472/**
473 * Node.js standard [`assert.fail`](http://nodejs.org/api/assert.html#assert_assert_fail_actual_expected_message_operator).
474 * @static
475 * @memberOf should
476 * @category assertion assert
477 * @param {*} actual Actual object
478 * @param {*} expected Expected object
479 * @param {string} message Message for assertion
480 * @param {string} operator Operator text
481 */
482function fail(actual, expected, message, operator, stackStartFunction) {
483 var a = new Assertion(actual);
484 a.params = {
485 operator: operator,
486 expected: expected,
487 message: message,
488 stackStartFunction: stackStartFunction || fail
489 };
490
491 a.fail();
492}
493
494// EXTENSION! allows for well behaved errors defined elsewhere.
495assert.fail = fail;
496
497// 4. Pure assertion tests whether a value is truthy, as determined
498// by !!guard.
499// assert.ok(guard, message_opt);
500// This statement is equivalent to assert.equal(true, !!guard,
501// message_opt);. To test strictly for the value true, use
502// assert.strictEqual(true, guard, message_opt);.
503/**
504 * Node.js standard [`assert.ok`](http://nodejs.org/api/assert.html#assert_assert_value_message_assert_ok_value_message).
505 * @static
506 * @memberOf should
507 * @category assertion assert
508 * @param {*} value
509 * @param {string} [message]
510 */
511function ok(value, message) {
512 if(!value) fail(value, true, message, '==', assert.ok);
513}
514assert.ok = ok;
515
516// 5. The equality assertion tests shallow, coercive equality with
517// ==.
518// assert.equal(actual, expected, message_opt);
519
520/**
521 * Node.js standard [`assert.equal`](http://nodejs.org/api/assert.html#assert_assert_equal_actual_expected_message).
522 * @static
523 * @memberOf should
524 * @category assertion assert
525 * @param {*} actual
526 * @param {*} expected
527 * @param {string} [message]
528 */
529assert.equal = function equal(actual, expected, message) {
530 if(actual != expected) fail(actual, expected, message, '==', assert.equal);
531};
532
533// 6. The non-equality assertion tests for whether two objects are not equal
534// with != assert.notEqual(actual, expected, message_opt);
535/**
536 * Node.js standard [`assert.notEqual`](http://nodejs.org/api/assert.html#assert_assert_notequal_actual_expected_message).
537 * @static
538 * @memberOf should
539 * @category assertion assert
540 * @param {*} actual
541 * @param {*} expected
542 * @param {string} [message]
543 */
544assert.notEqual = function notEqual(actual, expected, message) {
545 if(actual == expected) {
546 fail(actual, expected, message, '!=', assert.notEqual);
547 }
548};
549
550// 7. The equivalence assertion tests a deep equality relation.
551// assert.deepEqual(actual, expected, message_opt);
552/**
553 * Node.js standard [`assert.deepEqual`](http://nodejs.org/api/assert.html#assert_assert_deepequal_actual_expected_message).
554 * But uses should.js .eql implementation instead of Node.js own deepEqual.
555 *
556 * @static
557 * @memberOf should
558 * @category assertion assert
559 * @param {*} actual
560 * @param {*} expected
561 * @param {string} [message]
562 */
563assert.deepEqual = function deepEqual(actual, expected, message) {
564 if(!_deepEqual(actual, expected).result) {
565 fail(actual, expected, message, 'deepEqual', assert.deepEqual);
566 }
567};
568
569
570// 8. The non-equivalence assertion tests for any deep inequality.
571// assert.notDeepEqual(actual, expected, message_opt);
572/**
573 * Node.js standard [`assert.notDeepEqual`](http://nodejs.org/api/assert.html#assert_assert_notdeepequal_actual_expected_message).
574 * But uses should.js .eql implementation instead of Node.js own deepEqual.
575 *
576 * @static
577 * @memberOf should
578 * @category assertion assert
579 * @param {*} actual
580 * @param {*} expected
581 * @param {string} [message]
582 */
583assert.notDeepEqual = function notDeepEqual(actual, expected, message) {
584 if(_deepEqual(actual, expected).result) {
585 fail(actual, expected, message, 'notDeepEqual', assert.notDeepEqual);
586 }
587};
588
589// 9. The strict equality assertion tests strict equality, as determined by ===.
590// assert.strictEqual(actual, expected, message_opt);
591/**
592 * Node.js standard [`assert.strictEqual`](http://nodejs.org/api/assert.html#assert_assert_strictequal_actual_expected_message).
593 * @static
594 * @memberOf should
595 * @category assertion assert
596 * @param {*} actual
597 * @param {*} expected
598 * @param {string} [message]
599 */
600assert.strictEqual = function strictEqual(actual, expected, message) {
601 if(actual !== expected) {
602 fail(actual, expected, message, '===', assert.strictEqual);
603 }
604};
605
606// 10. The strict non-equality assertion tests for strict inequality, as
607// determined by !==. assert.notStrictEqual(actual, expected, message_opt);
608/**
609 * Node.js standard [`assert.notStrictEqual`](http://nodejs.org/api/assert.html#assert_assert_notstrictequal_actual_expected_message).
610 * @static
611 * @memberOf should
612 * @category assertion assert
613 * @param {*} actual
614 * @param {*} expected
615 * @param {string} [message]
616 */
617assert.notStrictEqual = function notStrictEqual(actual, expected, message) {
618 if(actual === expected) {
619 fail(actual, expected, message, '!==', assert.notStrictEqual);
620 }
621};
622
623function expectedException(actual, expected) {
624 if(!actual || !expected) {
625 return false;
626 }
627
628 if(Object.prototype.toString.call(expected) == '[object RegExp]') {
629 return expected.test(actual);
630 } else if(actual instanceof expected) {
631 return true;
632 } else if(expected.call({}, actual) === true) {
633 return true;
634 }
635
636 return false;
637}
638
639function _throws(shouldThrow, block, expected, message) {
640 var actual;
641
642 if(typeof expected == 'string') {
643 message = expected;
644 expected = null;
645 }
646
647 try {
648 block();
649 } catch(e) {
650 actual = e;
651 }
652
653 message = (expected && expected.name ? ' (' + expected.name + ')' : '.') +
654 (message ? ' ' + message : '.');
655
656 if(shouldThrow && !actual) {
657 fail(actual, expected, 'Missing expected exception' + message);
658 }
659
660 if(!shouldThrow && expectedException(actual, expected)) {
661 fail(actual, expected, 'Got unwanted exception' + message);
662 }
663
664 if((shouldThrow && actual && expected && !expectedException(actual, expected)) || (!shouldThrow && actual)) {
665 throw actual;
666 }
667}
668
669// 11. Expected to throw an error:
670// assert.throws(block, Error_opt, message_opt);
671/**
672 * Node.js standard [`assert.throws`](http://nodejs.org/api/assert.html#assert_assert_throws_block_error_message).
673 * @static
674 * @memberOf should
675 * @category assertion assert
676 * @param {Function} block
677 * @param {Function} [error]
678 * @param {String} [message]
679 */
680assert.throws = function(block, /*optional*/error, /*optional*/message) {
681 _throws.apply(this, [true].concat(pSlice.call(arguments)));
682};
683
684// EXTENSION! This is annoying to write outside this module.
685/**
686 * Node.js standard [`assert.doesNotThrow`](http://nodejs.org/api/assert.html#assert_assert_doesnotthrow_block_message).
687 * @static
688 * @memberOf should
689 * @category assertion assert
690 * @param {Function} block
691 * @param {String} [message]
692 */
693assert.doesNotThrow = function(block, /*optional*/message) {
694 _throws.apply(this, [false].concat(pSlice.call(arguments)));
695};
696
697/**
698 * Node.js standard [`assert.ifError`](http://nodejs.org/api/assert.html#assert_assert_iferror_value).
699 * @static
700 * @memberOf should
701 * @category assertion assert
702 * @param {Error} err
703 */
704assert.ifError = function(err) {
705 if(err) {
706 throw err;
707 }
708};
709
710},{"./../assertion":4,"should-equal":22}],7:[function(require,module,exports){
711/*
712 * Should
713 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
714 * MIT Licensed
715 */
716
717var util = require('../util')
718 , assert = require('./_assert')
719 , AssertionError = require('../assertion-error');
720
721module.exports = function(should) {
722 var i = should.format;
723
724 /*
725 * Expose assert to should
726 *
727 * This allows you to do things like below
728 * without require()ing the assert module.
729 *
730 * should.equal(foo.bar, undefined);
731 *
732 */
733 util.merge(should, assert);
734
735 /**
736 * Assert _obj_ exists, with optional message.
737 *
738 * @static
739 * @memberOf should
740 * @category assertion assert
741 * @alias should.exists
742 * @param {*} obj
743 * @param {String} [msg]
744 * @example
745 *
746 * should.exist(1);
747 * should.exist(new Date());
748 */
749 should.exist = should.exists = function(obj, msg) {
750 if(null == obj) {
751 throw new AssertionError({
752 message: msg || ('expected ' + i(obj) + ' to exist'), stackStartFunction: should.exist
753 });
754 }
755 };
756
757 should.not = {};
758 /**
759 * Asserts _obj_ does not exist, with optional message.
760 *
761 * @name not.exist
762 * @static
763 * @memberOf should
764 * @category assertion assert
765 * @alias should.not.exists
766 * @param {*} obj
767 * @param {String} [msg]
768 * @example
769 *
770 * should.not.exist(null);
771 * should.not.exist(void 0);
772 */
773 should.not.exist = should.not.exists = function(obj, msg) {
774 if(null != obj) {
775 throw new AssertionError({
776 message: msg || ('expected ' + i(obj) + ' to not exist'), stackStartFunction: should.not.exist
777 });
778 }
779 };
780};
781},{"../assertion-error":3,"../util":20,"./_assert":6}],8:[function(require,module,exports){
782/*
783 * Should
784 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
785 * MIT Licensed
786 */
787
788module.exports = function(should, Assertion) {
789 /**
790 * Assert given object is exactly `true`.
791 *
792 * @name true
793 * @memberOf Assertion
794 * @category assertion bool
795 * @alias Assertion#True
796 * @example
797 *
798 * (true).should.be.true();
799 * false.should.not.be.true();
800 *
801 * ({ a: 10}).should.not.be.true();
802 */
803 Assertion.add('true', function() {
804 this.is.exactly(true);
805 });
806
807 Assertion.alias('true', 'True');
808
809 /**
810 * Assert given object is exactly `false`.
811 *
812 * @name false
813 * @memberOf Assertion
814 * @category assertion bool
815 * @alias Assertion#False
816 * @example
817 *
818 * (true).should.not.be.false();
819 * false.should.be.false();
820 */
821 Assertion.add('false', function() {
822 this.is.exactly(false);
823 });
824
825 Assertion.alias('false', 'False');
826
827 /**
828 * Assert given object is thuthy according javascript type conversions.
829 *
830 * @name ok
831 * @memberOf Assertion
832 * @category assertion bool
833 * @example
834 *
835 * (true).should.be.ok();
836 * ''.should.not.be.ok();
837 * should(null).not.be.ok();
838 * should(void 0).not.be.ok();
839 *
840 * (10).should.be.ok();
841 * (0).should.not.be.ok();
842 */
843 Assertion.add('ok', function() {
844 this.params = { operator: 'to be truthy' };
845
846 this.assert(this.obj);
847 });
848};
849
850},{}],9:[function(require,module,exports){
851/*
852 * Should
853 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
854 * MIT Licensed
855 */
856
857module.exports = function(should, Assertion) {
858 /**
859 * Simple chaining. It actually do nothing.
860 *
861 * @memberOf Assertion
862 * @name be
863 * @property {should.Assertion} be
864 * @alias Assertion#an
865 * @alias Assertion#of
866 * @alias Assertion#a
867 * @alias Assertion#and
868 * @alias Assertion#have
869 * @alias Assertion#has
870 * @alias Assertion#with
871 * @alias Assertion#is
872 * @alias Assertion#which
873 * @alias Assertion#the
874 * @alias Assertion#it
875 * @category assertion chaining
876 */
877 ['an', 'of', 'a', 'and', 'be', 'has', 'have', 'with', 'is', 'which', 'the', 'it'].forEach(function(name) {
878 Assertion.addChain(name);
879 });
880};
881
882},{}],10:[function(require,module,exports){
883/*
884 * Should
885 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
886 * MIT Licensed
887 */
888
889var util = require('../util');
890var eql = require('should-equal');
891
892module.exports = function(should, Assertion) {
893 var i = should.format;
894
895 /**
896 * Assert that given object contain something that equal to `other`. It uses `should-equal` for equality checks.
897 * If given object is array it search that one of elements was equal to `other`.
898 * If given object is string it checks if `other` is a substring - expected that `other` is a string.
899 * If given object is Object it checks that `other` is a subobject - expected that `other` is a object.
900 *
901 * @name containEql
902 * @memberOf Assertion
903 * @category assertion contain
904 * @param {*} other Nested object
905 * @example
906 *
907 * [1, 2, 3].should.containEql(1);
908 * [{ a: 1 }, 'a', 10].should.containEql({ a: 1 });
909 *
910 * 'abc'.should.containEql('b');
911 * 'ab1c'.should.containEql(1);
912 *
913 * ({ a: 10, c: { d: 10 }}).should.containEql({ a: 10 });
914 * ({ a: 10, c: { d: 10 }}).should.containEql({ c: { d: 10 }});
915 * ({ a: 10, c: { d: 10 }}).should.containEql({ b: 10 });
916 * // throws AssertionError: expected { a: 10, c: { d: 10 } } to contain { b: 10 }
917 * // expected { a: 10, c: { d: 10 } } to have property b
918 */
919 Assertion.add('containEql', function(other) {
920 this.params = {operator: 'to contain ' + i(other)};
921
922 this.is.not.null().and.not.undefined();
923
924 var obj = this.obj;
925
926 if(typeof obj == 'string') {
927 this.assert(obj.indexOf(String(other)) >= 0);
928 } else if(util.isIndexable(obj)) {
929 this.assert(util.some(obj, function(v) {
930 return eql(v, other).result;
931 }));
932 } else {
933 this.have.properties(other);
934 }
935 });
936
937 /**
938 * Assert that given object is contain equally structured object on the same depth level.
939 * If given object is an array and `other` is an array it checks that the eql elements is going in the same sequence in given array (recursive)
940 * If given object is an object it checks that the same keys contain deep equal values (recursive)
941 * On other cases it try to check with `.eql`
942 *
943 * @name containDeepOrdered
944 * @memberOf Assertion
945 * @category assertion contain
946 * @param {*} other Nested object
947 * @example
948 *
949 * [ 1, 2, 3].should.containDeepOrdered([1, 2]);
950 * [ 1, 2, [ 1, 2, 3 ]].should.containDeepOrdered([ 1, [ 2, 3 ]]);
951 *
952 * ({ a: 10, b: { c: 10, d: [1, 2, 3] }}).should.containDeepOrdered({a: 10});
953 * ({ a: 10, b: { c: 10, d: [1, 2, 3] }}).should.containDeepOrdered({b: {c: 10}});
954 * ({ a: 10, b: { c: 10, d: [1, 2, 3] }}).should.containDeepOrdered({b: {d: [1, 3]}});
955 */
956 Assertion.add('containDeepOrdered', function(other) {
957 this.params = {operator: 'to contain ' + i(other)};
958
959 var obj = this.obj;
960 if(typeof obj == 'string') {// expect other to be string
961 this.is.equal(String(other));
962 } else if(util.isIndexable(obj) && util.isIndexable(other)) {
963 for(var objIdx = 0, otherIdx = 0, objLength = util.length(obj), otherLength = util.length(other); objIdx < objLength && otherIdx < otherLength; objIdx++) {
964 try {
965 should(obj[objIdx]).containDeepOrdered(other[otherIdx]);
966 otherIdx++;
967 } catch(e) {
968 if(e instanceof should.AssertionError) {
969 continue;
970 }
971 throw e;
972 }
973 }
974
975 this.assert(otherIdx === otherLength);
976 } else if(obj != null && other != null && typeof obj == 'object' && typeof other == 'object') {// object contains object case
977 util.forEach(other, function(value, key) {
978 should(obj[key]).containDeepOrdered(value);
979 });
980
981 // if both objects is empty means we finish traversing - and we need to compare for hidden values
982 if(util.isEmptyObject(other)) {
983 this.eql(other);
984 }
985 } else {
986 this.eql(other);
987 }
988 });
989
990 /**
991 * The same like `Assertion#containDeepOrdered` but all checks on arrays without order.
992 *
993 * @name containDeep
994 * @memberOf Assertion
995 * @category assertion contain
996 * @param {*} other Nested object
997 * @example
998 *
999 * [ 1, 2, 3].should.containDeep([2, 1]);
1000 * [ 1, 2, [ 1, 2, 3 ]].should.containDeep([ 1, [ 3, 1 ]]);
1001 */
1002 Assertion.add('containDeep', function(other) {
1003 this.params = {operator: 'to contain ' + i(other)};
1004
1005 var obj = this.obj;
1006 if(typeof obj == 'string') {// expect other to be string
1007 this.is.equal(String(other));
1008 } else if(util.isIndexable(obj) && util.isIndexable(other)) {
1009 var usedKeys = {};
1010 util.forEach(other, function(otherItem) {
1011 this.assert(util.some(obj, function(item, index) {
1012 if(index in usedKeys) return false;
1013
1014 try {
1015 should(item).containDeep(otherItem);
1016 usedKeys[index] = true;
1017 return true;
1018 } catch(e) {
1019 if(e instanceof should.AssertionError) {
1020 return false;
1021 }
1022 throw e;
1023 }
1024 }));
1025 }, this);
1026 } else if(obj != null && other != null && typeof obj == 'object' && typeof other == 'object') {// object contains object case
1027 util.forEach(other, function(value, key) {
1028 should(obj[key]).containDeep(value);
1029 });
1030
1031 // if both objects is empty means we finish traversing - and we need to compare for hidden values
1032 if(util.isEmptyObject(other)) {
1033 this.eql(other);
1034 }
1035 } else {
1036 this.eql(other);
1037 }
1038 });
1039
1040};
1041
1042},{"../util":20,"should-equal":22}],11:[function(require,module,exports){
1043/*
1044 * Should
1045 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1046 * MIT Licensed
1047 */
1048
1049var eql = require('should-equal');
1050var type = require('should-type');
1051var util = require('../util');
1052
1053function formatEqlResult(r, a, b) {
1054 return ((r.path.length > 0 ? 'at ' + r.path.map(util.formatProp).join(' -> ') : '') +
1055 (r.a === a ? '' : ', A has ' + util.format(r.a)) +
1056 (r.b === b ? '' : ' and B has ' + util.format(r.b)) +
1057 (r.showReason ? ' because ' + r.reason : '')).trim();
1058}
1059
1060module.exports = function(should, Assertion) {
1061
1062 /**
1063 * Deep object equality comparison. For full spec see [`should-equal tests`](https://github.com/shouldjs/equal/blob/master/test.js).
1064 *
1065 * @name eql
1066 * @memberOf Assertion
1067 * @category assertion equality
1068 * @alias Assertion#deepEqual
1069 * @param {*} val Expected value
1070 * @param {string} [description] Optional message
1071 * @example
1072 *
1073 * (10).should.be.eql(10);
1074 * ('10').should.not.be.eql(10);
1075 * (-0).should.not.be.eql(+0);
1076 *
1077 * NaN.should.be.eql(NaN);
1078 *
1079 * ({ a: 10}).should.be.eql({ a: 10 });
1080 * [ 'a' ].should.not.be.eql({ '0': 'a' });
1081 */
1082 Assertion.add('eql', function(val, description) {
1083 this.params = {operator: 'to equal', expected: val, message: description};
1084
1085 var result = eql(this.obj, val, should.config);
1086 this.params.details = result.result ? '' : formatEqlResult(result, this.obj, val);
1087
1088 this.params.showDiff = eql(type(this.obj), type(val)).result;
1089
1090 this.assert(result.result);
1091 });
1092
1093 /**
1094 * Exact comparison using ===.
1095 *
1096 * @name equal
1097 * @memberOf Assertion
1098 * @category assertion equality
1099 * @alias Assertion#exactly
1100 * @param {*} val Expected value
1101 * @param {string} [description] Optional message
1102 * @example
1103 *
1104 * 10.should.be.equal(10);
1105 * 'a'.should.be.exactly('a');
1106 *
1107 * should(null).be.exactly(null);
1108 */
1109 Assertion.add('equal', function(val, description) {
1110 this.params = {operator: 'to be', expected: val, message: description};
1111
1112 this.params.showDiff = eql(type(this.obj), type(val)).result;
1113
1114 this.assert(val === this.obj);
1115 });
1116
1117 Assertion.alias('equal', 'exactly');
1118 Assertion.alias('eql', 'deepEqual');
1119
1120 function addOneOf(name, message, method) {
1121 Assertion.add(name, function(vals) {
1122 if(arguments.length !== 1) {
1123 vals = Array.prototype.slice.call(arguments);
1124 } else {
1125 should(vals).be.Array();
1126 }
1127
1128 this.params = {operator: message, expected: vals};
1129
1130 var obj = this.obj;
1131 var found = false;
1132
1133 util.forEach(vals, function(val) {
1134 try {
1135 should(val)[method](obj);
1136 found = true;
1137 return false;
1138 } catch(e) {
1139 if(e instanceof should.AssertionError) {
1140 return;//do nothing
1141 }
1142 throw e;
1143 }
1144 });
1145
1146 this.assert(found);
1147 });
1148 }
1149
1150 /**
1151 * Exact comparison using === to be one of supplied objects.
1152 *
1153 * @name equalOneOf
1154 * @memberOf Assertion
1155 * @category assertion equality
1156 * @param {Array|*} vals Expected values
1157 * @example
1158 *
1159 * 'ab'.should.be.equalOneOf('a', 10, 'ab');
1160 * 'ab'.should.be.equalOneOf(['a', 10, 'ab']);
1161 */
1162 addOneOf('equalOneOf', 'to be equals one of', 'equal');
1163
1164 /**
1165 * Exact comparison using .eql to be one of supplied objects.
1166 *
1167 * @name oneOf
1168 * @memberOf Assertion
1169 * @category assertion equality
1170 * @param {Array|*} vals Expected values
1171 * @example
1172 *
1173 * ({a: 10}).should.be.oneOf('a', 10, 'ab', {a: 10});
1174 * ({a: 10}).should.be.oneOf(['a', 10, 'ab', {a: 10}]);
1175 */
1176 addOneOf('oneOf', 'to be one of', 'eql');
1177
1178};
1179
1180},{"../util":20,"should-equal":22,"should-type":27}],12:[function(require,module,exports){
1181/*
1182 * Should
1183 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1184 * MIT Licensed
1185 */
1186var util = require('../util');
1187
1188module.exports = function(should, Assertion) {
1189 var i = should.format;
1190
1191 /**
1192 * Assert given function throws error with such message.
1193 *
1194 * @name throw
1195 * @memberOf Assertion
1196 * @category assertion errors
1197 * @alias Assertion#throwError
1198 * @param {string|RegExp|Function|Object|GeneratorFunction|GeneratorObject} [message] Message to match or properties
1199 * @param {Object} [properties] Optional properties that will be matched to thrown error
1200 * @example
1201 *
1202 * (function(){ throw new Error('fail') }).should.throw();
1203 * (function(){ throw new Error('fail') }).should.throw('fail');
1204 * (function(){ throw new Error('fail') }).should.throw(/fail/);
1205 *
1206 * (function(){ throw new Error('fail') }).should.throw(Error);
1207 * var error = new Error();
1208 * error.a = 10;
1209 * (function(){ throw error; }).should.throw(Error, { a: 10 });
1210 * (function(){ throw error; }).should.throw({ a: 10 });
1211 * (function*() {
1212 * yield throwError();
1213 * }).should.throw();
1214 */
1215 Assertion.add('throw', function(message, properties) {
1216 var fn = this.obj
1217 , err = {}
1218 , errorInfo = ''
1219 , thrown = false;
1220
1221 if(util.isGeneratorFunction(fn)) {
1222 return should(fn()).throw(message, properties);
1223 } else if(util.isGeneratorObject(fn)) {
1224 return should(fn.next.bind(fn)).throw(message, properties);
1225 }
1226
1227 this.is.a.Function();
1228
1229 var errorMatched = true;
1230
1231 try {
1232 fn();
1233 } catch(e) {
1234 thrown = true;
1235 err = e;
1236 }
1237
1238 if(thrown) {
1239 if(message) {
1240 if('string' == typeof message) {
1241 errorMatched = message == err.message;
1242 } else if(message instanceof RegExp) {
1243 errorMatched = message.test(err.message);
1244 } else if('function' == typeof message) {
1245 errorMatched = err instanceof message;
1246 } else if(null != message) {
1247 try {
1248 should(err).match(message);
1249 } catch(e) {
1250 if(e instanceof should.AssertionError) {
1251 errorInfo = ": " + e.message;
1252 errorMatched = false;
1253 } else {
1254 throw e;
1255 }
1256 }
1257 }
1258
1259 if(!errorMatched) {
1260 if('string' == typeof message || message instanceof RegExp) {
1261 errorInfo = " with a message matching " + i(message) + ", but got '" + err.message + "'";
1262 } else if('function' == typeof message) {
1263 errorInfo = " of type " + util.functionName(message) + ", but got " + util.functionName(err.constructor);
1264 }
1265 } else if('function' == typeof message && properties) {
1266 try {
1267 should(err).match(properties);
1268 } catch(e) {
1269 if(e instanceof should.AssertionError) {
1270 errorInfo = ": " + e.message;
1271 errorMatched = false;
1272 } else {
1273 throw e;
1274 }
1275 }
1276 }
1277 } else {
1278 errorInfo = " (got " + i(err) + ")";
1279 }
1280 }
1281
1282 this.params = { operator: 'to throw exception' + errorInfo };
1283
1284 this.assert(thrown);
1285 this.assert(errorMatched);
1286 });
1287
1288 Assertion.alias('throw', 'throwError');
1289};
1290
1291},{"../util":20}],13:[function(require,module,exports){
1292/*
1293 * Should
1294 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1295 * MIT Licensed
1296 */
1297
1298var util = require('../util');
1299var eql = require('should-equal');
1300
1301module.exports = function(should, Assertion) {
1302 var i = should.format;
1303
1304 /**
1305 * Asserts if given object match `other` object, using some assumptions:
1306 * First object matched if they are equal,
1307 * If `other` is a regexp and given object is a string check on matching with regexp
1308 * If `other` is a regexp and given object is an array check if all elements matched regexp
1309 * If `other` is a regexp and given object is an object check values on matching regexp
1310 * If `other` is a function check if this function throws AssertionError on given object or return false - it will be assumed as not matched
1311 * If `other` is an object check if the same keys matched with above rules
1312 * All other cases failed.
1313 *
1314 * Usually it is right idea to add pre type assertions, like `.String()` or `.Object()` to be sure assertions will do what you are expecting.
1315 * Object iteration happen by keys (properties with enumerable: true), thus some objects can cause small pain. Typical example is js
1316 * Error - it by default has 2 properties `name` and `message`, but they both non-enumerable. In this case make sure you specify checking props (see examples).
1317 *
1318 * @name match
1319 * @memberOf Assertion
1320 * @category assertion matching
1321 * @param {*} other Object to match
1322 * @param {string} [description] Optional message
1323 * @example
1324 * 'foobar'.should.match(/^foo/);
1325 * 'foobar'.should.not.match(/^bar/);
1326 *
1327 * ({ a: 'foo', c: 'barfoo' }).should.match(/foo$/);
1328 *
1329 * ['a', 'b', 'c'].should.match(/[a-z]/);
1330 *
1331 * (5).should.not.match(function(n) {
1332 * return n < 0;
1333 * });
1334 * (5).should.not.match(function(it) {
1335 * it.should.be.an.Array();
1336 * });
1337 * ({ a: 10, b: 'abc', c: { d: 10 }, d: 0 }).should
1338 * .match({ a: 10, b: /c$/, c: function(it) {
1339 * return it.should.have.property('d', 10);
1340 * }});
1341 *
1342 * [10, 'abc', { d: 10 }, 0].should
1343 * .match({ '0': 10, '1': /c$/, '2': function(it) {
1344 * return it.should.have.property('d', 10);
1345 * }});
1346 *
1347 * var myString = 'abc';
1348 *
1349 * myString.should.be.a.String().and.match(/abc/);
1350 *
1351 * myString = {};
1352 *
1353 * myString.should.match(/abc/); //yes this will pass
1354 * //better to do
1355 * myString.should.be.an.Object().and.not.empty().and.match(/abc/);//fixed
1356 *
1357 * (new Error('boom')).should.match(/abc/);//passed because no keys
1358 * (new Error('boom')).should.not.match({ message: /abc/ });//check specified property
1359 */
1360 Assertion.add('match', function(other, description) {
1361 this.params = {operator: 'to match ' + i(other), message: description};
1362
1363 if(!eql(this.obj, other).result) {
1364 if(other instanceof RegExp) { // something - regex
1365
1366 if(typeof this.obj == 'string') {
1367
1368 this.assert(other.exec(this.obj));
1369 } else if(util.isIndexable(this.obj)) {
1370 util.forEach(this.obj, function(item) {
1371 this.assert(other.exec(item));// should we try to convert to String and exec?
1372 }, this);
1373 } else if(null != this.obj && typeof this.obj == 'object') {
1374
1375 var notMatchedProps = [], matchedProps = [];
1376 util.forEach(this.obj, function(value, name) {
1377 if(other.exec(value)) matchedProps.push(util.formatProp(name));
1378 else notMatchedProps.push(util.formatProp(name) + ' (' + i(value) + ')');
1379 }, this);
1380
1381 if(notMatchedProps.length)
1382 this.params.operator += '\n not matched properties: ' + notMatchedProps.join(', ');
1383 if(matchedProps.length)
1384 this.params.operator += '\n matched properties: ' + matchedProps.join(', ');
1385
1386 this.assert(notMatchedProps.length === 0);
1387 } // should we try to convert to String and exec?
1388 } else if(typeof other == 'function') {
1389 var res;
1390
1391 res = other(this.obj);
1392
1393 //if(res instanceof Assertion) {
1394 // this.params.operator += '\n ' + res.getMessage();
1395 //}
1396
1397 //if we throw exception ok - it is used .should inside
1398 if(typeof res == 'boolean') {
1399 this.assert(res); // if it is just boolean function assert on it
1400 }
1401 } else if(other != null && this.obj != null && typeof other == 'object') { // try to match properties (for Object and Array)
1402 notMatchedProps = [];
1403 matchedProps = [];
1404
1405 util.forEach(other, function(value, key) {
1406 try {
1407 should(this.obj).have.property(key).which.match(value);
1408 matchedProps.push(util.formatProp(key));
1409 } catch(e) {
1410 if(e instanceof should.AssertionError) {
1411 notMatchedProps.push(util.formatProp(key) + ' (' + i(this.obj[key]) + ')');
1412 } else {
1413 throw e;
1414 }
1415 }
1416 }, this);
1417
1418 if(notMatchedProps.length)
1419 this.params.operator += '\n not matched properties: ' + notMatchedProps.join(', ');
1420 if(matchedProps.length)
1421 this.params.operator += '\n matched properties: ' + matchedProps.join(', ');
1422
1423 this.assert(notMatchedProps.length === 0);
1424 } else {
1425 this.assert(false);
1426 }
1427 }
1428 });
1429
1430 /**
1431 * Asserts if given object values or array elements all match `other` object, using some assumptions:
1432 * First object matched if they are equal,
1433 * If `other` is a regexp - matching with regexp
1434 * If `other` is a function check if this function throws AssertionError on given object or return false - it will be assumed as not matched
1435 * All other cases check if this `other` equal to each element
1436 *
1437 * @name matchEach
1438 * @memberOf Assertion
1439 * @category assertion matching
1440 * @alias Assertion#matchSome
1441 * @param {*} other Object to match
1442 * @param {string} [description] Optional message
1443 * @example
1444 * [ 'a', 'b', 'c'].should.matchEach(/\w+/);
1445 * [ 'a', 'a', 'a'].should.matchEach('a');
1446 *
1447 * [ 'a', 'a', 'a'].should.matchEach(function(value) { value.should.be.eql('a') });
1448 *
1449 * { a: 'a', b: 'a', c: 'a' }.should.matchEach(function(value) { value.should.be.eql('a') });
1450 */
1451 Assertion.add('matchEach', function(other, description) {
1452 this.params = {operator: 'to match each ' + i(other), message: description};
1453
1454 util.forEach(this.obj, function(value) {
1455 should(value).match(other);
1456 }, this);
1457 });
1458
1459 /**
1460 * Asserts if any of given object values or array elements match `other` object, using some assumptions:
1461 * First object matched if they are equal,
1462 * If `other` is a regexp - matching with regexp
1463 * If `other` is a function check if this function throws AssertionError on given object or return false - it will be assumed as not matched
1464 * All other cases check if this `other` equal to each element
1465 *
1466 * @name matchAny
1467 * @memberOf Assertion
1468 * @category assertion matching
1469 * @param {*} other Object to match
1470 * @alias Assertion#matchEvery
1471 * @param {string} [description] Optional message
1472 * @example
1473 * [ 'a', 'b', 'c'].should.matchAny(/\w+/);
1474 * [ 'a', 'b', 'c'].should.matchAny('a');
1475 *
1476 * [ 'a', 'b', 'c'].should.matchAny(function(value) { value.should.be.eql('a') });
1477 *
1478 * { a: 'a', b: 'b', c: 'c' }.should.matchAny(function(value) { value.should.be.eql('a') });
1479 */
1480 Assertion.add('matchAny', function(other, description) {
1481 this.params = {operator: 'to match any ' + i(other), message: description};
1482
1483 this.assert(util.some(this.obj, function(value) {
1484 try {
1485 should(value).match(other);
1486 return true;
1487 } catch(e) {
1488 if(e instanceof should.AssertionError) {
1489 // Caught an AssertionError, return false to the iterator
1490 return false;
1491 }
1492 throw e;
1493 }
1494 }));
1495 });
1496
1497 Assertion.alias('matchAny', 'matchSome');
1498 Assertion.alias('matchEach', 'matchEvery');
1499};
1500
1501},{"../util":20,"should-equal":22}],14:[function(require,module,exports){
1502/*
1503 * Should
1504 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1505 * MIT Licensed
1506 */
1507
1508module.exports = function(should, Assertion) {
1509
1510 /**
1511 * Assert given object is NaN
1512 * @name NaN
1513 * @memberOf Assertion
1514 * @category assertion numbers
1515 * @example
1516 *
1517 * (10).should.not.be.NaN();
1518 * NaN.should.be.NaN();
1519 */
1520 Assertion.add('NaN', function() {
1521 this.params = { operator: 'to be NaN' };
1522
1523 this.assert(this.obj !== this.obj);
1524 });
1525
1526 /**
1527 * Assert given object is not finite (positive or negative)
1528 *
1529 * @name Infinity
1530 * @memberOf Assertion
1531 * @category assertion numbers
1532 * @example
1533 *
1534 * (10).should.not.be.Infinity();
1535 * NaN.should.not.be.Infinity();
1536 */
1537 Assertion.add('Infinity', function() {
1538 this.params = { operator: 'to be Infinity' };
1539
1540 this.is.a.Number()
1541 .and.not.a.NaN()
1542 .and.assert(!isFinite(this.obj));
1543 });
1544
1545 /**
1546 * Assert given number between `start` and `finish` or equal one of them.
1547 *
1548 * @name within
1549 * @memberOf Assertion
1550 * @category assertion numbers
1551 * @param {number} start Start number
1552 * @param {number} finish Finish number
1553 * @param {string} [description] Optional message
1554 * @example
1555 *
1556 * (10).should.be.within(0, 20);
1557 */
1558 Assertion.add('within', function(start, finish, description) {
1559 this.params = { operator: 'to be within ' + start + '..' + finish, message: description };
1560
1561 this.assert(this.obj >= start && this.obj <= finish);
1562 });
1563
1564 /**
1565 * Assert given number near some other `value` within `delta`
1566 *
1567 * @name approximately
1568 * @memberOf Assertion
1569 * @category assertion numbers
1570 * @param {number} value Center number
1571 * @param {number} delta Radius
1572 * @param {string} [description] Optional message
1573 * @example
1574 *
1575 * (9.99).should.be.approximately(10, 0.1);
1576 */
1577 Assertion.add('approximately', function(value, delta, description) {
1578 this.params = { operator: 'to be approximately ' + value + ' ±' + delta, message: description };
1579
1580 this.assert(Math.abs(this.obj - value) <= delta);
1581 });
1582
1583 /**
1584 * Assert given number above `n`.
1585 *
1586 * @name above
1587 * @alias Assertion#greaterThan
1588 * @memberOf Assertion
1589 * @category assertion numbers
1590 * @param {number} n Margin number
1591 * @param {string} [description] Optional message
1592 * @example
1593 *
1594 * (10).should.be.above(0);
1595 */
1596 Assertion.add('above', function(n, description) {
1597 this.params = { operator: 'to be above ' + n, message: description };
1598
1599 this.assert(this.obj > n);
1600 });
1601
1602 /**
1603 * Assert given number below `n`.
1604 *
1605 * @name below
1606 * @alias Assertion#lessThan
1607 * @memberOf Assertion
1608 * @category assertion numbers
1609 * @param {number} n Margin number
1610 * @param {string} [description] Optional message
1611 * @example
1612 *
1613 * (0).should.be.below(10);
1614 */
1615 Assertion.add('below', function(n, description) {
1616 this.params = { operator: 'to be below ' + n, message: description };
1617
1618 this.assert(this.obj < n);
1619 });
1620
1621 Assertion.alias('above', 'greaterThan');
1622 Assertion.alias('below', 'lessThan');
1623
1624 /**
1625 * Assert given number above `n`.
1626 *
1627 * @name aboveOrEqual
1628 * @alias Assertion#greaterThanOrEqual
1629 * @memberOf Assertion
1630 * @category assertion numbers
1631 * @param {number} n Margin number
1632 * @param {string} [description] Optional message
1633 * @example
1634 *
1635 * (10).should.be.aboveOrEqual(0);
1636 * (10).should.be.aboveOrEqual(10);
1637 */
1638 Assertion.add('aboveOrEqual', function(n, description) {
1639 this.params = { operator: 'to be above or equal' + n, message: description };
1640
1641 this.assert(this.obj >= n);
1642 });
1643
1644 /**
1645 * Assert given number below `n`.
1646 *
1647 * @name belowOrEqual
1648 * @alias Assertion#lessThanOrEqual
1649 * @memberOf Assertion
1650 * @category assertion numbers
1651 * @param {number} n Margin number
1652 * @param {string} [description] Optional message
1653 * @example
1654 *
1655 * (0).should.be.belowOrEqual(10);
1656 * (0).should.be.belowOrEqual(0);
1657 */
1658 Assertion.add('belowOrEqual', function(n, description) {
1659 this.params = { operator: 'to be below or equal' + n, message: description };
1660
1661 this.assert(this.obj <= n);
1662 });
1663
1664 Assertion.alias('aboveOrEqual', 'greaterThanOrEqual');
1665 Assertion.alias('belowOrEqual', 'lessThanOrEqual');
1666
1667};
1668
1669},{}],15:[function(require,module,exports){
1670/*
1671 * Should
1672 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1673 * MIT Licensed
1674 */
1675
1676var util = require('../util');
1677var PromisedAssertion = require('../assertion').PromisedAssertion;
1678var Assertion = require('../assertion');
1679
1680module.exports = function(should) {
1681 /**
1682 * Assert given object is a Promise
1683 *
1684 * @name Promise
1685 * @memberOf Assertion
1686 * @category assertion promises
1687 * @example
1688 *
1689 * promise.should.be.Promise()
1690 * (new Promise(function(resolve, reject) { resolve(10); })).should.be.a.Promise()
1691 * (10).should.not.be.a.Promise()
1692 */
1693 Assertion.add('Promise', function() {
1694 this.params = {operator: 'to be promise'};
1695
1696 var obj = this.obj;
1697
1698 should(obj).have.property('then')
1699 .which.is.a.Function();
1700 });
1701
1702 /**
1703 * Assert given promise will be fulfilled. Result of assertion is still .thenable and should be handled accordingly.
1704 *
1705 * @name fulfilled
1706 * @memberOf Assertion
1707 * @returns {Promise}
1708 * @category assertion promises
1709 * @example
1710 *
1711 * // don't forget to handle async nature
1712 * (new Promise(function(resolve, reject) { resolve(10); })).should.be.fulfilled();
1713 *
1714 * // test example with mocha it is possible to return promise
1715 * it('is async', () => {
1716 * return new Promise(resolve => resolve(10))
1717 * .should.be.fulfilled();
1718 * });
1719 */
1720 Assertion.prototype.fulfilled = function Assertion$fulfilled() {
1721 this.params = {operator: 'to be fulfilled'};
1722
1723 should(this.obj).be.a.Promise();
1724
1725 var that = this;
1726 return this.obj.then(function next$onResolve(value) {
1727 if (that.negate) {
1728 that.fail();
1729 }
1730 return value;
1731 }, function next$onReject(err) {
1732 if (!that.negate) {
1733 that.fail();
1734 }
1735 return err;
1736 });
1737 };
1738
1739 /**
1740 * Assert given promise will be rejected. Result of assertion is still .thenable and should be handled accordingly.
1741 *
1742 * @name rejected
1743 * @memberOf Assertion
1744 * @category assertion promises
1745 * @returns {Promise}
1746 * @example
1747 *
1748 * // don't forget to handle async nature
1749 * (new Promise(function(resolve, reject) { resolve(10); }))
1750 * .should.not.be.rejected();
1751 *
1752 * // test example with mocha it is possible to return promise
1753 * it('is async', () => {
1754 * return new Promise((resolve, reject) => reject(new Error('boom')))
1755 * .should.be.rejected();
1756 * });
1757 */
1758 Assertion.prototype.rejected = function() {
1759 this.params = {operator: 'to be rejected'};
1760
1761 should(this.obj).be.a.Promise();
1762
1763 var that = this;
1764 return this.obj.then(function(value) {
1765 if (!that.negate) {
1766 that.fail();
1767 }
1768 return value;
1769 }, function next$onError(err) {
1770 if (that.negate) {
1771 that.fail();
1772 }
1773 return err;
1774 });
1775 };
1776
1777 /**
1778 * Assert given promise will be fulfilled with some expected value (value compared using .eql).
1779 * Result of assertion is still .thenable and should be handled accordingly.
1780 *
1781 * @name fulfilledWith
1782 * @memberOf Assertion
1783 * @category assertion promises
1784 * @returns {Promise}
1785 * @example
1786 *
1787 * // don't forget to handle async nature
1788 * (new Promise(function(resolve, reject) { resolve(10); }))
1789 * .should.be.fulfilledWith(10);
1790 *
1791 * // test example with mocha it is possible to return promise
1792 * it('is async', () => {
1793 * return new Promise((resolve, reject) => resolve(10))
1794 * .should.be.fulfilledWith(10);
1795 * });
1796 */
1797 Assertion.prototype.fulfilledWith = function(expectedValue) {
1798 this.params = {operator: 'to be fulfilled'};
1799
1800 should(this.obj).be.a.Promise();
1801
1802 var that = this;
1803 return this.obj.then(function(value) {
1804 if (that.negate) {
1805 that.fail();
1806 }
1807 should(value).eql(expectedValue);
1808 return value;
1809 }, function next$onError(err) {
1810 if (!that.negate) {
1811 that.fail();
1812 }
1813 return err;
1814 });
1815 };
1816
1817 /**
1818 * Assert given promise will be rejected with some sort of error. Arguments is the same for Assertion#throw.
1819 * Result of assertion is still .thenable and should be handled accordingly.
1820 *
1821 * @name rejectedWith
1822 * @memberOf Assertion
1823 * @category assertion promises
1824 * @returns {Promise}
1825 * @example
1826 *
1827 * function failedPromise() {
1828 * return new Promise(function(resolve, reject) {
1829 * reject(new Error('boom'))
1830 * })
1831 * }
1832 * failedPromise().should.be.rejectedWith(Error);
1833 * failedPromise().should.be.rejectedWith('boom');
1834 * failedPromise().should.be.rejectedWith(/boom/);
1835 * failedPromise().should.be.rejectedWith(Error, { message: 'boom' });
1836 * failedPromise().should.be.rejectedWith({ message: 'boom' });
1837 *
1838 * // test example with mocha it is possible to return promise
1839 * it('is async', () => {
1840 * return failedPromise().should.be.rejectedWith({ message: 'boom' });
1841 * });
1842 */
1843 Assertion.prototype.rejectedWith = function(message, properties) {
1844 this.params = {operator: 'to be rejected'};
1845
1846 should(this.obj).be.a.Promise();
1847
1848 var that = this;
1849 return this.obj.then(function(value) {
1850 if (!that.negate) {
1851 that.fail();
1852 }
1853 return value;
1854 }, function next$onError(err) {
1855 if (that.negate) {
1856 that.fail();
1857 }
1858
1859 var errorMatched = true;
1860 var errorInfo = '';
1861
1862 if ('string' === typeof message) {
1863 errorMatched = message === err.message;
1864 } else if (message instanceof RegExp) {
1865 errorMatched = message.test(err.message);
1866 } else if ('function' === typeof message) {
1867 errorMatched = err instanceof message;
1868 } else if (message !== null && typeof message === 'object') {
1869 try {
1870 should(err).match(message);
1871 } catch (e) {
1872 if (e instanceof should.AssertionError) {
1873 errorInfo = ': ' + e.message;
1874 errorMatched = false;
1875 } else {
1876 throw e;
1877 }
1878 }
1879 }
1880
1881 if (!errorMatched) {
1882 if ( typeof message === 'string' || message instanceof RegExp) {
1883 errorInfo = ' with a message matching ' + should.format(message) + ", but got '" + err.message + "'";
1884 } else if ('function' === typeof message) {
1885 errorInfo = ' of type ' + util.functionName(message) + ', but got ' + util.functionName(err.constructor);
1886 }
1887 } else if ('function' === typeof message && properties) {
1888 try {
1889 should(err).match(properties);
1890 } catch (e) {
1891 if (e instanceof should.AssertionError) {
1892 errorInfo = ': ' + e.message;
1893 errorMatched = false;
1894 } else {
1895 throw e;
1896 }
1897 }
1898 }
1899
1900 that.params.operator += errorInfo;
1901
1902 that.assert(errorMatched);
1903
1904 return err;
1905 });
1906 };
1907
1908 /**
1909 * Assert given object is promise and wrap it in PromisedAssertion, which has all properties of Assertion.
1910 * That means you can chain as with usual Assertion.
1911 * Result of assertion is still .thenable and should be handled accordingly.
1912 *
1913 * @name finally
1914 * @memberOf Assertion
1915 * @alias Assertion#eventually
1916 * @category assertion promises
1917 * @returns {PromisedAssertion} Like Assertion, but .then this.obj in Assertion
1918 * @example
1919 *
1920 * (new Promise(function(resolve, reject) { resolve(10); }))
1921 * .should.be.eventually.equal(10);
1922 *
1923 * // test example with mocha it is possible to return promise
1924 * it('is async', () => {
1925 * return new Promise(resolve => resolve(10))
1926 * .should.be.finally.equal(10);
1927 * });
1928 */
1929 Object.defineProperty(Assertion.prototype, 'finally', {
1930 get: function() {
1931 should(this.obj).be.a.Promise();
1932
1933 var that = this;
1934
1935 return new PromisedAssertion(this.obj.then(function(obj) {
1936 var a = should(obj);
1937
1938 a.negate = that.negate;
1939 a.anyOne = that.anyOne;
1940
1941 return a;
1942 }));
1943 }
1944 });
1945
1946 Assertion.alias('finally', 'eventually');
1947};
1948
1949},{"../assertion":4,"../util":20}],16:[function(require,module,exports){
1950/*
1951 * Should
1952 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
1953 * MIT Licensed
1954 */
1955
1956var util = require('../util');
1957var eql = require('should-equal');
1958
1959var aSlice = Array.prototype.slice;
1960
1961module.exports = function(should, Assertion) {
1962 var i = should.format;
1963 /**
1964 * Asserts given object has some descriptor. **On success it change given object to be value of property**.
1965 *
1966 * @name propertyWithDescriptor
1967 * @memberOf Assertion
1968 * @category assertion property
1969 * @param {string} name Name of property
1970 * @param {Object} desc Descriptor like used in Object.defineProperty (not required to add all properties)
1971 * @example
1972 *
1973 * ({ a: 10 }).should.have.propertyWithDescriptor('a', { enumerable: true });
1974 */
1975 Assertion.add('propertyWithDescriptor', function(name, desc) {
1976 this.params = {actual: this.obj, operator: 'to have own property with descriptor ' + i(desc)};
1977 var obj = this.obj;
1978 this.have.ownProperty(name);
1979 should(Object.getOwnPropertyDescriptor(Object(obj), name)).have.properties(desc);
1980 });
1981
1982 function processPropsArgs() {
1983 var args = {};
1984 if(arguments.length > 1) {
1985 args.names = aSlice.call(arguments);
1986 } else {
1987 var arg = arguments[0];
1988 if(typeof arg === 'string') {
1989 args.names = [arg];
1990 } else if(util.isIndexable(arg)) {
1991 args.names = arg;
1992 } else {
1993 args.names = Object.keys(arg);
1994 args.values = arg;
1995 }
1996 }
1997 return args;
1998 }
1999
2000
2001 /**
2002 * Asserts given object has enumerable property with optionally value. **On success it change given object to be value of property**.
2003 *
2004 * @name enumerable
2005 * @memberOf Assertion
2006 * @category assertion property
2007 * @param {string} name Name of property
2008 * @param {*} [val] Optional property value to check
2009 * @example
2010 *
2011 * ({ a: 10 }).should.have.enumerable('a');
2012 */
2013 Assertion.add('enumerable', function(name, val) {
2014 name = util.convertPropertyName(name);
2015
2016 this.params = {
2017 operator: "to have enumerable property " + util.formatProp(name) + (arguments.length > 1 ? " equal to " + i(val): "")
2018 };
2019
2020 var desc = { enumerable: true };
2021 if(arguments.length > 1) desc.value = val;
2022 this.have.propertyWithDescriptor(name, desc);
2023 });
2024
2025 /**
2026 * Asserts given object has enumerable properties
2027 *
2028 * @name enumerables
2029 * @memberOf Assertion
2030 * @category assertion property
2031 * @param {Array|...string|Object} names Names of property
2032 * @example
2033 *
2034 * ({ a: 10, b: 10 }).should.have.enumerables('a');
2035 */
2036 Assertion.add('enumerables', function(names) {
2037 var args = processPropsArgs.apply(null, arguments);
2038
2039 this.params = {
2040 operator: "to have enumerables " + args.names.map(util.formatProp)
2041 };
2042
2043 var obj = this.obj;
2044 args.names.forEach(function(name) {
2045 should(obj).have.enumerable(name);
2046 });
2047 });
2048
2049 /**
2050 * Asserts given object has property with optionally value. **On success it change given object to be value of property**.
2051 *
2052 * @name property
2053 * @memberOf Assertion
2054 * @category assertion property
2055 * @param {string} name Name of property
2056 * @param {*} [val] Optional property value to check
2057 * @example
2058 *
2059 * ({ a: 10 }).should.have.property('a');
2060 */
2061 Assertion.add('property', function(name, val) {
2062 name = util.convertPropertyName(name);
2063 if(arguments.length > 1) {
2064 var p = {};
2065 p[name] = val;
2066 this.have.properties(p);
2067 } else {
2068 this.have.properties(name);
2069 }
2070 this.obj = this.obj[name];
2071 });
2072
2073 /**
2074 * Asserts given object has properties. On this method affect .any modifier, which allow to check not all properties.
2075 *
2076 * @name properties
2077 * @memberOf Assertion
2078 * @category assertion property
2079 * @param {Array|...string|Object} names Names of property
2080 * @example
2081 *
2082 * ({ a: 10 }).should.have.properties('a');
2083 * ({ a: 10, b: 20 }).should.have.properties([ 'a' ]);
2084 * ({ a: 10, b: 20 }).should.have.properties({ b: 20 });
2085 */
2086 Assertion.add('properties', function(names) {
2087 var values = {};
2088 if(arguments.length > 1) {
2089 names = aSlice.call(arguments);
2090 } else if(!Array.isArray(names)) {
2091 if(typeof names == 'string' || typeof names == 'symbol') {
2092 names = [names];
2093 } else {
2094 values = names;
2095 names = Object.keys(names);
2096 }
2097 }
2098
2099 var obj = Object(this.obj), missingProperties = [];
2100
2101 //just enumerate properties and check if they all present
2102 names.forEach(function(name) {
2103 if(!(name in obj)) missingProperties.push(util.formatProp(name));
2104 });
2105
2106 var props = missingProperties;
2107 if(props.length === 0) {
2108 props = names.map(util.formatProp);
2109 } else if(this.anyOne) {
2110 props = names.filter(function(name) {
2111 return missingProperties.indexOf(util.formatProp(name)) < 0;
2112 }).map(util.formatProp);
2113 }
2114
2115 var operator = (props.length === 1 ?
2116 'to have property ' : 'to have ' + (this.anyOne ? 'any of ' : '') + 'properties ') + props.join(', ');
2117
2118 this.params = {obj: this.obj, operator: operator};
2119
2120 //check that all properties presented
2121 //or if we request one of them that at least one them presented
2122 this.assert(missingProperties.length === 0 || (this.anyOne && missingProperties.length != names.length));
2123
2124 // check if values in object matched expected
2125 var valueCheckNames = Object.keys(values);
2126 if(valueCheckNames.length) {
2127 var wrongValues = [];
2128 props = [];
2129
2130 // now check values, as there we have all properties
2131 valueCheckNames.forEach(function(name) {
2132 var value = values[name];
2133 if(!eql(obj[name], value).result) {
2134 wrongValues.push(util.formatProp(name) + ' of ' + i(value) + ' (got ' + i(obj[name]) + ')');
2135 } else {
2136 props.push(util.formatProp(name) + ' of ' + i(value));
2137 }
2138 });
2139
2140 if((wrongValues.length !== 0 && !this.anyOne) || (this.anyOne && props.length === 0)) {
2141 props = wrongValues;
2142 }
2143
2144 operator = (props.length === 1 ?
2145 'to have property ' : 'to have ' + (this.anyOne ? 'any of ' : '') + 'properties ') + props.join(', ');
2146
2147 this.params = {obj: this.obj, operator: operator};
2148
2149 //if there is no not matched values
2150 //or there is at least one matched
2151 this.assert(wrongValues.length === 0 || (this.anyOne && wrongValues.length != valueCheckNames.length));
2152 }
2153 });
2154
2155 /**
2156 * Asserts given object has property `length` with given value `n`
2157 *
2158 * @name length
2159 * @alias Assertion#lengthOf
2160 * @memberOf Assertion
2161 * @category assertion property
2162 * @param {number} n Expected length
2163 * @param {string} [description] Optional message
2164 * @example
2165 *
2166 * [1, 2].should.have.length(2);
2167 */
2168 Assertion.add('length', function(n, description) {
2169 this.have.property('length', n, description);
2170 });
2171
2172 Assertion.alias('length', 'lengthOf');
2173
2174 var hasOwnProperty = Object.prototype.hasOwnProperty;
2175
2176 /**
2177 * Asserts given object has own property. **On success it change given object to be value of property**.
2178 *
2179 * @name ownProperty
2180 * @alias Assertion#hasOwnProperty
2181 * @memberOf Assertion
2182 * @category assertion property
2183 * @param {string} name Name of property
2184 * @param {string} [description] Optional message
2185 * @example
2186 *
2187 * ({ a: 10 }).should.have.ownProperty('a');
2188 */
2189 Assertion.add('ownProperty', function(name, description) {
2190 name = util.convertPropertyName(name);
2191 this.params = {
2192 actual: this.obj,
2193 operator: 'to have own property ' + util.formatProp(name),
2194 message: description
2195 };
2196
2197 this.assert(hasOwnProperty.call(this.obj, name));
2198
2199 this.obj = this.obj[name];
2200 });
2201
2202 Assertion.alias('ownProperty', 'hasOwnProperty');
2203
2204 /**
2205 * Asserts given object is empty. For strings, arrays and arguments it checks .length property, for objects it checks keys.
2206 *
2207 * @name empty
2208 * @memberOf Assertion
2209 * @category assertion property
2210 * @example
2211 *
2212 * ''.should.be.empty();
2213 * [].should.be.empty();
2214 * ({}).should.be.empty();
2215 */
2216 Assertion.add('empty', function() {
2217 this.params = {operator: 'to be empty'};
2218
2219 if(util.length(this.obj) !== void 0) {
2220 should(this.obj).have.property('length', 0);
2221 } else {
2222 var obj = Object(this.obj); // wrap to reference for booleans and numbers
2223 for(var prop in obj) {
2224 should(this.obj).not.have.ownProperty(prop);
2225 }
2226 }
2227 }, true);
2228
2229 /**
2230 * Asserts given object has exact keys. Compared to `properties`, `keys` does not accept Object as a argument.
2231 *
2232 * @name keys
2233 * @alias Assertion#key
2234 * @memberOf Assertion
2235 * @category assertion property
2236 * @param {Array|...string} [keys] Keys to check
2237 * @example
2238 *
2239 * ({ a: 10 }).should.have.keys('a');
2240 * ({ a: 10, b: 20 }).should.have.keys('a', 'b');
2241 * ({ a: 10, b: 20 }).should.have.keys([ 'a', 'b' ]);
2242 * ({}).should.have.keys();
2243 */
2244 Assertion.add('keys', function(keys) {
2245 if(arguments.length > 1) keys = aSlice.call(arguments);
2246 else if(arguments.length === 1 && typeof keys === 'string') keys = [keys];
2247 else if(arguments.length === 0) keys = [];
2248
2249 keys = keys.map(String);
2250
2251 var obj = Object(this.obj);
2252
2253 // first check if some keys are missing
2254 var missingKeys = [];
2255 keys.forEach(function(key) {
2256 if(!hasOwnProperty.call(this.obj, key))
2257 missingKeys.push(util.formatProp(key));
2258 }, this);
2259
2260 // second check for extra keys
2261 var extraKeys = [];
2262 Object.keys(obj).forEach(function(key) {
2263 if(keys.indexOf(key) < 0) {
2264 extraKeys.push(util.formatProp(key));
2265 }
2266 });
2267
2268 var verb = keys.length === 0 ? 'to be empty' :
2269 'to have ' + (keys.length === 1 ? 'key ' : 'keys ');
2270
2271 this.params = {operator: verb + keys.map(util.formatProp).join(', ')};
2272
2273 if(missingKeys.length > 0)
2274 this.params.operator += '\n\tmissing keys: ' + missingKeys.join(', ');
2275
2276 if(extraKeys.length > 0)
2277 this.params.operator += '\n\textra keys: ' + extraKeys.join(', ');
2278
2279 this.assert(missingKeys.length === 0 && extraKeys.length === 0);
2280 });
2281
2282 Assertion.alias("keys", "key");
2283
2284 /**
2285 * Asserts given object has nested property in depth by path. **On success it change given object to be value of final property**.
2286 *
2287 * @name propertyByPath
2288 * @memberOf Assertion
2289 * @category assertion property
2290 * @param {Array|...string} properties Properties path to search
2291 * @example
2292 *
2293 * ({ a: {b: 10}}).should.have.propertyByPath('a', 'b').eql(10);
2294 */
2295 Assertion.add('propertyByPath', function(properties) {
2296 if(arguments.length > 1) properties = aSlice.call(arguments);
2297 else if(arguments.length === 1 && typeof properties == 'string') properties = [properties];
2298 else if(arguments.length === 0) properties = [];
2299
2300 var allProps = properties.map(util.formatProp);
2301
2302 properties = properties.map(String);
2303
2304 var obj = should(Object(this.obj));
2305
2306 var foundProperties = [];
2307
2308 var currentProperty;
2309 while(currentProperty = properties.shift()) {
2310 this.params = {operator: 'to have property by path ' + allProps.join(', ') + ' - failed on ' + util.formatProp(currentProperty)};
2311 obj = obj.have.property(currentProperty);
2312 foundProperties.push(currentProperty);
2313 }
2314
2315 this.params = {obj: this.obj, operator: 'to have property by path ' + allProps.join(', ')};
2316
2317 this.obj = obj.obj;
2318 });
2319};
2320
2321},{"../util":20,"should-equal":22}],17:[function(require,module,exports){
2322/*
2323 * Should
2324 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
2325 * MIT Licensed
2326 */
2327
2328module.exports = function(should, Assertion) {
2329 /**
2330 * Assert given string starts with prefix
2331 * @name startWith
2332 * @memberOf Assertion
2333 * @category assertion strings
2334 * @param {string} str Prefix
2335 * @param {string} [description] Optional message
2336 * @example
2337 *
2338 * 'abc'.should.startWith('a');
2339 */
2340 Assertion.add('startWith', function(str, description) {
2341 this.params = { operator: 'to start with ' + should.format(str), message: description };
2342
2343 this.assert(0 === this.obj.indexOf(str));
2344 });
2345
2346 /**
2347 * Assert given string ends with prefix
2348 * @name endWith
2349 * @memberOf Assertion
2350 * @category assertion strings
2351 * @param {string} str Prefix
2352 * @param {string} [description] Optional message
2353 * @example
2354 *
2355 * 'abca'.should.endWith('a');
2356 */
2357 Assertion.add('endWith', function(str, description) {
2358 this.params = { operator: 'to end with ' + should.format(str), message: description };
2359
2360 this.assert(this.obj.indexOf(str, this.obj.length - str.length) >= 0);
2361 });
2362};
2363
2364},{}],18:[function(require,module,exports){
2365/*
2366 * Should
2367 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
2368 * MIT Licensed
2369 */
2370
2371var util = require('../util');
2372
2373module.exports = function(should, Assertion) {
2374 /**
2375 * Assert given object is number
2376 * @name Number
2377 * @memberOf Assertion
2378 * @category assertion types
2379 */
2380 Assertion.add('Number', function() {
2381 this.params = {operator: 'to be a number'};
2382
2383 this.have.type('number');
2384 });
2385
2386 /**
2387 * Assert given object is arguments
2388 * @name arguments
2389 * @alias Assertion#Arguments
2390 * @memberOf Assertion
2391 * @category assertion types
2392 */
2393 Assertion.add('arguments', function() {
2394 this.params = {operator: 'to be arguments'};
2395
2396 this.have.class('Arguments');
2397 });
2398
2399 Assertion.alias('arguments', 'Arguments');
2400
2401 /**
2402 * Assert given object has some type using `typeof`
2403 * @name type
2404 * @memberOf Assertion
2405 * @param {string} type Type name
2406 * @param {string} [description] Optional message
2407 * @category assertion types
2408 */
2409 Assertion.add('type', function(type, description) {
2410 this.params = {operator: 'to have type ' + type, message: description};
2411
2412 should(typeof this.obj).be.exactly(type);
2413 });
2414
2415 /**
2416 * Assert given object is instance of `constructor`
2417 * @name instanceof
2418 * @alias Assertion#instanceOf
2419 * @memberOf Assertion
2420 * @param {Function} constructor Constructor function
2421 * @param {string} [description] Optional message
2422 * @category assertion types
2423 */
2424 Assertion.add('instanceof', function(constructor, description) {
2425 this.params = {operator: 'to be an instance of ' + util.functionName(constructor), message: description};
2426
2427 this.assert(Object(this.obj) instanceof constructor);
2428 });
2429
2430 Assertion.alias('instanceof', 'instanceOf');
2431
2432 /**
2433 * Assert given object is function
2434 * @name Function
2435 * @memberOf Assertion
2436 * @category assertion types
2437 */
2438 Assertion.add('Function', function() {
2439 this.params = {operator: 'to be a function'};
2440
2441 this.have.type('function');
2442 });
2443
2444 /**
2445 * Assert given object is object
2446 * @name Object
2447 * @memberOf Assertion
2448 * @category assertion types
2449 */
2450 Assertion.add('Object', function() {
2451 this.params = {operator: 'to be an object'};
2452
2453 this.is.not.null().and.have.type('object');
2454 });
2455
2456 /**
2457 * Assert given object is string
2458 * @name String
2459 * @memberOf Assertion
2460 * @category assertion types
2461 */
2462 Assertion.add('String', function() {
2463 this.params = {operator: 'to be a string'};
2464
2465 this.have.type('string');
2466 });
2467
2468 /**
2469 * Assert given object is array
2470 * @name Array
2471 * @memberOf Assertion
2472 * @category assertion types
2473 */
2474 Assertion.add('Array', function() {
2475 this.params = {operator: 'to be an array'};
2476
2477 this.have.class('Array');
2478 });
2479
2480 /**
2481 * Assert given object is boolean
2482 * @name Boolean
2483 * @memberOf Assertion
2484 * @category assertion types
2485 */
2486 Assertion.add('Boolean', function() {
2487 this.params = {operator: 'to be a boolean'};
2488
2489 this.have.type('boolean');
2490 });
2491
2492 /**
2493 * Assert given object is error
2494 * @name Error
2495 * @memberOf Assertion
2496 * @category assertion types
2497 */
2498 Assertion.add('Error', function() {
2499 this.params = {operator: 'to be an error'};
2500
2501 this.have.instanceOf(Error);
2502 });
2503
2504 /**
2505 * Assert given object is a date
2506 * @name Date
2507 * @memberOf Assertion
2508 * @category assertion types
2509 */
2510 Assertion.add('Date', function() {
2511 this.params = {operator: 'to be a date'};
2512
2513 this.have.instanceOf(Date);
2514 });
2515
2516 /**
2517 * Assert given object is null
2518 * @name null
2519 * @alias Assertion#Null
2520 * @memberOf Assertion
2521 * @category assertion types
2522 */
2523 Assertion.add('null', function() {
2524 this.params = {operator: 'to be null'};
2525
2526 this.assert(this.obj === null);
2527 });
2528
2529 Assertion.alias('null', 'Null');
2530
2531 /**
2532 * Assert given object has some internal [[Class]], via Object.prototype.toString call
2533 * @name class
2534 * @alias Assertion#Class
2535 * @memberOf Assertion
2536 * @category assertion types
2537 */
2538 Assertion.add('class', function(cls) {
2539 this.params = {operator: 'to have [[Class]] ' + cls};
2540
2541 this.assert(Object.prototype.toString.call(this.obj) === '[object ' + cls + ']');
2542 });
2543
2544 Assertion.alias('class', 'Class');
2545
2546 /**
2547 * Assert given object is undefined
2548 * @name undefined
2549 * @alias Assertion#Undefined
2550 * @memberOf Assertion
2551 * @category assertion types
2552 */
2553 Assertion.add('undefined', function() {
2554 this.params = {operator: 'to be undefined'};
2555
2556 this.assert(this.obj === void 0);
2557 });
2558
2559 Assertion.alias('undefined', 'Undefined');
2560
2561 /**
2562 * Assert given object supports es6 iterable protocol (just check
2563 * that object has property Symbol.iterator, which is a function)
2564 * @name iterable
2565 * @memberOf Assertion
2566 * @category assertion es6
2567 */
2568 Assertion.add('iterable', function() {
2569 this.params = {operator: 'to be iterable'};
2570
2571 should(this.obj).have.property(Symbol.iterator).which.is.a.Function();
2572 });
2573
2574 /**
2575 * Assert given object supports es6 iterator protocol (just check
2576 * that object has property next, which is a function)
2577 * @name iterator
2578 * @memberOf Assertion
2579 * @category assertion es6
2580 */
2581 Assertion.add('iterator', function() {
2582 this.params = {operator: 'to be iterator'};
2583
2584 should(this.obj).have.property('next').which.is.a.Function();
2585 });
2586
2587 /**
2588 * Assert given object is a generator object
2589 * @name generator
2590 * @memberOf Assertion
2591 * @category assertion es6
2592 */
2593 Assertion.add('generator', function() {
2594 this.params = {operator: 'to be generator'};
2595
2596 should(this.obj).be.iterable
2597 .and.iterator
2598 .and.it.is.equal(this.obj[Symbol.iterator]());
2599 });
2600};
2601
2602},{"../util":20}],19:[function(require,module,exports){
2603/*
2604 * Should
2605 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
2606 * MIT Licensed
2607 */
2608
2609
2610var util = require('./util');
2611
2612/**
2613 * Our function should
2614 *
2615 * @param {*} obj Object to assert
2616 * @returns {should.Assertion} Returns new Assertion for beginning assertion chain
2617 * @example
2618 *
2619 * var should = require('should');
2620 * should('abc').be.a.String();
2621 */
2622function should(obj) {
2623 return (new should.Assertion(obj));
2624}
2625
2626should.AssertionError = require('./assertion-error');
2627should.Assertion = require('./assertion');
2628
2629should.format = util.format;
2630should.type = require('should-type');
2631should.util = util;
2632
2633/**
2634 * Object with configuration.
2635 * It contains such properties:
2636 * * `checkProtoEql` boolean - Affect if `.eql` will check objects prototypes
2637 * * `plusZeroAndMinusZeroEqual` boolean - Affect if `.eql` will treat +0 and -0 as equal
2638 * Also it can contain options for should-format.
2639 *
2640 * @type {Object}
2641 * @memberOf should
2642 * @static
2643 * @example
2644 *
2645 * var a = { a: 10 }, b = Object.create(null);
2646 * b.a = 10;
2647 *
2648 * a.should.be.eql(b);
2649 * //not throws
2650 *
2651 * should.config.checkProtoEql = true;
2652 * a.should.be.eql(b);
2653 * //throws AssertionError: expected { a: 10 } to equal { a: 10 } (because A and B have different prototypes)
2654 */
2655should.config = require('./config');
2656
2657// Expose should to external world.
2658exports = module.exports = should;
2659
2660/**
2661 * Allow to extend given prototype with should property using given name. This getter will **unwrap** all standard wrappers like `Number`, `Boolean`, `String`.
2662 * Using `should(obj)` is the equivalent of using `obj.should` with known issues (like nulls and method calls etc).
2663 *
2664 * To add new assertions, need to use Assertion.add method.
2665 *
2666 * @param {string} [propertyName] Name of property to add. Default is `'should'`.
2667 * @param {Object} [proto] Prototype to extend with. Default is `Object.prototype`.
2668 * @memberOf should
2669 * @returns {{ name: string, descriptor: Object, proto: Object }} Descriptor enough to return all back
2670 * @static
2671 * @example
2672 *
2673 * var prev = should.extend('must', Object.prototype);
2674 *
2675 * 'abc'.must.startWith('a');
2676 *
2677 * var should = should.noConflict(prev);
2678 * should.not.exist(Object.prototype.must);
2679 */
2680should.extend = function(propertyName, proto) {
2681 propertyName = propertyName || 'should';
2682 proto = proto || Object.prototype;
2683
2684 var prevDescriptor = Object.getOwnPropertyDescriptor(proto, propertyName);
2685
2686 Object.defineProperty(proto, propertyName, {
2687 set: function() {
2688 },
2689 get: function() {
2690 return should(util.isWrapperType(this) ? this.valueOf() : this);
2691 },
2692 configurable: true
2693 });
2694
2695 return { name: propertyName, descriptor: prevDescriptor, proto: proto };
2696};
2697
2698/**
2699 * Delete previous extension. If `desc` missing it will remove default extension.
2700 *
2701 * @param {{ name: string, descriptor: Object, proto: Object }} [desc] Returned from `should.extend` object
2702 * @memberOf should
2703 * @returns {Function} Returns should function
2704 * @static
2705 * @example
2706 *
2707 * var should = require('should').noConflict();
2708 *
2709 * should(Object.prototype).not.have.property('should');
2710 *
2711 * var prev = should.extend('must', Object.prototype);
2712 * 'abc'.must.startWith('a');
2713 * should.noConflict(prev);
2714 *
2715 * should(Object.prototype).not.have.property('must');
2716 */
2717should.noConflict = function(desc) {
2718 desc = desc || should._prevShould;
2719
2720 if(desc) {
2721 delete desc.proto[desc.name];
2722
2723 if(desc.descriptor) {
2724 Object.defineProperty(desc.proto, desc.name, desc.descriptor);
2725 }
2726 }
2727 return should;
2728};
2729
2730/**
2731 * Simple utility function for a bit more easier should assertion extension
2732 * @param {Function} f So called plugin function. It should accept 2 arguments: `should` function and `Assertion` constructor
2733 * @memberOf should
2734 * @returns {Function} Returns `should` function
2735 * @static
2736 * @example
2737 *
2738 * should.use(function(should, Assertion) {
2739 * Assertion.add('asset', function() {
2740 * this.params = { operator: 'to be asset' };
2741 *
2742 * this.obj.should.have.property('id').which.is.a.Number();
2743 * this.obj.should.have.property('path');
2744 * })
2745 * })
2746 */
2747should.use = function(f) {
2748 f(should, should.Assertion);
2749 return this;
2750};
2751
2752should
2753 .use(require('./ext/assert'))
2754 .use(require('./ext/chain'))
2755 .use(require('./ext/bool'))
2756 .use(require('./ext/number'))
2757 .use(require('./ext/eql'))
2758 .use(require('./ext/type'))
2759 .use(require('./ext/string'))
2760 .use(require('./ext/property'))
2761 .use(require('./ext/error'))
2762 .use(require('./ext/match'))
2763 .use(require('./ext/contain'))
2764 .use(require('./ext/promise'));
2765
2766},{"./assertion":4,"./assertion-error":3,"./config":5,"./ext/assert":7,"./ext/bool":8,"./ext/chain":9,"./ext/contain":10,"./ext/eql":11,"./ext/error":12,"./ext/match":13,"./ext/number":14,"./ext/promise":15,"./ext/property":16,"./ext/string":17,"./ext/type":18,"./util":20,"should-type":27}],20:[function(require,module,exports){
2767/*
2768 * Should
2769 * Copyright(c) 2010-2015 TJ Holowaychuk <tj@vision-media.ca>
2770 * MIT Licensed
2771 */
2772
2773var type = require('should-type');
2774var config = require('./config');
2775
2776/**
2777 * Check if given obj just a primitive type wrapper
2778 * @param {Object} obj
2779 * @returns {boolean}
2780 * @private
2781 */
2782exports.isWrapperType = function(obj) {
2783 return obj instanceof Number || obj instanceof String || obj instanceof Boolean;
2784};
2785
2786exports.merge = function(a, b) {
2787 if(a && b) {
2788 for(var key in b) {
2789 a[key] = b[key];
2790 }
2791 }
2792 return a;
2793};
2794
2795var hasOwnProperty = Object.prototype.hasOwnProperty;
2796
2797exports.forEach = function forEach(obj, f, context) {
2798 if(exports.isGeneratorFunction(obj)) {
2799 return forEach(obj(), f, context);
2800 } else if (exports.isGeneratorObject(obj)) {
2801 var value = obj.next();
2802 while(!value.done) {
2803 if(f.call(context, value.value, 'value', obj) === false)
2804 return;
2805 value = obj.next();
2806 }
2807 } else {
2808 for(var prop in obj) {
2809 if(hasOwnProperty.call(obj, prop)) {
2810 if(f.call(context, obj[prop], prop, obj) === false)
2811 return;
2812 }
2813 }
2814 }
2815};
2816
2817exports.some = function(obj, f, context) {
2818 var res = false;
2819 exports.forEach(obj, function(value, key) {
2820 if(f.call(context, value, key, obj)) {
2821 res = true;
2822 return false;
2823 }
2824 }, context);
2825 return res;
2826};
2827
2828exports.isEmptyObject = function(obj) {
2829 for(var prop in obj) {
2830 if(hasOwnProperty.call(obj, prop)) {
2831 return false;
2832 }
2833 }
2834 return true;
2835};
2836
2837exports.isIndexable = function(obj) {
2838 var t = type(obj);
2839 return (t.type === type.OBJECT && t.cls === type.ARRAY) ||
2840 (t.type === type.OBJECT && t.cls === type.BUFFER) ||
2841 (t.type === type.OBJECT && t.cls === type.ARGUMENTS) ||
2842 (t.type === type.OBJECT && t.cls === type.ARRAY_BUFFER) ||
2843 (t.type === type.OBJECT && t.cls === type.TYPED_ARRAY) ||
2844 (t.type === type.OBJECT && t.cls === type.DATA_VIEW) ||
2845 (t.type === type.OBJECT && t.cls === type.STRING) ||
2846 (t.type === type.STRING);
2847};
2848
2849exports.length = function(obj) {
2850 var t = type(obj);
2851 switch(t.type) {
2852 case type.STRING:
2853 return obj.length;
2854 case type.OBJECT:
2855 switch(t.cls) {
2856 case type.ARRAY_BUFFER:
2857 case type.TYPED_ARRAY:
2858 case type.DATA_VIEW:
2859 return obj.byteLength;
2860
2861 case type.ARRAY:
2862 case type.BUFFER:
2863 case type.ARGUMENTS:
2864 case type.FUNCTION:
2865 return obj.length;
2866 }
2867 }
2868};
2869
2870exports.convertPropertyName = function(name) {
2871 if(typeof name == 'symbol') {
2872 return name;
2873 } else {
2874 return String(name);
2875 }
2876};
2877
2878exports.isGeneratorObject = function(obj) {
2879 if(!obj) return false;
2880
2881 return typeof obj.next == 'function' &&
2882 typeof obj[Symbol.iterator] == 'function' &&
2883 obj[Symbol.iterator]() === obj;
2884};
2885
2886//TODO find better way
2887exports.isGeneratorFunction = function(f) {
2888 if(typeof f != 'function') return false;
2889
2890 return /^function\s*\*\s*/.test(f.toString());
2891};
2892
2893exports.format = function(value, opts) {
2894 return config.getFormatter(opts).format(value);
2895};
2896
2897exports.functionName = require('should-format').Formatter.functionName;
2898
2899exports.formatProp = function(value) {
2900 return config.getFormatter().formatPropertyName(String(value));
2901};
2902
2903},{"./config":5,"should-format":23,"should-type":27}],21:[function(require,module,exports){
2904module.exports = function format(msg) {
2905 var args = arguments;
2906 for(var i = 1, l = args.length; i < l; i++) {
2907 msg = msg.replace(/%s/, args[i]);
2908 }
2909 return msg;
2910}
2911
2912},{}],22:[function(require,module,exports){
2913var getType = require('should-type');
2914var format = require('./format');
2915var hasOwnProperty = Object.prototype.hasOwnProperty;
2916
2917function makeResult(r, path, reason, a, b) {
2918 var o = {result: r};
2919 if(!r) {
2920 o.path = path;
2921 o.reason = reason;
2922 o.a = a;
2923 o.b = b;
2924 }
2925 return o;
2926}
2927
2928var EQUALS = makeResult(true);
2929
2930function typeToString(t) {
2931 return t.type + (t.cls ? '(' + t.cls + (t.sub ? ' ' + t.sub : '') + ')' : '');
2932}
2933
2934
2935
2936var REASON = {
2937 PLUS_0_AND_MINUS_0: '+0 is not equal to -0',
2938 DIFFERENT_TYPES: 'A has type %s and B has type %s',
2939 NAN_NUMBER: 'NaN is not equal to any number',
2940 EQUALITY: 'A is not equal to B',
2941 EQUALITY_PROTOTYPE: 'A and B have different prototypes',
2942 WRAPPED_VALUE: 'A wrapped value is not equal to B wrapped value',
2943 FUNCTION_SOURCES: 'function A is not equal to B by source code value (via .toString call)',
2944 MISSING_KEY: '%s has no key %s',
2945 CIRCULAR_VALUES: 'A has circular reference that was visited not in the same time as B',
2946 SET_MAP_MISSING_KEY: 'Set/Map missing key',
2947 MAP_VALUE_EQUALITY: 'Values of the same key in A and B is not equal'
2948};
2949
2950
2951function eqInternal(a, b, opts, stackA, stackB, path, fails) {
2952 var r = EQUALS;
2953
2954 function result(comparison, reason) {
2955 if(arguments.length > 2) {
2956 var args = Array.prototype.slice.call(arguments, 2);
2957 reason = format.apply(null, [reason].concat(args));
2958 }
2959 var res = makeResult(comparison, path, reason, a, b);
2960 if(!comparison && opts.collectAllFails) {
2961 fails.push(res);
2962 }
2963 return res;
2964 }
2965
2966 function checkPropertyEquality(property) {
2967 return eqInternal(a[property], b[property], opts, stackA, stackB, path.concat([property]), fails);
2968 }
2969
2970 function checkAlso(a1, b1) {
2971 return eqInternal(a1, b1, opts, stackA, stackB, path, fails);
2972 }
2973
2974 // equal a and b exit early
2975 if(a === b) {
2976 // check for +0 !== -0;
2977 return result(a !== 0 || (1 / a == 1 / b) || opts.plusZeroAndMinusZeroEqual, REASON.PLUS_0_AND_MINUS_0);
2978 }
2979
2980 var l, p;
2981
2982 var typeA = getType(a),
2983 typeB = getType(b);
2984
2985 var key;
2986
2987 // if objects has different types they are not equal
2988 var typeDifferent = typeA.type !== typeB.type || typeA.cls !== typeB.cls;
2989
2990 if(typeDifferent || ((opts.checkSubType && typeA.sub !== typeB.sub) || !opts.checkSubType)) {
2991 return result(false, REASON.DIFFERENT_TYPES, typeToString(typeA), typeToString(typeB));
2992 }
2993
2994 //early checks for types
2995 switch(typeA.type) {
2996 case 'number':
2997 // NaN !== NaN
2998 return (a !== a) ? result(b !== b, REASON.NAN_NUMBER)
2999 : result(a === b, REASON.EQUALITY);
3000
3001 case 'boolean':
3002 case 'string':
3003 return result(a === b, REASON.EQUALITY);
3004
3005 case 'function':
3006 // functions are compared by their source code
3007 r = checkAlso(a.toString(), b.toString());
3008 if(!r.result) {
3009 r.reason = REASON.FUNCTION_SOURCES;
3010 if(!opts.collectAllFails) return r;
3011 }
3012
3013 break;//check user properties
3014
3015 case 'object':
3016 // additional checks for object instances
3017 switch(typeA.cls) {
3018 // check regexp flags
3019 // TODO add es6 flags
3020 case 'regexp':
3021 p = ['source', 'global', 'multiline', 'lastIndex', 'ignoreCase'];
3022 while(p.length) {
3023 r = checkPropertyEquality(p.shift());
3024 if(!r.result && !opts.collectAllFails) return r;
3025 }
3026 break;//check user properties
3027
3028 //check by timestamp only (using .valueOf)
3029 case 'date':
3030 if(+a !== +b) {
3031 r = result(false, REASON.EQUALITY);
3032 if(!r.result && !opts.collectAllFails) return r;
3033 }
3034 break;//check user properties
3035
3036 //primitive type wrappers
3037 case 'number':
3038 case 'boolean':
3039 case 'string':
3040 //check their internal value
3041 r = checkAlso(a.valueOf(), b.valueOf());
3042 if(!r.result) {
3043 r.reason = REASON.WRAPPED_VALUE;
3044 if(!opts.collectAllFails) return r;
3045 }
3046 break;//check user properties
3047
3048 //node buffer
3049 case 'buffer':
3050 //if length different it is obviously different
3051 r = checkPropertyEquality('length');
3052 if(!r.result && !opts.collectAllFails) return r;
3053
3054 l = a.length;
3055 while(l--) {
3056 r = checkPropertyEquality(l);
3057 if(!r.result && !opts.collectAllFails) return r;
3058 }
3059
3060 //we do not check for user properties because
3061 //node Buffer have some strange hidden properties
3062 return EQUALS;
3063
3064 case 'error':
3065 //check defined properties
3066 p = ['name', 'message'];
3067 while(p.length) {
3068 r = checkPropertyEquality(p.shift());
3069 if(!r.result && !opts.collectAllFails) return r;
3070 }
3071
3072 break;//check user properties
3073
3074 case 'array':
3075 case 'arguments':
3076 case 'typed-array':
3077 r = checkPropertyEquality('length');
3078 if(!r.result && !opts.collectAllFails) return r;
3079
3080 break;//check user properties
3081
3082 case 'array-buffer':
3083 r = checkPropertyEquality('byteLength');
3084 if(!r.result && !opts.collectAllFails) return r;
3085
3086 break;//check user properties
3087
3088 case 'map':
3089 case 'set':
3090 r = checkPropertyEquality('size');
3091 if(!r.result && !opts.collectAllFails) return r;
3092
3093 stackA.push(a);
3094 stackB.push(b);
3095
3096 var itA = a.entries();
3097 var nextA = itA.next();
3098
3099 while(!nextA.done) {
3100 key = nextA.value[0];
3101 //first check for primitive key if we can do light check
3102 //using .has and .get
3103 if(getType(key).type != 'object') {
3104 if(b.has(key)) {
3105 if(typeA.cls == 'map') {
3106 //for map we also check its value to be equal
3107 var value = b.get(key);
3108 r = checkAlso(nextA.value[1], value);
3109 if(!r.result) {
3110 r.a = nextA.value;
3111 r.b = value;
3112 r.reason = REASON.MAP_VALUE_EQUALITY;
3113
3114 if(!opts.collectAllFails) break;
3115 }
3116 }
3117
3118 } else {
3119 r = result(false, REASON.SET_MAP_MISSING_KEY);
3120 r.a = key;
3121 r.b = key;
3122
3123 if(!opts.collectAllFails) break;
3124 }
3125 } else {
3126 //heavy check
3127 //we search by iterator for key equality using equal
3128 var itB = b.entries();
3129 var nextB = itB.next();
3130
3131 while(!nextB.done) {
3132 //first check for keys
3133 r = checkAlso(nextA.value[0], nextB.value[0]);
3134
3135 if(!r.result) {
3136 r.reason = REASON.SET_MAP_MISSING_KEY;
3137 r.a = key;
3138 r.b = key;
3139 } else {
3140 if(typeA.cls == 'map') {
3141 r = checkAlso(nextA.value[1], nextB.value[1]);
3142
3143 if(!r.result) {
3144 r.a = nextA.value;
3145 r.b = nextB.value;
3146 r.reason = REASON.MAP_VALUE_EQUALITY;
3147 }
3148 }
3149
3150 if(!opts.collectAllFails) break;
3151 }
3152
3153 nextB = itB.next();
3154 }
3155 }
3156
3157 if(!r.result && !opts.collectAllFails) break;
3158
3159 nextA = itA.next();
3160 }
3161
3162 stackA.pop();
3163 stackB.pop();
3164
3165 if(!r.result) {
3166 r.reason = REASON.SET_MAP_MISSING_ENTRY;
3167 if(!opts.collectAllFails) return r;
3168 }
3169
3170 break; //check user properties
3171 }
3172 }
3173
3174 // compare deep objects and arrays
3175 // stacks contain references only
3176 //
3177
3178 l = stackA.length;
3179 while(l--) {
3180 if(stackA[l] == a) {
3181 return result(stackB[l] == b, REASON.CIRCULAR_VALUES);
3182 }
3183 }
3184
3185 // add `a` and `b` to the stack of traversed objects
3186 stackA.push(a);
3187 stackB.push(b);
3188
3189 for(key in b) {
3190 if(hasOwnProperty.call(b, key)) {
3191 r = result(hasOwnProperty.call(a, key), REASON.MISSING_KEY, 'A', key);
3192 if(!r.result && !opts.collectAllFails) break;
3193
3194 if(r.result) {
3195 r = checkPropertyEquality(key);
3196 if(!r.result && !opts.collectAllFails) break;
3197 }
3198 }
3199 }
3200
3201 if(r.result || opts.collectAllFails) {
3202 // ensure both objects have the same number of properties
3203 for(key in a) {
3204 if(hasOwnProperty.call(a, key)) {
3205 r = result(hasOwnProperty.call(b, key), REASON.MISSING_KEY, 'B', key);
3206 if(!r.result && !opts.collectAllFails) return r;
3207 }
3208 }
3209 }
3210
3211 stackA.pop();
3212 stackB.pop();
3213
3214 if(!r.result && !opts.collectAllFails) return r;
3215
3216 var prototypesEquals = false, canComparePrototypes = false;
3217
3218 if(opts.checkProtoEql) {
3219 if(Object.getPrototypeOf) {//TODO should i check prototypes for === or use eq?
3220 prototypesEquals = Object.getPrototypeOf(a) === Object.getPrototypeOf(b);
3221 canComparePrototypes = true;
3222 }
3223
3224 if(canComparePrototypes && !prototypesEquals) {
3225 r = result(prototypesEquals, REASON.EQUALITY_PROTOTYPE);
3226 r.showReason = true;
3227 if(!r.result && !opts.collectAllFails) {
3228 return r;
3229 }
3230 }
3231 }
3232
3233 return EQUALS;
3234}
3235
3236var defaultOptions = {
3237 checkProtoEql: true,
3238 checkSubType: true,
3239 plusZeroAndMinusZeroEqual: false
3240};
3241
3242function eq(a, b, opts) {
3243 opts = opts || {};
3244 if(typeof opts.checkProtoEql !== 'boolean') {
3245 opts.checkProtoEql = defaultOptions.checkProtoEql;
3246 }
3247 if(typeof opts.checkSubType !== 'boolean') {
3248 opts.checkSubType = defaultOptions.checkSubType;
3249 }
3250 if(typeof opts.plusZeroAndMinusZeroEqual !== 'boolean') {
3251 opts.plusZeroAndMinusZeroEqual = defaultOptions.plusZeroAndMinusZeroEqual;
3252 }
3253
3254 var fails = [];
3255 var r = eqInternal(a, b, opts, [], [], [], fails);
3256 return opts.collectAllFails ? fails : r;
3257}
3258
3259module.exports = eq;
3260
3261eq.r = REASON;
3262
3263},{"./format":21,"should-type":27}],23:[function(require,module,exports){
3264var getType = require('should-type');
3265var util = require('./util');
3266
3267function genKeysFunc(f) {
3268 return function(value) {
3269 var k = f(value);
3270 k.sort();
3271 return k;
3272 };
3273}
3274
3275
3276function Formatter(opts) {
3277 opts = opts || {};
3278
3279 this.seen = [];
3280 this.keys = genKeysFunc(opts.keys === false ? Object.getOwnPropertyNames : Object.keys);
3281
3282 this.maxLineLength = typeof opts.maxLineLength === 'number' ? opts.maxLineLength : 60;
3283 this.propSep = opts.propSep || ',';
3284
3285 this.isUTCdate = !!opts.isUTCdate;
3286}
3287
3288Formatter.prototype = {
3289 constructor: Formatter,
3290
3291 format: function(value) {
3292 var t = getType(value);
3293 var name1 = t.type, name2 = t.type;
3294 if(t.cls) {
3295 name1 += '_' + t.cls;
3296 name2 += '_' + t.cls;
3297 }
3298 if(t.sub) {
3299 name2 += '_' + t.sub;
3300 }
3301 var f = this['_format_' + name2] || this['_format_' + name1] || this['_format_' + t.type] || this.defaultFormat;
3302 return f.call(this, value).trim();
3303 },
3304
3305 _formatObject: function(value, opts) {
3306 opts = opts || {};
3307 var mainKeys = opts.keys || this.keys(value);
3308
3309 var len = 0;
3310
3311 var formatPropertyValue = opts.formatPropertyValue || this.formatPropertyValue;
3312 var formatPropertyName = opts.formatPropertyName || this.formatPropertyName;
3313 var keyValueSep = opts.keyValueSep || ': ';
3314 var keyFilter = opts.keyFilter || function() { return true; };
3315
3316 this.seen.push(value);
3317 var keys = [];
3318
3319 mainKeys.forEach(function(key) {
3320 if(!keyFilter(key)) return;
3321
3322 var fName = formatPropertyName.call(this, key);
3323
3324 var f = (fName ? fName + keyValueSep : '') + formatPropertyValue.call(this, value, key);
3325 len += f.length;
3326 keys.push(f);
3327 }, this);
3328 this.seen.pop();
3329
3330 (opts.additionalProperties || []).forEach(function(keyValue) {
3331 var f = keyValue[0] + keyValueSep + this.format(keyValue[1]);
3332 len += f.length;
3333 keys.push(f);
3334 }, this);
3335
3336 var prefix = opts.prefix || Formatter.constructorName(value) || '';
3337 if(prefix.length > 0) prefix += ' ';
3338
3339 var lbracket, rbracket;
3340 if(Array.isArray(opts.brackets)) {
3341 lbracket = opts.brackets && opts.brackets[0];
3342 rbracket = opts.brackets && opts.brackets[1];
3343 } else {
3344 lbracket = '{';
3345 rbracket = '}';
3346 }
3347
3348 var rootValue = opts.value || '';
3349
3350 if(keys.length === 0)
3351 return rootValue || (prefix + lbracket + rbracket);
3352
3353 if(len <= this.maxLineLength) {
3354 return prefix + lbracket + ' ' + (rootValue ? rootValue + ' ' : '') + keys.join(this.propSep + ' ') + ' ' + rbracket;
3355 } else {
3356 return prefix + lbracket + '\n' + (rootValue ? ' ' + rootValue + '\n' : '') + keys.map(util.addSpaces).join(this.propSep + '\n') + '\n' + rbracket;
3357 }
3358 },
3359
3360 formatObject: function(value, prefix, props) {
3361 props = props || this.keys(value);
3362
3363 var len = 0;
3364
3365 this.seen.push(value);
3366 props = props.map(function(prop) {
3367 var f = this.formatProperty(value, prop);
3368 len += f.length;
3369 return f;
3370 }, this);
3371 this.seen.pop();
3372
3373 if(props.length === 0) return '{}';
3374
3375 if(len <= this.maxLineLength) {
3376 return '{ ' + (prefix ? prefix + ' ' : '') + props.join(this.propSep + ' ') + ' }';
3377 } else {
3378 return '{' + '\n' + (prefix ? ' ' + prefix + '\n' : '') + props.map(util.addSpaces).join(this.propSep + '\n') + '\n' + '}';
3379 }
3380 },
3381
3382 formatPropertyName: function(name) {
3383 return name.match(/^[a-zA-Z_$][a-zA-Z_$0-9]*$/) ? name : this.format(name);
3384 },
3385
3386 formatProperty: function(value, prop) {
3387 var desc = Formatter.getPropertyDescriptor(value, prop);
3388
3389 var propName = this.formatPropertyName(prop);
3390
3391 var propValue = desc.get && desc.set ?
3392 '[Getter/Setter]' : desc.get ?
3393 '[Getter]' : desc.set ?
3394 '[Setter]' : this.seen.indexOf(desc.value) >= 0 ?
3395 '[Circular]' :
3396 this.format(desc.value);
3397
3398 return propName + ': ' + propValue;
3399 },
3400
3401 formatPropertyValue: function(value, prop) {
3402 var desc = Formatter.getPropertyDescriptor(value, prop);
3403
3404 var propValue = desc.get && desc.set ?
3405 '[Getter/Setter]' : desc.get ?
3406 '[Getter]' : desc.set ?
3407 '[Setter]' : this.seen.indexOf(desc.value) >= 0 ?
3408 '[Circular]' :
3409 this.format(desc.value);
3410
3411 return propValue;
3412 }
3413};
3414
3415Formatter.add = function add(type, cls, sub, f) {
3416 var args = Array.prototype.slice.call(arguments);
3417 f = args.pop();
3418 Formatter.prototype['_format_' + args.join('_')] = f;
3419};
3420
3421Formatter.formatObjectWithPrefix = function formatObjectWithPrefix(f) {
3422 return function(value) {
3423 var prefix = f.call(this, value);
3424 var props = this.keys(value);
3425 if(props.length == 0) return prefix;
3426 else return this.formatObject(value, prefix, props);
3427 };
3428};
3429
3430var functionNameRE = /^\s*function\s*(\S*)\s*\(/;
3431
3432Formatter.functionName = function functionName(f) {
3433 if(f.name) {
3434 return f.name;
3435 }
3436 var matches = f.toString().match(functionNameRE);
3437 if (matches === null) {
3438 // `functionNameRE` doesn't match arrow functions.
3439 return '';
3440 }
3441 var name = matches[1];
3442 return name;
3443};
3444
3445Formatter.constructorName = function(obj) {
3446 while (obj) {
3447 var descriptor = Object.getOwnPropertyDescriptor(obj, 'constructor');
3448 if (descriptor !== undefined &&
3449 typeof descriptor.value === 'function') {
3450
3451 var name = Formatter.functionName(descriptor.value);
3452 if(name !== '') {
3453 return name;
3454 }
3455 }
3456
3457 obj = Object.getPrototypeOf(obj);
3458 }
3459};
3460
3461Formatter.getPropertyDescriptor = function(obj, value) {
3462 var desc;
3463 try {
3464 desc = Object.getOwnPropertyDescriptor(obj, value) || {value: obj[value]};
3465 } catch(e) {
3466 desc = {value: e};
3467 }
3468 return desc;
3469};
3470
3471Formatter.generateFunctionForIndexedArray = function generateFunctionForIndexedArray(lengthProp, name, padding) {
3472 return function(value) {
3473 var max = this.byteArrayMaxLength || 50;
3474 var length = value[lengthProp];
3475 var formattedValues = [];
3476 var len = 0;
3477 for(var i = 0; i < max && i < length; i++) {
3478 var b = value[i] || 0;
3479 var v = util.pad0(b.toString(16), padding);
3480 len += v.length;
3481 formattedValues.push(v);
3482 }
3483 var prefix = value.constructor.name || name || '';
3484 if(prefix) prefix += ' ';
3485
3486 if(formattedValues.length === 0)
3487 return prefix + '[]';
3488
3489 if(len <= this.maxLineLength) {
3490 return prefix + '[ ' + formattedValues.join(this.propSep + ' ') + ' ' + ']';
3491 } else {
3492 return prefix + '[\n' + formattedValues.map(util.addSpaces).join(this.propSep + '\n') + '\n' + ']';
3493 }
3494 };
3495};
3496
3497Formatter.add('undefined', function() { return 'undefined' });
3498Formatter.add('null', function() { return 'null' });
3499Formatter.add('boolean', function(value) { return value ? 'true': 'false' });
3500Formatter.add('symbol', function(value) { return value.toString() });
3501
3502['number', 'boolean'].forEach(function(name) {
3503 Formatter.add('object', name, function(value) {
3504 return this._formatObject(value, {
3505 additionalProperties: [['[[PrimitiveValue]]', value.valueOf()]]
3506 });
3507 });
3508});
3509
3510Formatter.add('object', 'string', function(value) {
3511 var realValue = value.valueOf();
3512
3513 return this._formatObject(value, {
3514 keyFilter: function(key) {
3515 //skip useless indexed properties
3516 return !(key.match(/\d+/) && parseInt(key, 10) < realValue.length);
3517 },
3518 additionalProperties: [['[[PrimitiveValue]]', realValue]]
3519 });
3520});
3521
3522Formatter.add('object', 'regexp', function(value) {
3523 return this._formatObject(value, {
3524 value: String(value)
3525 });
3526});
3527
3528Formatter.add('number', function(value) {
3529 if(value === 0 && 1 / value < 0) return '-0';
3530 return String(value);
3531});
3532
3533Formatter.add('string', function(value) {
3534 return '\'' + JSON.stringify(value).replace(/^"|"$/g, '')
3535 .replace(/'/g, "\\'")
3536 .replace(/\\"/g, '"') + '\'';
3537});
3538
3539Formatter.add('object', function(value) {
3540 return this._formatObject(value);
3541});
3542
3543Formatter.add('object', 'arguments', function(value) {
3544 return this._formatObject(value, {
3545 prefix: 'Arguments',
3546 formatPropertyName: function(key) {
3547 if(!key.match(/\d+/)) {
3548 return this.formatPropertyName(key);
3549 }
3550 },
3551 brackets: ['[', ']']
3552 });
3553});
3554
3555Formatter.add('object', 'array', function(value) {
3556 return this._formatObject(value, {
3557 formatPropertyName: function(key) {
3558 if(!key.match(/\d+/)) {
3559 return this.formatPropertyName(key);
3560 }
3561 },
3562 brackets: ['[', ']']
3563 });
3564});
3565
3566
3567function formatDate(value, isUTC) {
3568 var prefix = isUTC ? 'UTC' : '';
3569
3570 var date = value['get' + prefix + 'FullYear']() +
3571 '-' +
3572 util.pad0(value['get' + prefix + 'Month']() + 1, 2) +
3573 '-' +
3574 util.pad0(value['get' + prefix + 'Date'](), 2);
3575
3576 var time = util.pad0(value['get' + prefix + 'Hours'](), 2) +
3577 ':' +
3578 util.pad0(value['get' + prefix + 'Minutes'](), 2) +
3579 ':' +
3580 util.pad0(value['get' + prefix + 'Seconds'](), 2) +
3581 '.' +
3582 util.pad0(value['get' + prefix + 'Milliseconds'](), 3);
3583
3584 var to = value.getTimezoneOffset();
3585 var absTo = Math.abs(to);
3586 var hours = Math.floor(absTo / 60);
3587 var minutes = absTo - hours * 60;
3588 var tzFormat = (to < 0 ? '+' : '-') + util.pad0(hours, 2) + util.pad0(minutes, 2);
3589
3590 return date + ' ' + time + (isUTC ? '' : ' ' + tzFormat);
3591}
3592
3593Formatter.add('object', 'date', function(value) {
3594 return this._formatObject(value, { value: formatDate(value, this.isUTCdate) });
3595});
3596
3597Formatter.add('function', function(value) {
3598 return this._formatObject(value, {
3599 additionalProperties: [['name', Formatter.functionName(value)]]
3600 });
3601});
3602
3603Formatter.add('object', 'error', function(value) {
3604 return this._formatObject(value, {
3605 prefix: value.name,
3606 additionalProperties: [['message', value.message]]
3607 });
3608});
3609
3610Formatter.add('object', 'buffer', Formatter.generateFunctionForIndexedArray('length', 'Buffer', 2));
3611
3612Formatter.add('object', 'array-buffer', Formatter.generateFunctionForIndexedArray('byteLength', 'ArrayBuffer', 2));
3613
3614Formatter.add('object', 'typed-array', 'int8', Formatter.generateFunctionForIndexedArray('length', 'Int8Array', 2));
3615Formatter.add('object', 'typed-array', 'uint8', Formatter.generateFunctionForIndexedArray('length', 'Uint8Array', 2));
3616Formatter.add('object', 'typed-array', 'uint8clamped', Formatter.generateFunctionForIndexedArray('length', 'Uint8ClampedArray', 2));
3617
3618Formatter.add('object', 'typed-array', 'int16', Formatter.generateFunctionForIndexedArray('length', 'Int16Array', 4));
3619Formatter.add('object', 'typed-array', 'uint16', Formatter.generateFunctionForIndexedArray('length', 'Uint16Array', 4));
3620
3621Formatter.add('object', 'typed-array', 'int32', Formatter.generateFunctionForIndexedArray('length', 'Int32Array', 8));
3622Formatter.add('object', 'typed-array', 'uint32', Formatter.generateFunctionForIndexedArray('length', 'Uint32Array', 8));
3623
3624//TODO add float32 and float64
3625
3626Formatter.add('object', 'promise', function() {
3627 return '[Promise]';//TODO it could be nice to inspect its state and value
3628});
3629
3630Formatter.add('object', 'xhr', function() {
3631 return '[XMLHttpRequest]';//TODO it could be nice to inspect its state
3632});
3633
3634Formatter.add('object', 'html-element', function(value) {
3635 return value.outerHTML;
3636});
3637
3638Formatter.add('object', 'html-element', '#text', function(value) {
3639 return value.nodeValue;
3640});
3641
3642Formatter.add('object', 'html-element', '#document', function(value) {
3643 return value.documentElement.outerHTML;
3644});
3645
3646Formatter.add('object', 'host', function() {
3647 return '[Host]';
3648});
3649
3650Formatter.add('object', 'set', function(value) {
3651 var iter = value.values();
3652 var len = 0;
3653
3654 this.seen.push(value);
3655
3656 var props = [];
3657
3658 var next = iter.next();
3659 while(!next.done) {
3660 var val = next.value;
3661 var f = this.format(val);
3662 len += f.length;
3663 props.push(f);
3664
3665 next = iter.next();
3666 }
3667
3668 this.seen.pop();
3669
3670 if(props.length === 0) return 'Set {}';
3671
3672 if(len <= this.maxLineLength) {
3673 return 'Set { ' + props.join(this.propSep + ' ') + ' }';
3674 } else {
3675 return 'Set {\n' + props.map(util.addSpaces).join(this.propSep + '\n') + '\n' + '}';
3676 }
3677});
3678
3679Formatter.add('object', 'map', function(value) {
3680 var iter = value.entries();
3681 var len = 0;
3682
3683 this.seen.push(value);
3684
3685 var props = [];
3686
3687 var next = iter.next();
3688 while(!next.done) {
3689 var val = next.value;
3690 var fK = this.format(val[0]);
3691 var fV = this.format(val[1]);
3692
3693 var f;
3694 if((fK.length + fV.length + 4) <= this.maxLineLength) {
3695 f = fK + ' => ' + fV;
3696 } else {
3697 f = fK + ' =>\n' + fV;
3698 }
3699
3700 len += fK.length + fV.length + 4;
3701 props.push(f);
3702
3703 next = iter.next();
3704 }
3705
3706 this.seen.pop();
3707
3708 if(props.length === 0) return 'Map {}';
3709
3710 if(len <= this.maxLineLength) {
3711 return 'Map { ' + props.join(this.propSep + ' ') + ' }';
3712 } else {
3713 return 'Map {\n' + props.map(util.addSpaces).join(this.propSep + '\n') + '\n' + '}';
3714 }
3715});
3716
3717Formatter.prototype.defaultFormat = Formatter.prototype._format_object;
3718
3719function defaultFormat(value, opts) {
3720 return new Formatter(opts).format(value);
3721}
3722
3723defaultFormat.Formatter = Formatter;
3724module.exports = defaultFormat;
3725
3726},{"./util":26,"should-type":24}],24:[function(require,module,exports){
3727var toString = Object.prototype.toString;
3728
3729var types = require('./types');
3730
3731/**
3732 * Simple data function to store type information
3733 * @param {string} type Usually what is returned from typeof
3734 * @param {string} cls Sanitized @Class via Object.prototype.toString
3735 * @param {string} sub If type and cls the same, and need to specify somehow
3736 * @private
3737 * @example
3738 *
3739 * //for null
3740 * new Type('null');
3741 *
3742 * //for Date
3743 * new Type('object', 'date');
3744 *
3745 * //for Uint8Array
3746 *
3747 * new Type('object', 'typed-array', 'uint8');
3748 */
3749function Type(type, cls, sub) {
3750 this.type = type;
3751 this.cls = cls;
3752 this.sub = sub;
3753}
3754
3755/**
3756 * Function to store type checks
3757 * @private
3758 */
3759function TypeChecker() {
3760 this.checks = [];
3761}
3762
3763TypeChecker.prototype = {
3764 add: function(func) {
3765 this.checks.push(func);
3766 return this;
3767 },
3768
3769 addTypeOf: function(type, res) {
3770 return this.add(function(obj, tpeOf) {
3771 if(tpeOf === type) {
3772 return new Type(res);
3773 }
3774 });
3775 },
3776
3777 addClass: function(cls, res, sub) {
3778 return this.add(function(obj, tpeOf, objCls) {
3779 if(objCls === cls) {
3780 return new Type(types.OBJECT, res, sub);
3781 }
3782 });
3783 },
3784
3785 getType: function(obj) {
3786 var typeOf = typeof obj;
3787 var cls = toString.call(obj);
3788
3789 for(var i = 0, l = this.checks.length; i < l; i++) {
3790 var res = this.checks[i].call(this, obj, typeOf, cls);
3791 if(typeof res !== 'undefined') return res;
3792 }
3793
3794 }
3795};
3796
3797var main = new TypeChecker();
3798
3799//TODO add iterators
3800
3801main
3802 .addTypeOf(types.NUMBER, types.NUMBER)
3803 .addTypeOf(types.UNDEFINED, types.UNDEFINED)
3804 .addTypeOf(types.STRING, types.STRING)
3805 .addTypeOf(types.BOOLEAN, types.BOOLEAN)
3806 .addTypeOf(types.FUNCTION, types.FUNCTION)
3807 .addTypeOf(types.SYMBOL, types.SYMBOL)
3808 .add(function(obj, tpeOf) {
3809 if(obj === null) return new Type(types.NULL);
3810 })
3811 .addClass('[object String]', types.STRING)
3812 .addClass('[object Boolean]', types.BOOLEAN)
3813 .addClass('[object Number]', types.NUMBER)
3814 .addClass('[object Array]', types.ARRAY)
3815 .addClass('[object RegExp]', types.REGEXP)
3816 .addClass('[object Error]', types.ERROR)
3817 .addClass('[object Date]', types.DATE)
3818 .addClass('[object Arguments]', types.ARGUMENTS)
3819 .addClass('[object Math]')
3820 .addClass('[object JSON]')
3821 .addClass('[object ArrayBuffer]', types.ARRAY_BUFFER)
3822 .addClass('[object Int8Array]', types.TYPED_ARRAY, 'int8')
3823 .addClass('[object Uint8Array]', types.TYPED_ARRAY, 'uint8')
3824 .addClass('[object Uint8ClampedArray]', types.TYPED_ARRAY, 'uint8clamped')
3825 .addClass('[object Int16Array]', types.TYPED_ARRAY, 'int16')
3826 .addClass('[object Uint16Array]', types.TYPED_ARRAY, 'uint16')
3827 .addClass('[object Int32Array]', types.TYPED_ARRAY, 'int32')
3828 .addClass('[object Uint32Array]', types.TYPED_ARRAY, 'uint32')
3829 .addClass('[object Float32Array]', types.TYPED_ARRAY, 'float32')
3830 .addClass('[object Float64Array]', types.TYPED_ARRAY, 'float64')
3831 .addClass('[object DataView]', types.DATA_VIEW)
3832 .addClass('[object Map]', types.MAP)
3833 .addClass('[object WeakMap]', types.WEAK_MAP)
3834 .addClass('[object Set]', types.SET)
3835 .addClass('[object WeakSet]', types.WEAK_SET)
3836 .addClass('[object Promise]', types.PROMISE)
3837 .addClass('[object Blob]', types.BLOB)
3838 .addClass('[object File]', types.FILE)
3839 .addClass('[object FileList]', types.FILE_LIST)
3840 .addClass('[object XMLHttpRequest]', types.XHR)
3841 .add(function(obj) {
3842 if((typeof Promise === types.FUNCTION && obj instanceof Promise) ||
3843 (typeof obj.then === types.FUNCTION)) {
3844 return new Type(types.OBJECT, types.PROMISE);
3845 }
3846 })
3847 .add(function(obj) {
3848 if(typeof Buffer !== 'undefined' && obj instanceof Buffer) {
3849 return new Type(types.OBJECT, types.BUFFER);
3850 }
3851 })
3852 .add(function(obj) {
3853 if(typeof Node !== 'undefined' && obj instanceof Node) {
3854 return new Type(types.OBJECT, types.HTML_ELEMENT, obj.nodeName);
3855 }
3856 })
3857 .add(function(obj) {
3858 // probably at the begginging should be enough these checks
3859 if(obj.Boolean === Boolean && obj.Number === Number && obj.String === String && obj.Date === Date) {
3860 return new Type(types.OBJECT, types.HOST);
3861 }
3862 })
3863 .add(function() {
3864 return new Type(types.OBJECT);
3865 });
3866
3867/**
3868 * Get type information of anything
3869 *
3870 * @param {any} obj Anything that could require type information
3871 * @return {Type} type info
3872 */
3873function getGlobalType(obj) {
3874 return main.getType(obj);
3875}
3876
3877getGlobalType.checker = main;
3878getGlobalType.TypeChecker = TypeChecker;
3879getGlobalType.Type = Type;
3880
3881Object.keys(types).forEach(function(typeName) {
3882 getGlobalType[typeName] = types[typeName];
3883});
3884
3885module.exports = getGlobalType;
3886
3887},{"./types":25}],25:[function(require,module,exports){
3888var types = {
3889 NUMBER: 'number',
3890 UNDEFINED: 'undefined',
3891 STRING: 'string',
3892 BOOLEAN: 'boolean',
3893 OBJECT: 'object',
3894 FUNCTION: 'function',
3895 NULL: 'null',
3896 ARRAY: 'array',
3897 REGEXP: 'regexp',
3898 DATE: 'date',
3899 ERROR: 'error',
3900 ARGUMENTS: 'arguments',
3901 SYMBOL: 'symbol',
3902 ARRAY_BUFFER: 'array-buffer',
3903 TYPED_ARRAY: 'typed-array',
3904 DATA_VIEW: 'data-view',
3905 MAP: 'map',
3906 SET: 'set',
3907 WEAK_SET: 'weak-set',
3908 WEAK_MAP: 'weak-map',
3909 PROMISE: 'promise',
3910
3911// node buffer
3912 BUFFER: 'buffer',
3913
3914// dom html element
3915 HTML_ELEMENT: 'html-element',
3916 HTML_ELEMENT_TEXT: 'html-element-text',
3917 DOCUMENT: 'document',
3918 WINDOW: 'window',
3919 FILE: 'file',
3920 FILE_LIST: 'file-list',
3921 BLOB: 'blob',
3922
3923 HOST: 'host',
3924
3925 XHR: 'xhr'
3926};
3927
3928module.exports = types;
3929
3930},{}],26:[function(require,module,exports){
3931function addSpaces(v) {
3932 return v.split('\n').map(function(vv) { return ' ' + vv; }).join('\n');
3933}
3934
3935function pad(str, value, filler) {
3936 str = String(str)
3937 var isRight = false;
3938
3939 if(value < 0) {
3940 isRight = true;
3941 value = -value;
3942 }
3943
3944 if(str.length < value) {
3945 var padding = new Array(value - str.length + 1).join(filler);
3946 return isRight ? str + padding : padding + str;
3947 } else{
3948 return str;
3949 }
3950}
3951
3952module.exports = {
3953 addSpaces: addSpaces,
3954 pad: pad,
3955 pad0: function(str, value) {
3956 return pad(str, value, '0');
3957 }
3958};
3959
3960},{}],27:[function(require,module,exports){
3961arguments[4][24][0].apply(exports,arguments)
3962},{"./types":28,"dup":24}],28:[function(require,module,exports){
3963arguments[4][25][0].apply(exports,arguments)
3964},{"dup":25}]},{},[1]);