chai 2.3.0 → 3.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/karma.conf.js CHANGED
@@ -2,7 +2,7 @@ module.exports = function(config) {
2
2
  config.set({
3
3
  frameworks: [ 'mocha' ]
4
4
  , files: [
5
- 'build/build.js'
5
+ 'chai.js'
6
6
  , 'test/bootstrap/karma.js'
7
7
  , 'test/*.js'
8
8
  ]
@@ -81,8 +81,8 @@ module.exports = function (_chai, util) {
81
81
  util.overwriteChainableMethod(this.prototype, name, fn, chainingBehavior);
82
82
  };
83
83
 
84
- /*!
85
- * ### .assert(expression, message, negateMessage, expected, actual)
84
+ /**
85
+ * ### .assert(expression, message, negateMessage, expected, actual, showDiff)
86
86
  *
87
87
  * Executes an expression and check expectations. Throws AssertionError for reporting if test doesn't pass.
88
88
  *
@@ -136,6 +136,12 @@ module.exports = function (chai, _) {
136
136
  * expect({ foo: 'bar' }).to.be.an('object');
137
137
  * expect(null).to.be.a('null');
138
138
  * expect(undefined).to.be.an('undefined');
139
+ * expect(new Promise).to.be.a('promise');
140
+ * expect(new Float32Array()).to.be.a('float32array');
141
+ * expect(Symbol()).to.be.a('symbol');
142
+ *
143
+ * // es6 overrides
144
+ * expect({[Symbol.toStringTag]:()=>'foo'}).to.be.a('foo');
139
145
  *
140
146
  * // language chain
141
147
  * expect(foo).to.be.an.instanceof(Foo);
@@ -208,7 +214,7 @@ module.exports = function (chai, _) {
208
214
  for (var k in val) subset[k] = obj[k];
209
215
  expected = _.eql(subset, val);
210
216
  } else {
211
- expected = obj && ~obj.indexOf(val);
217
+ expected = (obj != undefined) && ~obj.indexOf(val);
212
218
  }
213
219
  this.assert(
214
220
  expected
@@ -325,6 +331,25 @@ module.exports = function (chai, _) {
325
331
  );
326
332
  });
327
333
 
334
+ /**
335
+ * ### .NaN
336
+ * Asserts that the target is `NaN`.
337
+ *
338
+ * expect('foo').to.be.NaN;
339
+ * expect(4).not.to.be.NaN;
340
+ *
341
+ * @name NaN
342
+ * @api public
343
+ */
344
+
345
+ Assertion.addProperty('NaN', function () {
346
+ this.assert(
347
+ isNaN(flag(this, 'object'))
348
+ , 'expected #{this} to be NaN'
349
+ , 'expected #{this} not to be NaN'
350
+ );
351
+ });
352
+
328
353
  /**
329
354
  * ### .exist
330
355
  *
@@ -367,17 +392,8 @@ module.exports = function (chai, _) {
367
392
  */
368
393
 
369
394
  Assertion.addProperty('empty', function () {
370
- var obj = flag(this, 'object')
371
- , expected = obj;
372
-
373
- if (Array.isArray(obj) || 'string' === typeof object) {
374
- expected = obj.length;
375
- } else if (typeof obj === 'object') {
376
- expected = Object.keys(obj).length;
377
- }
378
-
379
395
  this.assert(
380
- !expected
396
+ Object.keys(Object(flag(this, 'object'))).length === 0
381
397
  , 'expected #{this} to be empty'
382
398
  , 'expected #{this} not to be empty'
383
399
  );
@@ -835,7 +851,7 @@ module.exports = function (chai, _) {
835
851
  ? pathInfo.value
836
852
  : obj[name];
837
853
 
838
- if (negate && undefined !== val) {
854
+ if (negate && arguments.length > 1) {
839
855
  if (undefined === value) {
840
856
  msg = (msg != null) ? msg + ': ' : '';
841
857
  throw new Error(msg + _.inspect(obj) + ' has no ' + descriptor + _.inspect(name));
@@ -847,7 +863,7 @@ module.exports = function (chai, _) {
847
863
  , 'expected #{this} to not have ' + descriptor + _.inspect(name));
848
864
  }
849
865
 
850
- if (undefined !== val) {
866
+ if (arguments.length > 1) {
851
867
  this.assert(
852
868
  val === value
853
869
  , 'expected #{this} to have a ' + descriptor + _.inspect(name) + ' of #{exp}, but got #{act}'
@@ -938,16 +954,10 @@ module.exports = function (chai, _) {
938
954
  Assertion.addMethod('haveOwnPropertyDescriptor', assertOwnPropertyDescriptor);
939
955
 
940
956
  /**
941
- * ### .length(value)
942
- *
943
- * Asserts that the target's `length` property has
944
- * the expected value.
945
- *
946
- * expect([ 1, 2, 3]).to.have.length(3);
947
- * expect('foobar').to.have.length(6);
957
+ * ### .length
948
958
  *
949
- * Can also be used as a chain precursor to a value
950
- * comparison for the length property.
959
+ * Sets the `doLength` flag later used as a chain precursor to a value
960
+ * comparison for the `length` property.
951
961
  *
952
962
  * expect('foo').to.have.length.above(2);
953
963
  * expect([ 1, 2, 3 ]).to.have.length.above(2);
@@ -956,8 +966,25 @@ module.exports = function (chai, _) {
956
966
  * expect('foo').to.have.length.within(2,4);
957
967
  * expect([ 1, 2, 3 ]).to.have.length.within(2,4);
958
968
  *
969
+ * *Deprecation notice:* Using `length` as an assertion will be deprecated
970
+ * in version 2.4.0 and removed in 3.0.0. Code using the old style of
971
+ * asserting for `length` property value using `length(value)` should be
972
+ * switched to use `lengthOf(value)` instead.
973
+ *
959
974
  * @name length
960
- * @alias lengthOf
975
+ * @api public
976
+ */
977
+
978
+ /**
979
+ * ### .lengthOf(value[, message])
980
+ *
981
+ * Asserts that the target's `length` property has
982
+ * the expected value.
983
+ *
984
+ * expect([ 1, 2, 3]).to.have.lengthOf(3);
985
+ * expect('foobar').to.have.lengthOf(6);
986
+ *
987
+ * @name lengthOf
961
988
  * @param {Number} length
962
989
  * @param {String} message _optional_
963
990
  * @api public
@@ -993,12 +1020,12 @@ module.exports = function (chai, _) {
993
1020
  * expect('foobar').to.match(/^foo/);
994
1021
  *
995
1022
  * @name match
1023
+ * @alias matches
996
1024
  * @param {RegExp} RegularExpression
997
1025
  * @param {String} message _optional_
998
1026
  * @api public
999
1027
  */
1000
-
1001
- Assertion.addMethod('match', function (re, msg) {
1028
+ function assertMatch(re, msg) {
1002
1029
  if (msg) flag(this, 'message', msg);
1003
1030
  var obj = flag(this, 'object');
1004
1031
  this.assert(
@@ -1006,7 +1033,10 @@ module.exports = function (chai, _) {
1006
1033
  , 'expected #{this} to match ' + re
1007
1034
  , 'expected #{this} not to match ' + re
1008
1035
  );
1009
- });
1036
+ }
1037
+
1038
+ Assertion.addMethod('match', assertMatch);
1039
+ Assertion.addMethod('matches', assertMatch);
1010
1040
 
1011
1041
  /**
1012
1042
  * ### .string(string)
@@ -1063,7 +1093,7 @@ module.exports = function (chai, _) {
1063
1093
  * expect({ foo: 1, bar: 2 }).to.have.all.keys(['bar', 'foo']);
1064
1094
  * expect({ foo: 1, bar: 2 }).to.have.all.keys({'bar': 6, 'foo': 7});
1065
1095
  * expect({ foo: 1, bar: 2, baz: 3 }).to.contain.all.keys(['bar', 'foo']);
1066
- * expect({ foo: 1, bar: 2, baz: 3 }).to.contain.all.keys([{'bar': 6}}]);
1096
+ * expect({ foo: 1, bar: 2, baz: 3 }).to.contain.all.keys({'bar': 6});
1067
1097
  *
1068
1098
  *
1069
1099
  * @name keys
@@ -1255,7 +1285,7 @@ module.exports = function (chai, _) {
1255
1285
  }
1256
1286
 
1257
1287
  // next, check message
1258
- var message = 'object' === _.type(err) && "message" in err
1288
+ var message = 'error' === _.type(err) && "message" in err
1259
1289
  ? err.message
1260
1290
  : '' + err;
1261
1291
 
@@ -1329,12 +1359,13 @@ module.exports = function (chai, _) {
1329
1359
  * expect(Klass).itself.to.respondTo('baz');
1330
1360
  *
1331
1361
  * @name respondTo
1362
+ * @alias respondsTo
1332
1363
  * @param {String} method
1333
1364
  * @param {String} message _optional_
1334
1365
  * @api public
1335
1366
  */
1336
1367
 
1337
- Assertion.addMethod('respondTo', function (method, msg) {
1368
+ function respondTo (method, msg) {
1338
1369
  if (msg) flag(this, 'message', msg);
1339
1370
  var obj = flag(this, 'object')
1340
1371
  , itself = flag(this, 'itself')
@@ -1347,7 +1378,10 @@ module.exports = function (chai, _) {
1347
1378
  , 'expected #{this} to respond to ' + _.inspect(method)
1348
1379
  , 'expected #{this} to not respond to ' + _.inspect(method)
1349
1380
  );
1350
- });
1381
+ }
1382
+
1383
+ Assertion.addMethod('respondTo', respondTo);
1384
+ Assertion.addMethod('respondsTo', respondTo);
1351
1385
 
1352
1386
  /**
1353
1387
  * ### .itself
@@ -1377,12 +1411,13 @@ module.exports = function (chai, _) {
1377
1411
  * expect(1).to.satisfy(function(num) { return num > 0; });
1378
1412
  *
1379
1413
  * @name satisfy
1414
+ * @alias satisfies
1380
1415
  * @param {Function} matcher
1381
1416
  * @param {String} message _optional_
1382
1417
  * @api public
1383
1418
  */
1384
1419
 
1385
- Assertion.addMethod('satisfy', function (matcher, msg) {
1420
+ function satisfy (matcher, msg) {
1386
1421
  if (msg) flag(this, 'message', msg);
1387
1422
  var obj = flag(this, 'object');
1388
1423
  var result = matcher(obj);
@@ -1393,7 +1428,10 @@ module.exports = function (chai, _) {
1393
1428
  , this.negate ? false : true
1394
1429
  , result
1395
1430
  );
1396
- });
1431
+ }
1432
+
1433
+ Assertion.addMethod('satisfy', satisfy);
1434
+ Assertion.addMethod('satisfies', satisfy);
1397
1435
 
1398
1436
  /**
1399
1437
  * ### .closeTo(expected, delta)
@@ -1598,4 +1636,126 @@ module.exports = function (chai, _) {
1598
1636
  Assertion.addChainableMethod('decrease', assertDecreases);
1599
1637
  Assertion.addChainableMethod('decreases', assertDecreases);
1600
1638
 
1639
+ /**
1640
+ * ### .extensible
1641
+ *
1642
+ * Asserts that the target is extensible (can have new properties added to
1643
+ * it).
1644
+ *
1645
+ * var nonExtensibleObject = Object.preventExtensions({});
1646
+ * var sealedObject = Object.seal({});
1647
+ * var frozenObject = Object.freeze({});
1648
+ *
1649
+ * expect({}).to.be.extensible;
1650
+ * expect(nonExtensibleObject).to.not.be.extensible;
1651
+ * expect(sealedObject).to.not.be.extensible;
1652
+ * expect(frozenObject).to.not.be.extensible;
1653
+ *
1654
+ * @name extensible
1655
+ * @api public
1656
+ */
1657
+
1658
+ Assertion.addProperty('extensible', function() {
1659
+ var obj = flag(this, 'object');
1660
+
1661
+ // In ES5, if the argument to this method is not an object (a primitive), then it will cause a TypeError.
1662
+ // In ES6, a non-object argument will be treated as if it was a non-extensible ordinary object, simply return false.
1663
+ // https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/isExtensible
1664
+ // The following provides ES6 behavior when a TypeError is thrown under ES5.
1665
+
1666
+ var isExtensible;
1667
+
1668
+ try {
1669
+ isExtensible = Object.isExtensible(obj);
1670
+ } catch (err) {
1671
+ if (err instanceof TypeError) isExtensible = false;
1672
+ else throw err;
1673
+ }
1674
+
1675
+ this.assert(
1676
+ isExtensible
1677
+ , 'expected #{this} to be extensible'
1678
+ , 'expected #{this} to not be extensible'
1679
+ );
1680
+ });
1681
+
1682
+ /**
1683
+ * ### .sealed
1684
+ *
1685
+ * Asserts that the target is sealed (cannot have new properties added to it
1686
+ * and its existing properties cannot be removed).
1687
+ *
1688
+ * var sealedObject = Object.seal({});
1689
+ * var frozenObject = Object.freeze({});
1690
+ *
1691
+ * expect(sealedObject).to.be.sealed;
1692
+ * expect(frozenObject).to.be.sealed;
1693
+ * expect({}).to.not.be.sealed;
1694
+ *
1695
+ * @name sealed
1696
+ * @api public
1697
+ */
1698
+
1699
+ Assertion.addProperty('sealed', function() {
1700
+ var obj = flag(this, 'object');
1701
+
1702
+ // In ES5, if the argument to this method is not an object (a primitive), then it will cause a TypeError.
1703
+ // In ES6, a non-object argument will be treated as if it was a sealed ordinary object, simply return true.
1704
+ // See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/isSealed
1705
+ // The following provides ES6 behavior when a TypeError is thrown under ES5.
1706
+
1707
+ var isSealed;
1708
+
1709
+ try {
1710
+ isSealed = Object.isSealed(obj);
1711
+ } catch (err) {
1712
+ if (err instanceof TypeError) isSealed = true;
1713
+ else throw err;
1714
+ }
1715
+
1716
+ this.assert(
1717
+ isSealed
1718
+ , 'expected #{this} to be sealed'
1719
+ , 'expected #{this} to not be sealed'
1720
+ );
1721
+ });
1722
+
1723
+ /**
1724
+ * ### .frozen
1725
+ *
1726
+ * Asserts that the target is frozen (cannot have new properties added to it
1727
+ * and its existing properties cannot be modified).
1728
+ *
1729
+ * var frozenObject = Object.freeze({});
1730
+ *
1731
+ * expect(frozenObject).to.be.frozen;
1732
+ * expect({}).to.not.be.frozen;
1733
+ *
1734
+ * @name frozen
1735
+ * @api public
1736
+ */
1737
+
1738
+ Assertion.addProperty('frozen', function() {
1739
+ var obj = flag(this, 'object');
1740
+
1741
+ // In ES5, if the argument to this method is not an object (a primitive), then it will cause a TypeError.
1742
+ // In ES6, a non-object argument will be treated as if it was a frozen ordinary object, simply return true.
1743
+ // See https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object/isFrozen
1744
+ // The following provides ES6 behavior when a TypeError is thrown under ES5.
1745
+
1746
+ var isFrozen;
1747
+
1748
+ try {
1749
+ isFrozen = Object.isFrozen(obj);
1750
+ } catch (err) {
1751
+ if (err instanceof TypeError) isFrozen = true;
1752
+ else throw err;
1753
+ }
1754
+
1755
+ this.assert(
1756
+ isFrozen
1757
+ , 'expected #{this} to be frozen'
1758
+ , 'expected #{this} to not be frozen'
1759
+ );
1760
+ });
1601
1761
  };