@vitest/expect 3.0.9 → 3.1.0-beta.2

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.
Files changed (2) hide show
  1. package/dist/index.js +1520 -2030
  2. package/package.json +4 -4
package/dist/index.js CHANGED
@@ -8,57 +8,55 @@ import { use, util } from 'chai';
8
8
  const MATCHERS_OBJECT = Symbol.for("matchers-object");
9
9
  const JEST_MATCHERS_OBJECT = Symbol.for("$$jest-matchers-object");
10
10
  const GLOBAL_EXPECT = Symbol.for("expect-global");
11
- const ASYMMETRIC_MATCHERS_OBJECT = Symbol.for(
12
- "asymmetric-matchers-object"
13
- );
11
+ const ASYMMETRIC_MATCHERS_OBJECT = Symbol.for("asymmetric-matchers-object");
14
12
 
15
13
  const customMatchers = {
16
- toSatisfy(actual, expected, message) {
17
- const { printReceived, printExpected, matcherHint } = this.utils;
18
- const pass = expected(actual);
19
- return {
20
- pass,
21
- message: () => pass ? `${matcherHint(".not.toSatisfy", "received", "")}
14
+ toSatisfy(actual, expected, message) {
15
+ const { printReceived, printExpected, matcherHint } = this.utils;
16
+ const pass = expected(actual);
17
+ return {
18
+ pass,
19
+ message: () => pass ? `\
20
+ ${matcherHint(".not.toSatisfy", "received", "")}
22
21
 
23
22
  Expected value to not satisfy:
24
23
  ${message || printExpected(expected)}
25
24
  Received:
26
- ${printReceived(actual)}` : `${matcherHint(".toSatisfy", "received", "")}
25
+ ${printReceived(actual)}` : `\
26
+ ${matcherHint(".toSatisfy", "received", "")}
27
27
 
28
28
  Expected value to satisfy:
29
29
  ${message || printExpected(expected)}
30
30
 
31
31
  Received:
32
32
  ${printReceived(actual)}`
33
- };
34
- },
35
- toBeOneOf(actual, expected) {
36
- const { equals, customTesters } = this;
37
- const { printReceived, printExpected, matcherHint } = this.utils;
38
- if (!Array.isArray(expected)) {
39
- throw new TypeError(
40
- `You must provide an array to ${matcherHint(".toBeOneOf")}, not '${typeof expected}'.`
41
- );
42
- }
43
- const pass = expected.length === 0 || expected.some(
44
- (item) => equals(item, actual, customTesters)
45
- );
46
- return {
47
- pass,
48
- message: () => pass ? `${matcherHint(".not.toBeOneOf", "received", "")}
33
+ };
34
+ },
35
+ toBeOneOf(actual, expected) {
36
+ const { equals, customTesters } = this;
37
+ const { printReceived, printExpected, matcherHint } = this.utils;
38
+ if (!Array.isArray(expected)) {
39
+ throw new TypeError(`You must provide an array to ${matcherHint(".toBeOneOf")}, not '${typeof expected}'.`);
40
+ }
41
+ const pass = expected.length === 0 || expected.some((item) => equals(item, actual, customTesters));
42
+ return {
43
+ pass,
44
+ message: () => pass ? `\
45
+ ${matcherHint(".not.toBeOneOf", "received", "")}
49
46
 
50
47
  Expected value to not be one of:
51
48
  ${printExpected(expected)}
52
49
  Received:
53
- ${printReceived(actual)}` : `${matcherHint(".toBeOneOf", "received", "")}
50
+ ${printReceived(actual)}` : `\
51
+ ${matcherHint(".toBeOneOf", "received", "")}
54
52
 
55
53
  Expected value to be one of:
56
54
  ${printExpected(expected)}
57
55
 
58
56
  Received:
59
57
  ${printReceived(actual)}`
60
- };
61
- }
58
+ };
59
+ }
62
60
  };
63
61
 
64
62
  const EXPECTED_COLOR = c.green;
@@ -67,289 +65,261 @@ const INVERTED_COLOR = c.inverse;
67
65
  const BOLD_WEIGHT = c.bold;
68
66
  const DIM_COLOR = c.dim;
69
67
  function matcherHint(matcherName, received = "received", expected = "expected", options = {}) {
70
- const {
71
- comment = "",
72
- isDirectExpectCall = false,
73
- // seems redundant with received === ''
74
- isNot = false,
75
- promise = "",
76
- secondArgument = "",
77
- expectedColor = EXPECTED_COLOR,
78
- receivedColor = RECEIVED_COLOR,
79
- secondArgumentColor = EXPECTED_COLOR
80
- } = options;
81
- let hint = "";
82
- let dimString = "expect";
83
- if (!isDirectExpectCall && received !== "") {
84
- hint += DIM_COLOR(`${dimString}(`) + receivedColor(received);
85
- dimString = ")";
86
- }
87
- if (promise !== "") {
88
- hint += DIM_COLOR(`${dimString}.`) + promise;
89
- dimString = "";
90
- }
91
- if (isNot) {
92
- hint += `${DIM_COLOR(`${dimString}.`)}not`;
93
- dimString = "";
94
- }
95
- if (matcherName.includes(".")) {
96
- dimString += matcherName;
97
- } else {
98
- hint += DIM_COLOR(`${dimString}.`) + matcherName;
99
- dimString = "";
100
- }
101
- if (expected === "") {
102
- dimString += "()";
103
- } else {
104
- hint += DIM_COLOR(`${dimString}(`) + expectedColor(expected);
105
- if (secondArgument) {
106
- hint += DIM_COLOR(", ") + secondArgumentColor(secondArgument);
107
- }
108
- dimString = ")";
109
- }
110
- if (comment !== "") {
111
- dimString += ` // ${comment}`;
112
- }
113
- if (dimString !== "") {
114
- hint += DIM_COLOR(dimString);
115
- }
116
- return hint;
68
+ const { comment = "", isDirectExpectCall = false, isNot = false, promise = "", secondArgument = "", expectedColor = EXPECTED_COLOR, receivedColor = RECEIVED_COLOR, secondArgumentColor = EXPECTED_COLOR } = options;
69
+ let hint = "";
70
+ let dimString = "expect";
71
+ if (!isDirectExpectCall && received !== "") {
72
+ hint += DIM_COLOR(`${dimString}(`) + receivedColor(received);
73
+ dimString = ")";
74
+ }
75
+ if (promise !== "") {
76
+ hint += DIM_COLOR(`${dimString}.`) + promise;
77
+ dimString = "";
78
+ }
79
+ if (isNot) {
80
+ hint += `${DIM_COLOR(`${dimString}.`)}not`;
81
+ dimString = "";
82
+ }
83
+ if (matcherName.includes(".")) {
84
+ dimString += matcherName;
85
+ } else {
86
+ hint += DIM_COLOR(`${dimString}.`) + matcherName;
87
+ dimString = "";
88
+ }
89
+ if (expected === "") {
90
+ dimString += "()";
91
+ } else {
92
+ hint += DIM_COLOR(`${dimString}(`) + expectedColor(expected);
93
+ if (secondArgument) {
94
+ hint += DIM_COLOR(", ") + secondArgumentColor(secondArgument);
95
+ }
96
+ dimString = ")";
97
+ }
98
+ if (comment !== "") {
99
+ dimString += ` // ${comment}`;
100
+ }
101
+ if (dimString !== "") {
102
+ hint += DIM_COLOR(dimString);
103
+ }
104
+ return hint;
117
105
  }
118
- const SPACE_SYMBOL = "\xB7";
106
+ const SPACE_SYMBOL = "·";
119
107
  function replaceTrailingSpaces(text) {
120
- return text.replace(/\s+$/gm, (spaces) => SPACE_SYMBOL.repeat(spaces.length));
108
+ return text.replace(/\s+$/gm, (spaces) => SPACE_SYMBOL.repeat(spaces.length));
121
109
  }
122
110
  function printReceived(object) {
123
- return RECEIVED_COLOR(replaceTrailingSpaces(stringify(object)));
111
+ return RECEIVED_COLOR(replaceTrailingSpaces(stringify(object)));
124
112
  }
125
113
  function printExpected(value) {
126
- return EXPECTED_COLOR(replaceTrailingSpaces(stringify(value)));
114
+ return EXPECTED_COLOR(replaceTrailingSpaces(stringify(value)));
127
115
  }
128
116
  function getMatcherUtils() {
129
- return {
130
- EXPECTED_COLOR,
131
- RECEIVED_COLOR,
132
- INVERTED_COLOR,
133
- BOLD_WEIGHT,
134
- DIM_COLOR,
135
- diff,
136
- matcherHint,
137
- printReceived,
138
- printExpected,
139
- printDiffOrStringify
140
- };
117
+ return {
118
+ EXPECTED_COLOR,
119
+ RECEIVED_COLOR,
120
+ INVERTED_COLOR,
121
+ BOLD_WEIGHT,
122
+ DIM_COLOR,
123
+ diff,
124
+ matcherHint,
125
+ printReceived,
126
+ printExpected,
127
+ printDiffOrStringify
128
+ };
141
129
  }
142
130
  function addCustomEqualityTesters(newTesters) {
143
- if (!Array.isArray(newTesters)) {
144
- throw new TypeError(
145
- `expect.customEqualityTesters: Must be set to an array of Testers. Was given "${getType(
146
- newTesters
147
- )}"`
148
- );
149
- }
150
- globalThis[JEST_MATCHERS_OBJECT].customEqualityTesters.push(
151
- ...newTesters
152
- );
131
+ if (!Array.isArray(newTesters)) {
132
+ throw new TypeError(`expect.customEqualityTesters: Must be set to an array of Testers. Was given "${getType(newTesters)}"`);
133
+ }
134
+ globalThis[JEST_MATCHERS_OBJECT].customEqualityTesters.push(...newTesters);
153
135
  }
154
136
  function getCustomEqualityTesters() {
155
- return globalThis[JEST_MATCHERS_OBJECT].customEqualityTesters;
137
+ return globalThis[JEST_MATCHERS_OBJECT].customEqualityTesters;
156
138
  }
157
139
 
158
140
  function equals(a, b, customTesters, strictCheck) {
159
- customTesters = customTesters || [];
160
- return eq(a, b, [], [], customTesters, strictCheck ? hasKey : hasDefinedKey);
141
+ customTesters = customTesters || [];
142
+ return eq(a, b, [], [], customTesters, strictCheck ? hasKey : hasDefinedKey);
161
143
  }
162
144
  const functionToString = Function.prototype.toString;
163
145
  function isAsymmetric(obj) {
164
- return !!obj && typeof obj === "object" && "asymmetricMatch" in obj && isA("Function", obj.asymmetricMatch);
146
+ return !!obj && typeof obj === "object" && "asymmetricMatch" in obj && isA("Function", obj.asymmetricMatch);
165
147
  }
166
- function hasAsymmetric(obj, seen = /* @__PURE__ */ new Set()) {
167
- if (seen.has(obj)) {
168
- return false;
169
- }
170
- seen.add(obj);
171
- if (isAsymmetric(obj)) {
172
- return true;
173
- }
174
- if (Array.isArray(obj)) {
175
- return obj.some((i) => hasAsymmetric(i, seen));
176
- }
177
- if (obj instanceof Set) {
178
- return Array.from(obj).some((i) => hasAsymmetric(i, seen));
179
- }
180
- if (isObject(obj)) {
181
- return Object.values(obj).some((v) => hasAsymmetric(v, seen));
182
- }
183
- return false;
148
+ function hasAsymmetric(obj, seen = new Set()) {
149
+ if (seen.has(obj)) {
150
+ return false;
151
+ }
152
+ seen.add(obj);
153
+ if (isAsymmetric(obj)) {
154
+ return true;
155
+ }
156
+ if (Array.isArray(obj)) {
157
+ return obj.some((i) => hasAsymmetric(i, seen));
158
+ }
159
+ if (obj instanceof Set) {
160
+ return Array.from(obj).some((i) => hasAsymmetric(i, seen));
161
+ }
162
+ if (isObject(obj)) {
163
+ return Object.values(obj).some((v) => hasAsymmetric(v, seen));
164
+ }
165
+ return false;
184
166
  }
185
167
  function asymmetricMatch(a, b) {
186
- const asymmetricA = isAsymmetric(a);
187
- const asymmetricB = isAsymmetric(b);
188
- if (asymmetricA && asymmetricB) {
189
- return void 0;
190
- }
191
- if (asymmetricA) {
192
- return a.asymmetricMatch(b);
193
- }
194
- if (asymmetricB) {
195
- return b.asymmetricMatch(a);
196
- }
168
+ const asymmetricA = isAsymmetric(a);
169
+ const asymmetricB = isAsymmetric(b);
170
+ if (asymmetricA && asymmetricB) {
171
+ return undefined;
172
+ }
173
+ if (asymmetricA) {
174
+ return a.asymmetricMatch(b);
175
+ }
176
+ if (asymmetricB) {
177
+ return b.asymmetricMatch(a);
178
+ }
197
179
  }
198
- function eq(a, b, aStack, bStack, customTesters, hasKey2) {
199
- let result = true;
200
- const asymmetricResult = asymmetricMatch(a, b);
201
- if (asymmetricResult !== void 0) {
202
- return asymmetricResult;
203
- }
204
- const testerContext = { equals };
205
- for (let i = 0; i < customTesters.length; i++) {
206
- const customTesterResult = customTesters[i].call(
207
- testerContext,
208
- a,
209
- b,
210
- customTesters
211
- );
212
- if (customTesterResult !== void 0) {
213
- return customTesterResult;
214
- }
215
- }
216
- if (typeof URL === "function" && a instanceof URL && b instanceof URL) {
217
- return a.href === b.href;
218
- }
219
- if (Object.is(a, b)) {
220
- return true;
221
- }
222
- if (a === null || b === null) {
223
- return a === b;
224
- }
225
- const className = Object.prototype.toString.call(a);
226
- if (className !== Object.prototype.toString.call(b)) {
227
- return false;
228
- }
229
- switch (className) {
230
- case "[object Boolean]":
231
- case "[object String]":
232
- case "[object Number]":
233
- if (typeof a !== typeof b) {
234
- return false;
235
- } else if (typeof a !== "object" && typeof b !== "object") {
236
- return Object.is(a, b);
237
- } else {
238
- return Object.is(a.valueOf(), b.valueOf());
239
- }
240
- case "[object Date]": {
241
- const numA = +a;
242
- const numB = +b;
243
- return numA === numB || Number.isNaN(numA) && Number.isNaN(numB);
244
- }
245
- // RegExps are compared by their source patterns and flags.
246
- case "[object RegExp]":
247
- return a.source === b.source && a.flags === b.flags;
248
- }
249
- if (typeof a !== "object" || typeof b !== "object") {
250
- return false;
251
- }
252
- if (isDomNode(a) && isDomNode(b)) {
253
- return a.isEqualNode(b);
254
- }
255
- let length = aStack.length;
256
- while (length--) {
257
- if (aStack[length] === a) {
258
- return bStack[length] === b;
259
- } else if (bStack[length] === b) {
260
- return false;
261
- }
262
- }
263
- aStack.push(a);
264
- bStack.push(b);
265
- if (className === "[object Array]" && a.length !== b.length) {
266
- return false;
267
- }
268
- if (a instanceof Error && b instanceof Error) {
269
- try {
270
- return isErrorEqual(a, b, aStack, bStack, customTesters, hasKey2);
271
- } finally {
272
- aStack.pop();
273
- bStack.pop();
274
- }
275
- }
276
- const aKeys = keys(a, hasKey2);
277
- let key;
278
- let size = aKeys.length;
279
- if (keys(b, hasKey2).length !== size) {
280
- return false;
281
- }
282
- while (size--) {
283
- key = aKeys[size];
284
- result = hasKey2(b, key) && eq(a[key], b[key], aStack, bStack, customTesters, hasKey2);
285
- if (!result) {
286
- return false;
287
- }
288
- }
289
- aStack.pop();
290
- bStack.pop();
291
- return result;
180
+ function eq(a, b, aStack, bStack, customTesters, hasKey) {
181
+ let result = true;
182
+ const asymmetricResult = asymmetricMatch(a, b);
183
+ if (asymmetricResult !== undefined) {
184
+ return asymmetricResult;
185
+ }
186
+ const testerContext = { equals };
187
+ for (let i = 0; i < customTesters.length; i++) {
188
+ const customTesterResult = customTesters[i].call(testerContext, a, b, customTesters);
189
+ if (customTesterResult !== undefined) {
190
+ return customTesterResult;
191
+ }
192
+ }
193
+ if (typeof URL === "function" && a instanceof URL && b instanceof URL) {
194
+ return a.href === b.href;
195
+ }
196
+ if (Object.is(a, b)) {
197
+ return true;
198
+ }
199
+ if (a === null || b === null) {
200
+ return a === b;
201
+ }
202
+ const className = Object.prototype.toString.call(a);
203
+ if (className !== Object.prototype.toString.call(b)) {
204
+ return false;
205
+ }
206
+ switch (className) {
207
+ case "[object Boolean]":
208
+ case "[object String]":
209
+ case "[object Number]": if (typeof a !== typeof b) {
210
+ return false;
211
+ } else if (typeof a !== "object" && typeof b !== "object") {
212
+ return Object.is(a, b);
213
+ } else {
214
+ return Object.is(a.valueOf(), b.valueOf());
215
+ }
216
+ case "[object Date]": {
217
+ const numA = +a;
218
+ const numB = +b;
219
+ return numA === numB || Number.isNaN(numA) && Number.isNaN(numB);
220
+ }
221
+ case "[object RegExp]": return a.source === b.source && a.flags === b.flags;
222
+ }
223
+ if (typeof a !== "object" || typeof b !== "object") {
224
+ return false;
225
+ }
226
+ if (isDomNode(a) && isDomNode(b)) {
227
+ return a.isEqualNode(b);
228
+ }
229
+ let length = aStack.length;
230
+ while (length--) {
231
+ if (aStack[length] === a) {
232
+ return bStack[length] === b;
233
+ } else if (bStack[length] === b) {
234
+ return false;
235
+ }
236
+ }
237
+ aStack.push(a);
238
+ bStack.push(b);
239
+ if (className === "[object Array]" && a.length !== b.length) {
240
+ return false;
241
+ }
242
+ if (a instanceof Error && b instanceof Error) {
243
+ try {
244
+ return isErrorEqual(a, b, aStack, bStack, customTesters, hasKey);
245
+ } finally {
246
+ aStack.pop();
247
+ bStack.pop();
248
+ }
249
+ }
250
+ const aKeys = keys(a, hasKey);
251
+ let key;
252
+ let size = aKeys.length;
253
+ if (keys(b, hasKey).length !== size) {
254
+ return false;
255
+ }
256
+ while (size--) {
257
+ key = aKeys[size];
258
+ result = hasKey(b, key) && eq(a[key], b[key], aStack, bStack, customTesters, hasKey);
259
+ if (!result) {
260
+ return false;
261
+ }
262
+ }
263
+ aStack.pop();
264
+ bStack.pop();
265
+ return result;
292
266
  }
293
- function isErrorEqual(a, b, aStack, bStack, customTesters, hasKey2) {
294
- let result = Object.getPrototypeOf(a) === Object.getPrototypeOf(b) && a.name === b.name && a.message === b.message;
295
- if (typeof b.cause !== "undefined") {
296
- result && (result = eq(a.cause, b.cause, aStack, bStack, customTesters, hasKey2));
297
- }
298
- if (a instanceof AggregateError && b instanceof AggregateError) {
299
- result && (result = eq(a.errors, b.errors, aStack, bStack, customTesters, hasKey2));
300
- }
301
- result && (result = eq({ ...a }, { ...b }, aStack, bStack, customTesters, hasKey2));
302
- return result;
267
+ function isErrorEqual(a, b, aStack, bStack, customTesters, hasKey) {
268
+ let result = Object.getPrototypeOf(a) === Object.getPrototypeOf(b) && a.name === b.name && a.message === b.message;
269
+ if (typeof b.cause !== "undefined") {
270
+ result && (result = eq(a.cause, b.cause, aStack, bStack, customTesters, hasKey));
271
+ }
272
+ if (a instanceof AggregateError && b instanceof AggregateError) {
273
+ result && (result = eq(a.errors, b.errors, aStack, bStack, customTesters, hasKey));
274
+ }
275
+ result && (result = eq({ ...a }, { ...b }, aStack, bStack, customTesters, hasKey));
276
+ return result;
303
277
  }
304
- function keys(obj, hasKey2) {
305
- const keys2 = [];
306
- for (const key in obj) {
307
- if (hasKey2(obj, key)) {
308
- keys2.push(key);
309
- }
310
- }
311
- return keys2.concat(
312
- Object.getOwnPropertySymbols(obj).filter(
313
- (symbol) => Object.getOwnPropertyDescriptor(obj, symbol).enumerable
314
- )
315
- );
278
+ function keys(obj, hasKey) {
279
+ const keys = [];
280
+ for (const key in obj) {
281
+ if (hasKey(obj, key)) {
282
+ keys.push(key);
283
+ }
284
+ }
285
+ return keys.concat(Object.getOwnPropertySymbols(obj).filter((symbol) => Object.getOwnPropertyDescriptor(obj, symbol).enumerable));
316
286
  }
317
287
  function hasDefinedKey(obj, key) {
318
- return hasKey(obj, key) && obj[key] !== void 0;
288
+ return hasKey(obj, key) && obj[key] !== undefined;
319
289
  }
320
290
  function hasKey(obj, key) {
321
- return Object.prototype.hasOwnProperty.call(obj, key);
291
+ return Object.prototype.hasOwnProperty.call(obj, key);
322
292
  }
323
293
  function isA(typeName, value) {
324
- return Object.prototype.toString.apply(value) === `[object ${typeName}]`;
294
+ return Object.prototype.toString.apply(value) === `[object ${typeName}]`;
325
295
  }
326
296
  function isDomNode(obj) {
327
- return obj !== null && typeof obj === "object" && "nodeType" in obj && typeof obj.nodeType === "number" && "nodeName" in obj && typeof obj.nodeName === "string" && "isEqualNode" in obj && typeof obj.isEqualNode === "function";
297
+ return obj !== null && typeof obj === "object" && "nodeType" in obj && typeof obj.nodeType === "number" && "nodeName" in obj && typeof obj.nodeName === "string" && "isEqualNode" in obj && typeof obj.isEqualNode === "function";
328
298
  }
329
299
  function fnNameFor(func) {
330
- if (func.name) {
331
- return func.name;
332
- }
333
- const matches = functionToString.call(func).match(/^(?:async)?\s*function\s*(?:\*\s*)?([\w$]+)\s*\(/);
334
- return matches ? matches[1] : "<anonymous>";
300
+ if (func.name) {
301
+ return func.name;
302
+ }
303
+ const matches = functionToString.call(func).match(/^(?:async)?\s*function\s*(?:\*\s*)?([\w$]+)\s*\(/);
304
+ return matches ? matches[1] : "<anonymous>";
335
305
  }
336
306
  function getPrototype(obj) {
337
- if (Object.getPrototypeOf) {
338
- return Object.getPrototypeOf(obj);
339
- }
340
- if (obj.constructor.prototype === obj) {
341
- return null;
342
- }
343
- return obj.constructor.prototype;
307
+ if (Object.getPrototypeOf) {
308
+ return Object.getPrototypeOf(obj);
309
+ }
310
+ if (obj.constructor.prototype === obj) {
311
+ return null;
312
+ }
313
+ return obj.constructor.prototype;
344
314
  }
345
315
  function hasProperty(obj, property) {
346
- if (!obj) {
347
- return false;
348
- }
349
- if (Object.prototype.hasOwnProperty.call(obj, property)) {
350
- return true;
351
- }
352
- return hasProperty(getPrototype(obj), property);
316
+ if (!obj) {
317
+ return false;
318
+ }
319
+ if (Object.prototype.hasOwnProperty.call(obj, property)) {
320
+ return true;
321
+ }
322
+ return hasProperty(getPrototype(obj), property);
353
323
  }
354
324
  const IS_KEYED_SENTINEL = "@@__IMMUTABLE_KEYED__@@";
355
325
  const IS_SET_SENTINEL = "@@__IMMUTABLE_SET__@@";
@@ -357,1852 +327,1372 @@ const IS_LIST_SENTINEL = "@@__IMMUTABLE_LIST__@@";
357
327
  const IS_ORDERED_SENTINEL = "@@__IMMUTABLE_ORDERED__@@";
358
328
  const IS_RECORD_SYMBOL = "@@__IMMUTABLE_RECORD__@@";
359
329
  function isImmutableUnorderedKeyed(maybeKeyed) {
360
- return !!(maybeKeyed && maybeKeyed[IS_KEYED_SENTINEL] && !maybeKeyed[IS_ORDERED_SENTINEL]);
330
+ return !!(maybeKeyed && maybeKeyed[IS_KEYED_SENTINEL] && !maybeKeyed[IS_ORDERED_SENTINEL]);
361
331
  }
362
332
  function isImmutableUnorderedSet(maybeSet) {
363
- return !!(maybeSet && maybeSet[IS_SET_SENTINEL] && !maybeSet[IS_ORDERED_SENTINEL]);
333
+ return !!(maybeSet && maybeSet[IS_SET_SENTINEL] && !maybeSet[IS_ORDERED_SENTINEL]);
364
334
  }
365
335
  function isObjectLiteral(source) {
366
- return source != null && typeof source === "object" && !Array.isArray(source);
336
+ return source != null && typeof source === "object" && !Array.isArray(source);
367
337
  }
368
338
  function isImmutableList(source) {
369
- return Boolean(source && isObjectLiteral(source) && source[IS_LIST_SENTINEL]);
339
+ return Boolean(source && isObjectLiteral(source) && source[IS_LIST_SENTINEL]);
370
340
  }
371
341
  function isImmutableOrderedKeyed(source) {
372
- return Boolean(
373
- source && isObjectLiteral(source) && source[IS_KEYED_SENTINEL] && source[IS_ORDERED_SENTINEL]
374
- );
342
+ return Boolean(source && isObjectLiteral(source) && source[IS_KEYED_SENTINEL] && source[IS_ORDERED_SENTINEL]);
375
343
  }
376
344
  function isImmutableOrderedSet(source) {
377
- return Boolean(
378
- source && isObjectLiteral(source) && source[IS_SET_SENTINEL] && source[IS_ORDERED_SENTINEL]
379
- );
345
+ return Boolean(source && isObjectLiteral(source) && source[IS_SET_SENTINEL] && source[IS_ORDERED_SENTINEL]);
380
346
  }
381
347
  function isImmutableRecord(source) {
382
- return Boolean(source && isObjectLiteral(source) && source[IS_RECORD_SYMBOL]);
348
+ return Boolean(source && isObjectLiteral(source) && source[IS_RECORD_SYMBOL]);
383
349
  }
350
+ /**
351
+ * Copyright (c) Facebook, Inc. and its affiliates. All Rights Reserved.
352
+ *
353
+ * This source code is licensed under the MIT license found in the
354
+ * LICENSE file in the root directory of this source tree.
355
+ *
356
+ */
384
357
  const IteratorSymbol = Symbol.iterator;
385
358
  function hasIterator(object) {
386
- return !!(object != null && object[IteratorSymbol]);
359
+ return !!(object != null && object[IteratorSymbol]);
387
360
  }
388
361
  function iterableEquality(a, b, customTesters = [], aStack = [], bStack = []) {
389
- if (typeof a !== "object" || typeof b !== "object" || Array.isArray(a) || Array.isArray(b) || !hasIterator(a) || !hasIterator(b)) {
390
- return void 0;
391
- }
392
- if (a.constructor !== b.constructor) {
393
- return false;
394
- }
395
- let length = aStack.length;
396
- while (length--) {
397
- if (aStack[length] === a) {
398
- return bStack[length] === b;
399
- }
400
- }
401
- aStack.push(a);
402
- bStack.push(b);
403
- const filteredCustomTesters = [
404
- ...customTesters.filter((t) => t !== iterableEquality),
405
- iterableEqualityWithStack
406
- ];
407
- function iterableEqualityWithStack(a2, b2) {
408
- return iterableEquality(a2, b2, [...customTesters], [...aStack], [...bStack]);
409
- }
410
- if (a.size !== void 0) {
411
- if (a.size !== b.size) {
412
- return false;
413
- } else if (isA("Set", a) || isImmutableUnorderedSet(a)) {
414
- let allFound = true;
415
- for (const aValue of a) {
416
- if (!b.has(aValue)) {
417
- let has = false;
418
- for (const bValue of b) {
419
- const isEqual = equals(aValue, bValue, filteredCustomTesters);
420
- if (isEqual === true) {
421
- has = true;
422
- }
423
- }
424
- if (has === false) {
425
- allFound = false;
426
- break;
427
- }
428
- }
429
- }
430
- aStack.pop();
431
- bStack.pop();
432
- return allFound;
433
- } else if (isA("Map", a) || isImmutableUnorderedKeyed(a)) {
434
- let allFound = true;
435
- for (const aEntry of a) {
436
- if (!b.has(aEntry[0]) || !equals(aEntry[1], b.get(aEntry[0]), filteredCustomTesters)) {
437
- let has = false;
438
- for (const bEntry of b) {
439
- const matchedKey = equals(
440
- aEntry[0],
441
- bEntry[0],
442
- filteredCustomTesters
443
- );
444
- let matchedValue = false;
445
- if (matchedKey === true) {
446
- matchedValue = equals(
447
- aEntry[1],
448
- bEntry[1],
449
- filteredCustomTesters
450
- );
451
- }
452
- if (matchedValue === true) {
453
- has = true;
454
- }
455
- }
456
- if (has === false) {
457
- allFound = false;
458
- break;
459
- }
460
- }
461
- }
462
- aStack.pop();
463
- bStack.pop();
464
- return allFound;
465
- }
466
- }
467
- const bIterator = b[IteratorSymbol]();
468
- for (const aValue of a) {
469
- const nextB = bIterator.next();
470
- if (nextB.done || !equals(aValue, nextB.value, filteredCustomTesters)) {
471
- return false;
472
- }
473
- }
474
- if (!bIterator.next().done) {
475
- return false;
476
- }
477
- if (!isImmutableList(a) && !isImmutableOrderedKeyed(a) && !isImmutableOrderedSet(a) && !isImmutableRecord(a)) {
478
- const aEntries = Object.entries(a);
479
- const bEntries = Object.entries(b);
480
- if (!equals(aEntries, bEntries)) {
481
- return false;
482
- }
483
- }
484
- aStack.pop();
485
- bStack.pop();
486
- return true;
362
+ if (typeof a !== "object" || typeof b !== "object" || Array.isArray(a) || Array.isArray(b) || !hasIterator(a) || !hasIterator(b)) {
363
+ return undefined;
364
+ }
365
+ if (a.constructor !== b.constructor) {
366
+ return false;
367
+ }
368
+ let length = aStack.length;
369
+ while (length--) {
370
+ if (aStack[length] === a) {
371
+ return bStack[length] === b;
372
+ }
373
+ }
374
+ aStack.push(a);
375
+ bStack.push(b);
376
+ const filteredCustomTesters = [...customTesters.filter((t) => t !== iterableEquality), iterableEqualityWithStack];
377
+ function iterableEqualityWithStack(a, b) {
378
+ return iterableEquality(a, b, [...customTesters], [...aStack], [...bStack]);
379
+ }
380
+ if (a.size !== undefined) {
381
+ if (a.size !== b.size) {
382
+ return false;
383
+ } else if (isA("Set", a) || isImmutableUnorderedSet(a)) {
384
+ let allFound = true;
385
+ for (const aValue of a) {
386
+ if (!b.has(aValue)) {
387
+ let has = false;
388
+ for (const bValue of b) {
389
+ const isEqual = equals(aValue, bValue, filteredCustomTesters);
390
+ if (isEqual === true) {
391
+ has = true;
392
+ }
393
+ }
394
+ if (has === false) {
395
+ allFound = false;
396
+ break;
397
+ }
398
+ }
399
+ }
400
+ aStack.pop();
401
+ bStack.pop();
402
+ return allFound;
403
+ } else if (isA("Map", a) || isImmutableUnorderedKeyed(a)) {
404
+ let allFound = true;
405
+ for (const aEntry of a) {
406
+ if (!b.has(aEntry[0]) || !equals(aEntry[1], b.get(aEntry[0]), filteredCustomTesters)) {
407
+ let has = false;
408
+ for (const bEntry of b) {
409
+ const matchedKey = equals(aEntry[0], bEntry[0], filteredCustomTesters);
410
+ let matchedValue = false;
411
+ if (matchedKey === true) {
412
+ matchedValue = equals(aEntry[1], bEntry[1], filteredCustomTesters);
413
+ }
414
+ if (matchedValue === true) {
415
+ has = true;
416
+ }
417
+ }
418
+ if (has === false) {
419
+ allFound = false;
420
+ break;
421
+ }
422
+ }
423
+ }
424
+ aStack.pop();
425
+ bStack.pop();
426
+ return allFound;
427
+ }
428
+ }
429
+ const bIterator = b[IteratorSymbol]();
430
+ for (const aValue of a) {
431
+ const nextB = bIterator.next();
432
+ if (nextB.done || !equals(aValue, nextB.value, filteredCustomTesters)) {
433
+ return false;
434
+ }
435
+ }
436
+ if (!bIterator.next().done) {
437
+ return false;
438
+ }
439
+ if (!isImmutableList(a) && !isImmutableOrderedKeyed(a) && !isImmutableOrderedSet(a) && !isImmutableRecord(a)) {
440
+ const aEntries = Object.entries(a);
441
+ const bEntries = Object.entries(b);
442
+ if (!equals(aEntries, bEntries)) {
443
+ return false;
444
+ }
445
+ }
446
+ aStack.pop();
447
+ bStack.pop();
448
+ return true;
487
449
  }
450
+ /**
451
+ * Checks if `hasOwnProperty(object, key)` up the prototype chain, stopping at `Object.prototype`.
452
+ */
488
453
  function hasPropertyInObject(object, key) {
489
- const shouldTerminate = !object || typeof object !== "object" || object === Object.prototype;
490
- if (shouldTerminate) {
491
- return false;
492
- }
493
- return Object.prototype.hasOwnProperty.call(object, key) || hasPropertyInObject(Object.getPrototypeOf(object), key);
454
+ const shouldTerminate = !object || typeof object !== "object" || object === Object.prototype;
455
+ if (shouldTerminate) {
456
+ return false;
457
+ }
458
+ return Object.prototype.hasOwnProperty.call(object, key) || hasPropertyInObject(Object.getPrototypeOf(object), key);
494
459
  }
495
460
  function isObjectWithKeys(a) {
496
- return isObject(a) && !(a instanceof Error) && !Array.isArray(a) && !(a instanceof Date);
461
+ return isObject(a) && !(a instanceof Error) && !Array.isArray(a) && !(a instanceof Date);
497
462
  }
498
463
  function subsetEquality(object, subset, customTesters = []) {
499
- const filteredCustomTesters = customTesters.filter(
500
- (t) => t !== subsetEquality
501
- );
502
- const subsetEqualityWithContext = (seenReferences = /* @__PURE__ */ new WeakMap()) => (object2, subset2) => {
503
- if (!isObjectWithKeys(subset2)) {
504
- return void 0;
505
- }
506
- return Object.keys(subset2).every((key) => {
507
- if (subset2[key] != null && typeof subset2[key] === "object") {
508
- if (seenReferences.has(subset2[key])) {
509
- return equals(object2[key], subset2[key], filteredCustomTesters);
510
- }
511
- seenReferences.set(subset2[key], true);
512
- }
513
- const result = object2 != null && hasPropertyInObject(object2, key) && equals(object2[key], subset2[key], [
514
- ...filteredCustomTesters,
515
- subsetEqualityWithContext(seenReferences)
516
- ]);
517
- seenReferences.delete(subset2[key]);
518
- return result;
519
- });
520
- };
521
- return subsetEqualityWithContext()(object, subset);
464
+ const filteredCustomTesters = customTesters.filter((t) => t !== subsetEquality);
465
+ const subsetEqualityWithContext = (seenReferences = new WeakMap()) => (object, subset) => {
466
+ if (!isObjectWithKeys(subset)) {
467
+ return undefined;
468
+ }
469
+ return Object.keys(subset).every((key) => {
470
+ if (subset[key] != null && typeof subset[key] === "object") {
471
+ if (seenReferences.has(subset[key])) {
472
+ return equals(object[key], subset[key], filteredCustomTesters);
473
+ }
474
+ seenReferences.set(subset[key], true);
475
+ }
476
+ const result = object != null && hasPropertyInObject(object, key) && equals(object[key], subset[key], [...filteredCustomTesters, subsetEqualityWithContext(seenReferences)]);
477
+ seenReferences.delete(subset[key]);
478
+ return result;
479
+ });
480
+ };
481
+ return subsetEqualityWithContext()(object, subset);
522
482
  }
523
483
  function typeEquality(a, b) {
524
- if (a == null || b == null || a.constructor === b.constructor) {
525
- return void 0;
526
- }
527
- return false;
484
+ if (a == null || b == null || a.constructor === b.constructor) {
485
+ return undefined;
486
+ }
487
+ return false;
528
488
  }
529
489
  function arrayBufferEquality(a, b) {
530
- let dataViewA = a;
531
- let dataViewB = b;
532
- if (!(a instanceof DataView && b instanceof DataView)) {
533
- if (!(a instanceof ArrayBuffer) || !(b instanceof ArrayBuffer)) {
534
- return void 0;
535
- }
536
- try {
537
- dataViewA = new DataView(a);
538
- dataViewB = new DataView(b);
539
- } catch {
540
- return void 0;
541
- }
542
- }
543
- if (dataViewA.byteLength !== dataViewB.byteLength) {
544
- return false;
545
- }
546
- for (let i = 0; i < dataViewA.byteLength; i++) {
547
- if (dataViewA.getUint8(i) !== dataViewB.getUint8(i)) {
548
- return false;
549
- }
550
- }
551
- return true;
490
+ let dataViewA = a;
491
+ let dataViewB = b;
492
+ if (!(a instanceof DataView && b instanceof DataView)) {
493
+ if (!(a instanceof ArrayBuffer) || !(b instanceof ArrayBuffer)) {
494
+ return undefined;
495
+ }
496
+ try {
497
+ dataViewA = new DataView(a);
498
+ dataViewB = new DataView(b);
499
+ } catch {
500
+ return undefined;
501
+ }
502
+ }
503
+ if (dataViewA.byteLength !== dataViewB.byteLength) {
504
+ return false;
505
+ }
506
+ for (let i = 0; i < dataViewA.byteLength; i++) {
507
+ if (dataViewA.getUint8(i) !== dataViewB.getUint8(i)) {
508
+ return false;
509
+ }
510
+ }
511
+ return true;
552
512
  }
553
513
  function sparseArrayEquality(a, b, customTesters = []) {
554
- if (!Array.isArray(a) || !Array.isArray(b)) {
555
- return void 0;
556
- }
557
- const aKeys = Object.keys(a);
558
- const bKeys = Object.keys(b);
559
- const filteredCustomTesters = customTesters.filter(
560
- (t) => t !== sparseArrayEquality
561
- );
562
- return equals(a, b, filteredCustomTesters, true) && equals(aKeys, bKeys);
514
+ if (!Array.isArray(a) || !Array.isArray(b)) {
515
+ return undefined;
516
+ }
517
+ const aKeys = Object.keys(a);
518
+ const bKeys = Object.keys(b);
519
+ const filteredCustomTesters = customTesters.filter((t) => t !== sparseArrayEquality);
520
+ return equals(a, b, filteredCustomTesters, true) && equals(aKeys, bKeys);
563
521
  }
564
522
  function generateToBeMessage(deepEqualityName, expected = "#{this}", actual = "#{exp}") {
565
- const toBeMessage = `expected ${expected} to be ${actual} // Object.is equality`;
566
- if (["toStrictEqual", "toEqual"].includes(deepEqualityName)) {
567
- return `${toBeMessage}
568
-
569
- If it should pass with deep equality, replace "toBe" with "${deepEqualityName}"
570
-
571
- Expected: ${expected}
572
- Received: serializes to the same string
573
- `;
574
- }
575
- return toBeMessage;
523
+ const toBeMessage = `expected ${expected} to be ${actual} // Object.is equality`;
524
+ if (["toStrictEqual", "toEqual"].includes(deepEqualityName)) {
525
+ return `${toBeMessage}\n\nIf it should pass with deep equality, replace "toBe" with "${deepEqualityName}"\n\nExpected: ${expected}\nReceived: serializes to the same string\n`;
526
+ }
527
+ return toBeMessage;
576
528
  }
577
529
  function pluralize(word, count) {
578
- return `${count} ${word}${count === 1 ? "" : "s"}`;
530
+ return `${count} ${word}${count === 1 ? "" : "s"}`;
579
531
  }
580
532
  function getObjectKeys(object) {
581
- return [
582
- ...Object.keys(object),
583
- ...Object.getOwnPropertySymbols(object).filter(
584
- (s) => {
585
- var _a;
586
- return (_a = Object.getOwnPropertyDescriptor(object, s)) == null ? void 0 : _a.enumerable;
587
- }
588
- )
589
- ];
533
+ return [...Object.keys(object), ...Object.getOwnPropertySymbols(object).filter((s) => {
534
+ var _Object$getOwnPropert;
535
+ return (_Object$getOwnPropert = Object.getOwnPropertyDescriptor(object, s)) === null || _Object$getOwnPropert === void 0 ? void 0 : _Object$getOwnPropert.enumerable;
536
+ })];
590
537
  }
591
538
  function getObjectSubset(object, subset, customTesters) {
592
- let stripped = 0;
593
- const getObjectSubsetWithContext = (seenReferences = /* @__PURE__ */ new WeakMap()) => (object2, subset2) => {
594
- if (Array.isArray(object2)) {
595
- if (Array.isArray(subset2) && subset2.length === object2.length) {
596
- return subset2.map(
597
- (sub, i) => getObjectSubsetWithContext(seenReferences)(object2[i], sub)
598
- );
599
- }
600
- } else if (object2 instanceof Date) {
601
- return object2;
602
- } else if (isObject(object2) && isObject(subset2)) {
603
- if (equals(object2, subset2, [
604
- ...customTesters,
605
- iterableEquality,
606
- subsetEquality
607
- ])) {
608
- return subset2;
609
- }
610
- const trimmed = {};
611
- seenReferences.set(object2, trimmed);
612
- if (typeof object2.constructor === "function" && typeof object2.constructor.name === "string") {
613
- Object.defineProperty(trimmed, "constructor", {
614
- enumerable: false,
615
- value: object2.constructor
616
- });
617
- }
618
- for (const key of getObjectKeys(object2)) {
619
- if (hasPropertyInObject(subset2, key)) {
620
- trimmed[key] = seenReferences.has(object2[key]) ? seenReferences.get(object2[key]) : getObjectSubsetWithContext(seenReferences)(
621
- object2[key],
622
- subset2[key]
623
- );
624
- } else {
625
- if (!seenReferences.has(object2[key])) {
626
- stripped += 1;
627
- if (isObject(object2[key])) {
628
- stripped += getObjectKeys(object2[key]).length;
629
- }
630
- getObjectSubsetWithContext(seenReferences)(
631
- object2[key],
632
- subset2[key]
633
- );
634
- }
635
- }
636
- }
637
- if (getObjectKeys(trimmed).length > 0) {
638
- return trimmed;
639
- }
640
- }
641
- return object2;
642
- };
643
- return { subset: getObjectSubsetWithContext()(object, subset), stripped };
539
+ let stripped = 0;
540
+ const getObjectSubsetWithContext = (seenReferences = new WeakMap()) => (object, subset) => {
541
+ if (Array.isArray(object)) {
542
+ if (Array.isArray(subset) && subset.length === object.length) {
543
+ return subset.map((sub, i) => getObjectSubsetWithContext(seenReferences)(object[i], sub));
544
+ }
545
+ } else if (object instanceof Date) {
546
+ return object;
547
+ } else if (isObject(object) && isObject(subset)) {
548
+ if (equals(object, subset, [
549
+ ...customTesters,
550
+ iterableEquality,
551
+ subsetEquality
552
+ ])) {
553
+ return subset;
554
+ }
555
+ const trimmed = {};
556
+ seenReferences.set(object, trimmed);
557
+ if (typeof object.constructor === "function" && typeof object.constructor.name === "string") {
558
+ Object.defineProperty(trimmed, "constructor", {
559
+ enumerable: false,
560
+ value: object.constructor
561
+ });
562
+ }
563
+ for (const key of getObjectKeys(object)) {
564
+ if (hasPropertyInObject(subset, key)) {
565
+ trimmed[key] = seenReferences.has(object[key]) ? seenReferences.get(object[key]) : getObjectSubsetWithContext(seenReferences)(object[key], subset[key]);
566
+ } else {
567
+ if (!seenReferences.has(object[key])) {
568
+ stripped += 1;
569
+ if (isObject(object[key])) {
570
+ stripped += getObjectKeys(object[key]).length;
571
+ }
572
+ getObjectSubsetWithContext(seenReferences)(object[key], subset[key]);
573
+ }
574
+ }
575
+ }
576
+ if (getObjectKeys(trimmed).length > 0) {
577
+ return trimmed;
578
+ }
579
+ }
580
+ return object;
581
+ };
582
+ return {
583
+ subset: getObjectSubsetWithContext()(object, subset),
584
+ stripped
585
+ };
644
586
  }
645
587
 
646
588
  if (!Object.prototype.hasOwnProperty.call(globalThis, MATCHERS_OBJECT)) {
647
- const globalState = /* @__PURE__ */ new WeakMap();
648
- const matchers = /* @__PURE__ */ Object.create(null);
649
- const customEqualityTesters = [];
650
- const asymmetricMatchers = /* @__PURE__ */ Object.create(null);
651
- Object.defineProperty(globalThis, MATCHERS_OBJECT, {
652
- get: () => globalState
653
- });
654
- Object.defineProperty(globalThis, JEST_MATCHERS_OBJECT, {
655
- configurable: true,
656
- get: () => ({
657
- state: globalState.get(globalThis[GLOBAL_EXPECT]),
658
- matchers,
659
- customEqualityTesters
660
- })
661
- });
662
- Object.defineProperty(globalThis, ASYMMETRIC_MATCHERS_OBJECT, {
663
- get: () => asymmetricMatchers
664
- });
589
+ const globalState = new WeakMap();
590
+ const matchers = Object.create(null);
591
+ const customEqualityTesters = [];
592
+ const asymmetricMatchers = Object.create(null);
593
+ Object.defineProperty(globalThis, MATCHERS_OBJECT, { get: () => globalState });
594
+ Object.defineProperty(globalThis, JEST_MATCHERS_OBJECT, {
595
+ configurable: true,
596
+ get: () => ({
597
+ state: globalState.get(globalThis[GLOBAL_EXPECT]),
598
+ matchers,
599
+ customEqualityTesters
600
+ })
601
+ });
602
+ Object.defineProperty(globalThis, ASYMMETRIC_MATCHERS_OBJECT, { get: () => asymmetricMatchers });
665
603
  }
666
604
  function getState(expect) {
667
- return globalThis[MATCHERS_OBJECT].get(expect);
605
+ return globalThis[MATCHERS_OBJECT].get(expect);
668
606
  }
669
607
  function setState(state, expect) {
670
- const map = globalThis[MATCHERS_OBJECT];
671
- const current = map.get(expect) || {};
672
- const results = Object.defineProperties(current, {
673
- ...Object.getOwnPropertyDescriptors(current),
674
- ...Object.getOwnPropertyDescriptors(state)
675
- });
676
- map.set(expect, results);
608
+ const map = globalThis[MATCHERS_OBJECT];
609
+ const current = map.get(expect) || {};
610
+ const results = Object.defineProperties(current, {
611
+ ...Object.getOwnPropertyDescriptors(current),
612
+ ...Object.getOwnPropertyDescriptors(state)
613
+ });
614
+ map.set(expect, results);
677
615
  }
678
616
 
679
617
  class AsymmetricMatcher {
680
- constructor(sample, inverse = false) {
681
- this.sample = sample;
682
- this.inverse = inverse;
683
- }
684
- // should have "jest" to be compatible with its ecosystem
685
- $$typeof = Symbol.for("jest.asymmetricMatcher");
686
- getMatcherContext(expect) {
687
- return {
688
- ...getState(expect || globalThis[GLOBAL_EXPECT]),
689
- equals,
690
- isNot: this.inverse,
691
- customTesters: getCustomEqualityTesters(),
692
- utils: {
693
- ...getMatcherUtils(),
694
- diff,
695
- stringify,
696
- iterableEquality,
697
- subsetEquality
698
- }
699
- };
700
- }
618
+ $$typeof = Symbol.for("jest.asymmetricMatcher");
619
+ constructor(sample, inverse = false) {
620
+ this.sample = sample;
621
+ this.inverse = inverse;
622
+ }
623
+ getMatcherContext(expect) {
624
+ return {
625
+ ...getState(expect || globalThis[GLOBAL_EXPECT]),
626
+ equals,
627
+ isNot: this.inverse,
628
+ customTesters: getCustomEqualityTesters(),
629
+ utils: {
630
+ ...getMatcherUtils(),
631
+ diff,
632
+ stringify,
633
+ iterableEquality,
634
+ subsetEquality
635
+ }
636
+ };
637
+ }
701
638
  }
702
639
  AsymmetricMatcher.prototype[Symbol.for("chai/inspect")] = function(options) {
703
- const result = stringify(this, options.depth, { min: true });
704
- if (result.length <= options.truncate) {
705
- return result;
706
- }
707
- return `${this.toString()}{\u2026}`;
640
+ const result = stringify(this, options.depth, { min: true });
641
+ if (result.length <= options.truncate) {
642
+ return result;
643
+ }
644
+ return `${this.toString()}{}`;
708
645
  };
709
646
  class StringContaining extends AsymmetricMatcher {
710
- constructor(sample, inverse = false) {
711
- if (!isA("String", sample)) {
712
- throw new Error("Expected is not a string");
713
- }
714
- super(sample, inverse);
715
- }
716
- asymmetricMatch(other) {
717
- const result = isA("String", other) && other.includes(this.sample);
718
- return this.inverse ? !result : result;
719
- }
720
- toString() {
721
- return `String${this.inverse ? "Not" : ""}Containing`;
722
- }
723
- getExpectedType() {
724
- return "string";
725
- }
647
+ constructor(sample, inverse = false) {
648
+ if (!isA("String", sample)) {
649
+ throw new Error("Expected is not a string");
650
+ }
651
+ super(sample, inverse);
652
+ }
653
+ asymmetricMatch(other) {
654
+ const result = isA("String", other) && other.includes(this.sample);
655
+ return this.inverse ? !result : result;
656
+ }
657
+ toString() {
658
+ return `String${this.inverse ? "Not" : ""}Containing`;
659
+ }
660
+ getExpectedType() {
661
+ return "string";
662
+ }
726
663
  }
727
664
  class Anything extends AsymmetricMatcher {
728
- asymmetricMatch(other) {
729
- return other != null;
730
- }
731
- toString() {
732
- return "Anything";
733
- }
734
- toAsymmetricMatcher() {
735
- return "Anything";
736
- }
665
+ asymmetricMatch(other) {
666
+ return other != null;
667
+ }
668
+ toString() {
669
+ return "Anything";
670
+ }
671
+ toAsymmetricMatcher() {
672
+ return "Anything";
673
+ }
737
674
  }
738
675
  class ObjectContaining extends AsymmetricMatcher {
739
- constructor(sample, inverse = false) {
740
- super(sample, inverse);
741
- }
742
- getPrototype(obj) {
743
- if (Object.getPrototypeOf) {
744
- return Object.getPrototypeOf(obj);
745
- }
746
- if (obj.constructor.prototype === obj) {
747
- return null;
748
- }
749
- return obj.constructor.prototype;
750
- }
751
- hasProperty(obj, property) {
752
- if (!obj) {
753
- return false;
754
- }
755
- if (Object.prototype.hasOwnProperty.call(obj, property)) {
756
- return true;
757
- }
758
- return this.hasProperty(this.getPrototype(obj), property);
759
- }
760
- asymmetricMatch(other) {
761
- if (typeof this.sample !== "object") {
762
- throw new TypeError(
763
- `You must provide an object to ${this.toString()}, not '${typeof this.sample}'.`
764
- );
765
- }
766
- let result = true;
767
- const matcherContext = this.getMatcherContext();
768
- for (const property in this.sample) {
769
- if (!this.hasProperty(other, property) || !equals(
770
- this.sample[property],
771
- other[property],
772
- matcherContext.customTesters
773
- )) {
774
- result = false;
775
- break;
776
- }
777
- }
778
- return this.inverse ? !result : result;
779
- }
780
- toString() {
781
- return `Object${this.inverse ? "Not" : ""}Containing`;
782
- }
783
- getExpectedType() {
784
- return "object";
785
- }
676
+ constructor(sample, inverse = false) {
677
+ super(sample, inverse);
678
+ }
679
+ getPrototype(obj) {
680
+ if (Object.getPrototypeOf) {
681
+ return Object.getPrototypeOf(obj);
682
+ }
683
+ if (obj.constructor.prototype === obj) {
684
+ return null;
685
+ }
686
+ return obj.constructor.prototype;
687
+ }
688
+ hasProperty(obj, property) {
689
+ if (!obj) {
690
+ return false;
691
+ }
692
+ if (Object.prototype.hasOwnProperty.call(obj, property)) {
693
+ return true;
694
+ }
695
+ return this.hasProperty(this.getPrototype(obj), property);
696
+ }
697
+ asymmetricMatch(other) {
698
+ if (typeof this.sample !== "object") {
699
+ throw new TypeError(`You must provide an object to ${this.toString()}, not '${typeof this.sample}'.`);
700
+ }
701
+ let result = true;
702
+ const matcherContext = this.getMatcherContext();
703
+ for (const property in this.sample) {
704
+ if (!this.hasProperty(other, property) || !equals(this.sample[property], other[property], matcherContext.customTesters)) {
705
+ result = false;
706
+ break;
707
+ }
708
+ }
709
+ return this.inverse ? !result : result;
710
+ }
711
+ toString() {
712
+ return `Object${this.inverse ? "Not" : ""}Containing`;
713
+ }
714
+ getExpectedType() {
715
+ return "object";
716
+ }
786
717
  }
787
718
  class ArrayContaining extends AsymmetricMatcher {
788
- constructor(sample, inverse = false) {
789
- super(sample, inverse);
790
- }
791
- asymmetricMatch(other) {
792
- if (!Array.isArray(this.sample)) {
793
- throw new TypeError(
794
- `You must provide an array to ${this.toString()}, not '${typeof this.sample}'.`
795
- );
796
- }
797
- const matcherContext = this.getMatcherContext();
798
- const result = this.sample.length === 0 || Array.isArray(other) && this.sample.every(
799
- (item) => other.some(
800
- (another) => equals(item, another, matcherContext.customTesters)
801
- )
802
- );
803
- return this.inverse ? !result : result;
804
- }
805
- toString() {
806
- return `Array${this.inverse ? "Not" : ""}Containing`;
807
- }
808
- getExpectedType() {
809
- return "array";
810
- }
719
+ constructor(sample, inverse = false) {
720
+ super(sample, inverse);
721
+ }
722
+ asymmetricMatch(other) {
723
+ if (!Array.isArray(this.sample)) {
724
+ throw new TypeError(`You must provide an array to ${this.toString()}, not '${typeof this.sample}'.`);
725
+ }
726
+ const matcherContext = this.getMatcherContext();
727
+ const result = this.sample.length === 0 || Array.isArray(other) && this.sample.every((item) => other.some((another) => equals(item, another, matcherContext.customTesters)));
728
+ return this.inverse ? !result : result;
729
+ }
730
+ toString() {
731
+ return `Array${this.inverse ? "Not" : ""}Containing`;
732
+ }
733
+ getExpectedType() {
734
+ return "array";
735
+ }
811
736
  }
812
737
  class Any extends AsymmetricMatcher {
813
- constructor(sample) {
814
- if (typeof sample === "undefined") {
815
- throw new TypeError(
816
- "any() expects to be passed a constructor function. Please pass one or use anything() to match any object."
817
- );
818
- }
819
- super(sample);
820
- }
821
- fnNameFor(func) {
822
- if (func.name) {
823
- return func.name;
824
- }
825
- const functionToString = Function.prototype.toString;
826
- const matches = functionToString.call(func).match(/^(?:async)?\s*function\s*(?:\*\s*)?([\w$]+)\s*\(/);
827
- return matches ? matches[1] : "<anonymous>";
828
- }
829
- asymmetricMatch(other) {
830
- if (this.sample === String) {
831
- return typeof other == "string" || other instanceof String;
832
- }
833
- if (this.sample === Number) {
834
- return typeof other == "number" || other instanceof Number;
835
- }
836
- if (this.sample === Function) {
837
- return typeof other == "function" || typeof other === "function";
838
- }
839
- if (this.sample === Boolean) {
840
- return typeof other == "boolean" || other instanceof Boolean;
841
- }
842
- if (this.sample === BigInt) {
843
- return typeof other == "bigint" || other instanceof BigInt;
844
- }
845
- if (this.sample === Symbol) {
846
- return typeof other == "symbol" || other instanceof Symbol;
847
- }
848
- if (this.sample === Object) {
849
- return typeof other == "object";
850
- }
851
- return other instanceof this.sample;
852
- }
853
- toString() {
854
- return "Any";
855
- }
856
- getExpectedType() {
857
- if (this.sample === String) {
858
- return "string";
859
- }
860
- if (this.sample === Number) {
861
- return "number";
862
- }
863
- if (this.sample === Function) {
864
- return "function";
865
- }
866
- if (this.sample === Object) {
867
- return "object";
868
- }
869
- if (this.sample === Boolean) {
870
- return "boolean";
871
- }
872
- return this.fnNameFor(this.sample);
873
- }
874
- toAsymmetricMatcher() {
875
- return `Any<${this.fnNameFor(this.sample)}>`;
876
- }
738
+ constructor(sample) {
739
+ if (typeof sample === "undefined") {
740
+ throw new TypeError("any() expects to be passed a constructor function. " + "Please pass one or use anything() to match any object.");
741
+ }
742
+ super(sample);
743
+ }
744
+ fnNameFor(func) {
745
+ if (func.name) {
746
+ return func.name;
747
+ }
748
+ const functionToString = Function.prototype.toString;
749
+ const matches = functionToString.call(func).match(/^(?:async)?\s*function\s*(?:\*\s*)?([\w$]+)\s*\(/);
750
+ return matches ? matches[1] : "<anonymous>";
751
+ }
752
+ asymmetricMatch(other) {
753
+ if (this.sample === String) {
754
+ return typeof other == "string" || other instanceof String;
755
+ }
756
+ if (this.sample === Number) {
757
+ return typeof other == "number" || other instanceof Number;
758
+ }
759
+ if (this.sample === Function) {
760
+ return typeof other == "function" || typeof other === "function";
761
+ }
762
+ if (this.sample === Boolean) {
763
+ return typeof other == "boolean" || other instanceof Boolean;
764
+ }
765
+ if (this.sample === BigInt) {
766
+ return typeof other == "bigint" || other instanceof BigInt;
767
+ }
768
+ if (this.sample === Symbol) {
769
+ return typeof other == "symbol" || other instanceof Symbol;
770
+ }
771
+ if (this.sample === Object) {
772
+ return typeof other == "object";
773
+ }
774
+ return other instanceof this.sample;
775
+ }
776
+ toString() {
777
+ return "Any";
778
+ }
779
+ getExpectedType() {
780
+ if (this.sample === String) {
781
+ return "string";
782
+ }
783
+ if (this.sample === Number) {
784
+ return "number";
785
+ }
786
+ if (this.sample === Function) {
787
+ return "function";
788
+ }
789
+ if (this.sample === Object) {
790
+ return "object";
791
+ }
792
+ if (this.sample === Boolean) {
793
+ return "boolean";
794
+ }
795
+ return this.fnNameFor(this.sample);
796
+ }
797
+ toAsymmetricMatcher() {
798
+ return `Any<${this.fnNameFor(this.sample)}>`;
799
+ }
877
800
  }
878
801
  class StringMatching extends AsymmetricMatcher {
879
- constructor(sample, inverse = false) {
880
- if (!isA("String", sample) && !isA("RegExp", sample)) {
881
- throw new Error("Expected is not a String or a RegExp");
882
- }
883
- super(new RegExp(sample), inverse);
884
- }
885
- asymmetricMatch(other) {
886
- const result = isA("String", other) && this.sample.test(other);
887
- return this.inverse ? !result : result;
888
- }
889
- toString() {
890
- return `String${this.inverse ? "Not" : ""}Matching`;
891
- }
892
- getExpectedType() {
893
- return "string";
894
- }
802
+ constructor(sample, inverse = false) {
803
+ if (!isA("String", sample) && !isA("RegExp", sample)) {
804
+ throw new Error("Expected is not a String or a RegExp");
805
+ }
806
+ super(new RegExp(sample), inverse);
807
+ }
808
+ asymmetricMatch(other) {
809
+ const result = isA("String", other) && this.sample.test(other);
810
+ return this.inverse ? !result : result;
811
+ }
812
+ toString() {
813
+ return `String${this.inverse ? "Not" : ""}Matching`;
814
+ }
815
+ getExpectedType() {
816
+ return "string";
817
+ }
895
818
  }
896
819
  class CloseTo extends AsymmetricMatcher {
897
- precision;
898
- constructor(sample, precision = 2, inverse = false) {
899
- if (!isA("Number", sample)) {
900
- throw new Error("Expected is not a Number");
901
- }
902
- if (!isA("Number", precision)) {
903
- throw new Error("Precision is not a Number");
904
- }
905
- super(sample);
906
- this.inverse = inverse;
907
- this.precision = precision;
908
- }
909
- asymmetricMatch(other) {
910
- if (!isA("Number", other)) {
911
- return false;
912
- }
913
- let result = false;
914
- if (other === Number.POSITIVE_INFINITY && this.sample === Number.POSITIVE_INFINITY) {
915
- result = true;
916
- } else if (other === Number.NEGATIVE_INFINITY && this.sample === Number.NEGATIVE_INFINITY) {
917
- result = true;
918
- } else {
919
- result = Math.abs(this.sample - other) < 10 ** -this.precision / 2;
920
- }
921
- return this.inverse ? !result : result;
922
- }
923
- toString() {
924
- return `Number${this.inverse ? "Not" : ""}CloseTo`;
925
- }
926
- getExpectedType() {
927
- return "number";
928
- }
929
- toAsymmetricMatcher() {
930
- return [
931
- this.toString(),
932
- this.sample,
933
- `(${pluralize("digit", this.precision)})`
934
- ].join(" ");
935
- }
820
+ precision;
821
+ constructor(sample, precision = 2, inverse = false) {
822
+ if (!isA("Number", sample)) {
823
+ throw new Error("Expected is not a Number");
824
+ }
825
+ if (!isA("Number", precision)) {
826
+ throw new Error("Precision is not a Number");
827
+ }
828
+ super(sample);
829
+ this.inverse = inverse;
830
+ this.precision = precision;
831
+ }
832
+ asymmetricMatch(other) {
833
+ if (!isA("Number", other)) {
834
+ return false;
835
+ }
836
+ let result = false;
837
+ if (other === Number.POSITIVE_INFINITY && this.sample === Number.POSITIVE_INFINITY) {
838
+ result = true;
839
+ } else if (other === Number.NEGATIVE_INFINITY && this.sample === Number.NEGATIVE_INFINITY) {
840
+ result = true;
841
+ } else {
842
+ result = Math.abs(this.sample - other) < 10 ** -this.precision / 2;
843
+ }
844
+ return this.inverse ? !result : result;
845
+ }
846
+ toString() {
847
+ return `Number${this.inverse ? "Not" : ""}CloseTo`;
848
+ }
849
+ getExpectedType() {
850
+ return "number";
851
+ }
852
+ toAsymmetricMatcher() {
853
+ return [
854
+ this.toString(),
855
+ this.sample,
856
+ `(${pluralize("digit", this.precision)})`
857
+ ].join(" ");
858
+ }
936
859
  }
937
860
  const JestAsymmetricMatchers = (chai, utils) => {
938
- utils.addMethod(chai.expect, "anything", () => new Anything());
939
- utils.addMethod(chai.expect, "any", (expected) => new Any(expected));
940
- utils.addMethod(
941
- chai.expect,
942
- "stringContaining",
943
- (expected) => new StringContaining(expected)
944
- );
945
- utils.addMethod(
946
- chai.expect,
947
- "objectContaining",
948
- (expected) => new ObjectContaining(expected)
949
- );
950
- utils.addMethod(
951
- chai.expect,
952
- "arrayContaining",
953
- (expected) => new ArrayContaining(expected)
954
- );
955
- utils.addMethod(
956
- chai.expect,
957
- "stringMatching",
958
- (expected) => new StringMatching(expected)
959
- );
960
- utils.addMethod(
961
- chai.expect,
962
- "closeTo",
963
- (expected, precision) => new CloseTo(expected, precision)
964
- );
965
- chai.expect.not = {
966
- stringContaining: (expected) => new StringContaining(expected, true),
967
- objectContaining: (expected) => new ObjectContaining(expected, true),
968
- arrayContaining: (expected) => new ArrayContaining(expected, true),
969
- stringMatching: (expected) => new StringMatching(expected, true),
970
- closeTo: (expected, precision) => new CloseTo(expected, precision, true)
971
- };
861
+ utils.addMethod(chai.expect, "anything", () => new Anything());
862
+ utils.addMethod(chai.expect, "any", (expected) => new Any(expected));
863
+ utils.addMethod(chai.expect, "stringContaining", (expected) => new StringContaining(expected));
864
+ utils.addMethod(chai.expect, "objectContaining", (expected) => new ObjectContaining(expected));
865
+ utils.addMethod(chai.expect, "arrayContaining", (expected) => new ArrayContaining(expected));
866
+ utils.addMethod(chai.expect, "stringMatching", (expected) => new StringMatching(expected));
867
+ utils.addMethod(chai.expect, "closeTo", (expected, precision) => new CloseTo(expected, precision));
868
+ chai.expect.not = {
869
+ stringContaining: (expected) => new StringContaining(expected, true),
870
+ objectContaining: (expected) => new ObjectContaining(expected, true),
871
+ arrayContaining: (expected) => new ArrayContaining(expected, true),
872
+ stringMatching: (expected) => new StringMatching(expected, true),
873
+ closeTo: (expected, precision) => new CloseTo(expected, precision, true)
874
+ };
972
875
  };
973
876
 
974
877
  function createAssertionMessage(util, assertion, hasArgs) {
975
- const not = util.flag(assertion, "negate") ? "not." : "";
976
- const name = `${util.flag(assertion, "_name")}(${hasArgs ? "expected" : ""})`;
977
- const promiseName = util.flag(assertion, "promise");
978
- const promise = promiseName ? `.${promiseName}` : "";
979
- return `expect(actual)${promise}.${not}${name}`;
878
+ const not = util.flag(assertion, "negate") ? "not." : "";
879
+ const name = `${util.flag(assertion, "_name")}(${hasArgs ? "expected" : ""})`;
880
+ const promiseName = util.flag(assertion, "promise");
881
+ const promise = promiseName ? `.${promiseName}` : "";
882
+ return `expect(actual)${promise}.${not}${name}`;
980
883
  }
981
884
  function recordAsyncExpect(_test, promise, assertion, error) {
982
- const test = _test;
983
- if (test && promise instanceof Promise) {
984
- promise = promise.finally(() => {
985
- if (!test.promises) {
986
- return;
987
- }
988
- const index = test.promises.indexOf(promise);
989
- if (index !== -1) {
990
- test.promises.splice(index, 1);
991
- }
992
- });
993
- if (!test.promises) {
994
- test.promises = [];
995
- }
996
- test.promises.push(promise);
997
- let resolved = false;
998
- test.onFinished ?? (test.onFinished = []);
999
- test.onFinished.push(() => {
1000
- var _a;
1001
- if (!resolved) {
1002
- const processor = ((_a = globalThis.__vitest_worker__) == null ? void 0 : _a.onFilterStackTrace) || ((s) => s || "");
1003
- const stack = processor(error.stack);
1004
- console.warn([
1005
- `Promise returned by \`${assertion}\` was not awaited. `,
1006
- "Vitest currently auto-awaits hanging assertions at the end of the test, but this will cause the test to fail in Vitest 3. ",
1007
- "Please remember to await the assertion.\n",
1008
- stack
1009
- ].join(""));
1010
- }
1011
- });
1012
- return {
1013
- then(onFulfilled, onRejected) {
1014
- resolved = true;
1015
- return promise.then(onFulfilled, onRejected);
1016
- },
1017
- catch(onRejected) {
1018
- return promise.catch(onRejected);
1019
- },
1020
- finally(onFinally) {
1021
- return promise.finally(onFinally);
1022
- },
1023
- [Symbol.toStringTag]: "Promise"
1024
- };
1025
- }
1026
- return promise;
885
+ const test = _test;
886
+ if (test && promise instanceof Promise) {
887
+ promise = promise.finally(() => {
888
+ if (!test.promises) {
889
+ return;
890
+ }
891
+ const index = test.promises.indexOf(promise);
892
+ if (index !== -1) {
893
+ test.promises.splice(index, 1);
894
+ }
895
+ });
896
+ if (!test.promises) {
897
+ test.promises = [];
898
+ }
899
+ test.promises.push(promise);
900
+ let resolved = false;
901
+ test.onFinished ?? (test.onFinished = []);
902
+ test.onFinished.push(() => {
903
+ if (!resolved) {
904
+ var _vitest_worker__;
905
+ const processor = ((_vitest_worker__ = globalThis.__vitest_worker__) === null || _vitest_worker__ === void 0 ? void 0 : _vitest_worker__.onFilterStackTrace) || ((s) => s || "");
906
+ const stack = processor(error.stack);
907
+ console.warn([
908
+ `Promise returned by \`${assertion}\` was not awaited. `,
909
+ "Vitest currently auto-awaits hanging assertions at the end of the test, but this will cause the test to fail in Vitest 3. ",
910
+ "Please remember to await the assertion.\n",
911
+ stack
912
+ ].join(""));
913
+ }
914
+ });
915
+ return {
916
+ then(onFulfilled, onRejected) {
917
+ resolved = true;
918
+ return promise.then(onFulfilled, onRejected);
919
+ },
920
+ catch(onRejected) {
921
+ return promise.catch(onRejected);
922
+ },
923
+ finally(onFinally) {
924
+ return promise.finally(onFinally);
925
+ },
926
+ [Symbol.toStringTag]: "Promise"
927
+ };
928
+ }
929
+ return promise;
1027
930
  }
1028
931
  function wrapAssertion(utils, name, fn) {
1029
- return function(...args) {
1030
- var _a;
1031
- if (name !== "withTest") {
1032
- utils.flag(this, "_name", name);
1033
- }
1034
- if (!utils.flag(this, "soft")) {
1035
- return fn.apply(this, args);
1036
- }
1037
- const test = utils.flag(this, "vitest-test");
1038
- if (!test) {
1039
- throw new Error("expect.soft() can only be used inside a test");
1040
- }
1041
- try {
1042
- return fn.apply(this, args);
1043
- } catch (err) {
1044
- test.result || (test.result = { state: "fail" });
1045
- test.result.state = "fail";
1046
- (_a = test.result).errors || (_a.errors = []);
1047
- test.result.errors.push(processError(err));
1048
- }
1049
- };
932
+ return function(...args) {
933
+ if (name !== "withTest") {
934
+ utils.flag(this, "_name", name);
935
+ }
936
+ if (!utils.flag(this, "soft")) {
937
+ return fn.apply(this, args);
938
+ }
939
+ const test = utils.flag(this, "vitest-test");
940
+ if (!test) {
941
+ throw new Error("expect.soft() can only be used inside a test");
942
+ }
943
+ try {
944
+ return fn.apply(this, args);
945
+ } catch (err) {
946
+ var _test$result;
947
+ test.result || (test.result = { state: "fail" });
948
+ test.result.state = "fail";
949
+ (_test$result = test.result).errors || (_test$result.errors = []);
950
+ test.result.errors.push(processError(err));
951
+ }
952
+ };
1050
953
  }
1051
954
 
1052
955
  const JestChaiExpect = (chai, utils) => {
1053
- const { AssertionError } = chai;
1054
- const customTesters = getCustomEqualityTesters();
1055
- function def(name, fn) {
1056
- const addMethod = (n) => {
1057
- const softWrapper = wrapAssertion(utils, n, fn);
1058
- utils.addMethod(chai.Assertion.prototype, n, softWrapper);
1059
- utils.addMethod(
1060
- globalThis[JEST_MATCHERS_OBJECT].matchers,
1061
- n,
1062
- softWrapper
1063
- );
1064
- };
1065
- if (Array.isArray(name)) {
1066
- name.forEach((n) => addMethod(n));
1067
- } else {
1068
- addMethod(name);
1069
- }
1070
- }
1071
- ["throw", "throws", "Throw"].forEach((m) => {
1072
- utils.overwriteMethod(chai.Assertion.prototype, m, (_super) => {
1073
- return function(...args) {
1074
- const promise = utils.flag(this, "promise");
1075
- const object = utils.flag(this, "object");
1076
- const isNot = utils.flag(this, "negate");
1077
- if (promise === "rejects") {
1078
- utils.flag(this, "object", () => {
1079
- throw object;
1080
- });
1081
- } else if (promise === "resolves" && typeof object !== "function") {
1082
- if (!isNot) {
1083
- const message = utils.flag(this, "message") || "expected promise to throw an error, but it didn't";
1084
- const error = {
1085
- showDiff: false
1086
- };
1087
- throw new AssertionError(message, error, utils.flag(this, "ssfi"));
1088
- } else {
1089
- return;
1090
- }
1091
- }
1092
- _super.apply(this, args);
1093
- };
1094
- });
1095
- });
1096
- def("withTest", function(test) {
1097
- utils.flag(this, "vitest-test", test);
1098
- return this;
1099
- });
1100
- def("toEqual", function(expected) {
1101
- const actual = utils.flag(this, "object");
1102
- const equal = equals(actual, expected, [
1103
- ...customTesters,
1104
- iterableEquality
1105
- ]);
1106
- return this.assert(
1107
- equal,
1108
- "expected #{this} to deeply equal #{exp}",
1109
- "expected #{this} to not deeply equal #{exp}",
1110
- expected,
1111
- actual
1112
- );
1113
- });
1114
- def("toStrictEqual", function(expected) {
1115
- const obj = utils.flag(this, "object");
1116
- const equal = equals(
1117
- obj,
1118
- expected,
1119
- [
1120
- ...customTesters,
1121
- iterableEquality,
1122
- typeEquality,
1123
- sparseArrayEquality,
1124
- arrayBufferEquality
1125
- ],
1126
- true
1127
- );
1128
- return this.assert(
1129
- equal,
1130
- "expected #{this} to strictly equal #{exp}",
1131
- "expected #{this} to not strictly equal #{exp}",
1132
- expected,
1133
- obj
1134
- );
1135
- });
1136
- def("toBe", function(expected) {
1137
- const actual = this._obj;
1138
- const pass = Object.is(actual, expected);
1139
- let deepEqualityName = "";
1140
- if (!pass) {
1141
- const toStrictEqualPass = equals(
1142
- actual,
1143
- expected,
1144
- [
1145
- ...customTesters,
1146
- iterableEquality,
1147
- typeEquality,
1148
- sparseArrayEquality,
1149
- arrayBufferEquality
1150
- ],
1151
- true
1152
- );
1153
- if (toStrictEqualPass) {
1154
- deepEqualityName = "toStrictEqual";
1155
- } else {
1156
- const toEqualPass = equals(actual, expected, [
1157
- ...customTesters,
1158
- iterableEquality
1159
- ]);
1160
- if (toEqualPass) {
1161
- deepEqualityName = "toEqual";
1162
- }
1163
- }
1164
- }
1165
- return this.assert(
1166
- pass,
1167
- generateToBeMessage(deepEqualityName),
1168
- "expected #{this} not to be #{exp} // Object.is equality",
1169
- expected,
1170
- actual
1171
- );
1172
- });
1173
- def("toMatchObject", function(expected) {
1174
- const actual = this._obj;
1175
- const pass = equals(actual, expected, [
1176
- ...customTesters,
1177
- iterableEquality,
1178
- subsetEquality
1179
- ]);
1180
- const isNot = utils.flag(this, "negate");
1181
- const { subset: actualSubset, stripped } = getObjectSubset(
1182
- actual,
1183
- expected,
1184
- customTesters
1185
- );
1186
- if (pass && isNot || !pass && !isNot) {
1187
- const msg = utils.getMessage(this, [
1188
- pass,
1189
- "expected #{this} to match object #{exp}",
1190
- "expected #{this} to not match object #{exp}",
1191
- expected,
1192
- actualSubset,
1193
- false
1194
- ]);
1195
- const message = stripped === 0 ? msg : `${msg}
1196
- (${stripped} matching ${stripped === 1 ? "property" : "properties"} omitted from actual)`;
1197
- throw new AssertionError(message, {
1198
- showDiff: true,
1199
- expected,
1200
- actual: actualSubset
1201
- });
1202
- }
1203
- });
1204
- def("toMatch", function(expected) {
1205
- const actual = this._obj;
1206
- if (typeof actual !== "string") {
1207
- throw new TypeError(
1208
- `.toMatch() expects to receive a string, but got ${typeof actual}`
1209
- );
1210
- }
1211
- return this.assert(
1212
- typeof expected === "string" ? actual.includes(expected) : actual.match(expected),
1213
- `expected #{this} to match #{exp}`,
1214
- `expected #{this} not to match #{exp}`,
1215
- expected,
1216
- actual
1217
- );
1218
- });
1219
- def("toContain", function(item) {
1220
- const actual = this._obj;
1221
- if (typeof Node !== "undefined" && actual instanceof Node) {
1222
- if (!(item instanceof Node)) {
1223
- throw new TypeError(
1224
- `toContain() expected a DOM node as the argument, but got ${typeof item}`
1225
- );
1226
- }
1227
- return this.assert(
1228
- actual.contains(item),
1229
- "expected #{this} to contain element #{exp}",
1230
- "expected #{this} not to contain element #{exp}",
1231
- item,
1232
- actual
1233
- );
1234
- }
1235
- if (typeof DOMTokenList !== "undefined" && actual instanceof DOMTokenList) {
1236
- assertTypes(item, "class name", ["string"]);
1237
- const isNot = utils.flag(this, "negate");
1238
- const expectedClassList = isNot ? actual.value.replace(item, "").trim() : `${actual.value} ${item}`;
1239
- return this.assert(
1240
- actual.contains(item),
1241
- `expected "${actual.value}" to contain "${item}"`,
1242
- `expected "${actual.value}" not to contain "${item}"`,
1243
- expectedClassList,
1244
- actual.value
1245
- );
1246
- }
1247
- if (typeof actual === "string" && typeof item === "string") {
1248
- return this.assert(
1249
- actual.includes(item),
1250
- `expected #{this} to contain #{exp}`,
1251
- `expected #{this} not to contain #{exp}`,
1252
- item,
1253
- actual
1254
- );
1255
- }
1256
- if (actual != null && typeof actual !== "string") {
1257
- utils.flag(this, "object", Array.from(actual));
1258
- }
1259
- return this.contain(item);
1260
- });
1261
- def("toContainEqual", function(expected) {
1262
- const obj = utils.flag(this, "object");
1263
- const index = Array.from(obj).findIndex((item) => {
1264
- return equals(item, expected, customTesters);
1265
- });
1266
- this.assert(
1267
- index !== -1,
1268
- "expected #{this} to deep equally contain #{exp}",
1269
- "expected #{this} to not deep equally contain #{exp}",
1270
- expected
1271
- );
1272
- });
1273
- def("toBeTruthy", function() {
1274
- const obj = utils.flag(this, "object");
1275
- this.assert(
1276
- Boolean(obj),
1277
- "expected #{this} to be truthy",
1278
- "expected #{this} to not be truthy",
1279
- true,
1280
- obj
1281
- );
1282
- });
1283
- def("toBeFalsy", function() {
1284
- const obj = utils.flag(this, "object");
1285
- this.assert(
1286
- !obj,
1287
- "expected #{this} to be falsy",
1288
- "expected #{this} to not be falsy",
1289
- false,
1290
- obj
1291
- );
1292
- });
1293
- def("toBeGreaterThan", function(expected) {
1294
- const actual = this._obj;
1295
- assertTypes(actual, "actual", ["number", "bigint"]);
1296
- assertTypes(expected, "expected", ["number", "bigint"]);
1297
- return this.assert(
1298
- actual > expected,
1299
- `expected ${actual} to be greater than ${expected}`,
1300
- `expected ${actual} to be not greater than ${expected}`,
1301
- expected,
1302
- actual,
1303
- false
1304
- );
1305
- });
1306
- def("toBeGreaterThanOrEqual", function(expected) {
1307
- const actual = this._obj;
1308
- assertTypes(actual, "actual", ["number", "bigint"]);
1309
- assertTypes(expected, "expected", ["number", "bigint"]);
1310
- return this.assert(
1311
- actual >= expected,
1312
- `expected ${actual} to be greater than or equal to ${expected}`,
1313
- `expected ${actual} to be not greater than or equal to ${expected}`,
1314
- expected,
1315
- actual,
1316
- false
1317
- );
1318
- });
1319
- def("toBeLessThan", function(expected) {
1320
- const actual = this._obj;
1321
- assertTypes(actual, "actual", ["number", "bigint"]);
1322
- assertTypes(expected, "expected", ["number", "bigint"]);
1323
- return this.assert(
1324
- actual < expected,
1325
- `expected ${actual} to be less than ${expected}`,
1326
- `expected ${actual} to be not less than ${expected}`,
1327
- expected,
1328
- actual,
1329
- false
1330
- );
1331
- });
1332
- def("toBeLessThanOrEqual", function(expected) {
1333
- const actual = this._obj;
1334
- assertTypes(actual, "actual", ["number", "bigint"]);
1335
- assertTypes(expected, "expected", ["number", "bigint"]);
1336
- return this.assert(
1337
- actual <= expected,
1338
- `expected ${actual} to be less than or equal to ${expected}`,
1339
- `expected ${actual} to be not less than or equal to ${expected}`,
1340
- expected,
1341
- actual,
1342
- false
1343
- );
1344
- });
1345
- def("toBeNaN", function() {
1346
- const obj = utils.flag(this, "object");
1347
- this.assert(
1348
- Number.isNaN(obj),
1349
- "expected #{this} to be NaN",
1350
- "expected #{this} not to be NaN",
1351
- Number.NaN,
1352
- obj
1353
- );
1354
- });
1355
- def("toBeUndefined", function() {
1356
- const obj = utils.flag(this, "object");
1357
- this.assert(
1358
- void 0 === obj,
1359
- "expected #{this} to be undefined",
1360
- "expected #{this} not to be undefined",
1361
- void 0,
1362
- obj
1363
- );
1364
- });
1365
- def("toBeNull", function() {
1366
- const obj = utils.flag(this, "object");
1367
- this.assert(
1368
- obj === null,
1369
- "expected #{this} to be null",
1370
- "expected #{this} not to be null",
1371
- null,
1372
- obj
1373
- );
1374
- });
1375
- def("toBeDefined", function() {
1376
- const obj = utils.flag(this, "object");
1377
- this.assert(
1378
- typeof obj !== "undefined",
1379
- "expected #{this} to be defined",
1380
- "expected #{this} to be undefined",
1381
- obj
1382
- );
1383
- });
1384
- def(
1385
- "toBeTypeOf",
1386
- function(expected) {
1387
- const actual = typeof this._obj;
1388
- const equal = expected === actual;
1389
- return this.assert(
1390
- equal,
1391
- "expected #{this} to be type of #{exp}",
1392
- "expected #{this} not to be type of #{exp}",
1393
- expected,
1394
- actual
1395
- );
1396
- }
1397
- );
1398
- def("toBeInstanceOf", function(obj) {
1399
- return this.instanceOf(obj);
1400
- });
1401
- def("toHaveLength", function(length) {
1402
- return this.have.length(length);
1403
- });
1404
- def(
1405
- "toHaveProperty",
1406
- function(...args) {
1407
- if (Array.isArray(args[0])) {
1408
- args[0] = args[0].map((key) => String(key).replace(/([.[\]])/g, "\\$1")).join(".");
1409
- }
1410
- const actual = this._obj;
1411
- const [propertyName, expected] = args;
1412
- const getValue = () => {
1413
- const hasOwn = Object.prototype.hasOwnProperty.call(
1414
- actual,
1415
- propertyName
1416
- );
1417
- if (hasOwn) {
1418
- return { value: actual[propertyName], exists: true };
1419
- }
1420
- return utils.getPathInfo(actual, propertyName);
1421
- };
1422
- const { value, exists } = getValue();
1423
- const pass = exists && (args.length === 1 || equals(expected, value, customTesters));
1424
- const valueString = args.length === 1 ? "" : ` with value ${utils.objDisplay(expected)}`;
1425
- return this.assert(
1426
- pass,
1427
- `expected #{this} to have property "${propertyName}"${valueString}`,
1428
- `expected #{this} to not have property "${propertyName}"${valueString}`,
1429
- expected,
1430
- exists ? value : void 0
1431
- );
1432
- }
1433
- );
1434
- def("toBeCloseTo", function(received, precision = 2) {
1435
- const expected = this._obj;
1436
- let pass = false;
1437
- let expectedDiff = 0;
1438
- let receivedDiff = 0;
1439
- if (received === Number.POSITIVE_INFINITY && expected === Number.POSITIVE_INFINITY) {
1440
- pass = true;
1441
- } else if (received === Number.NEGATIVE_INFINITY && expected === Number.NEGATIVE_INFINITY) {
1442
- pass = true;
1443
- } else {
1444
- expectedDiff = 10 ** -precision / 2;
1445
- receivedDiff = Math.abs(expected - received);
1446
- pass = receivedDiff < expectedDiff;
1447
- }
1448
- return this.assert(
1449
- pass,
1450
- `expected #{this} to be close to #{exp}, received difference is ${receivedDiff}, but expected ${expectedDiff}`,
1451
- `expected #{this} to not be close to #{exp}, received difference is ${receivedDiff}, but expected ${expectedDiff}`,
1452
- received,
1453
- expected,
1454
- false
1455
- );
1456
- });
1457
- function assertIsMock(assertion) {
1458
- if (!isMockFunction(assertion._obj)) {
1459
- throw new TypeError(
1460
- `${utils.inspect(assertion._obj)} is not a spy or a call to a spy!`
1461
- );
1462
- }
1463
- }
1464
- function getSpy(assertion) {
1465
- assertIsMock(assertion);
1466
- return assertion._obj;
1467
- }
1468
- def(["toHaveBeenCalledTimes", "toBeCalledTimes"], function(number) {
1469
- const spy = getSpy(this);
1470
- const spyName = spy.getMockName();
1471
- const callCount = spy.mock.calls.length;
1472
- return this.assert(
1473
- callCount === number,
1474
- `expected "${spyName}" to be called #{exp} times, but got ${callCount} times`,
1475
- `expected "${spyName}" to not be called #{exp} times`,
1476
- number,
1477
- callCount,
1478
- false
1479
- );
1480
- });
1481
- def("toHaveBeenCalledOnce", function() {
1482
- const spy = getSpy(this);
1483
- const spyName = spy.getMockName();
1484
- const callCount = spy.mock.calls.length;
1485
- return this.assert(
1486
- callCount === 1,
1487
- `expected "${spyName}" to be called once, but got ${callCount} times`,
1488
- `expected "${spyName}" to not be called once`,
1489
- 1,
1490
- callCount,
1491
- false
1492
- );
1493
- });
1494
- def(["toHaveBeenCalled", "toBeCalled"], function() {
1495
- const spy = getSpy(this);
1496
- const spyName = spy.getMockName();
1497
- const callCount = spy.mock.calls.length;
1498
- const called = callCount > 0;
1499
- const isNot = utils.flag(this, "negate");
1500
- let msg = utils.getMessage(this, [
1501
- called,
1502
- `expected "${spyName}" to be called at least once`,
1503
- `expected "${spyName}" to not be called at all, but actually been called ${callCount} times`,
1504
- true,
1505
- called
1506
- ]);
1507
- if (called && isNot) {
1508
- msg = formatCalls(spy, msg);
1509
- }
1510
- if (called && isNot || !called && !isNot) {
1511
- throw new AssertionError(msg);
1512
- }
1513
- });
1514
- function equalsArgumentArray(a, b) {
1515
- return a.length === b.length && a.every(
1516
- (aItem, i) => equals(aItem, b[i], [...customTesters, iterableEquality])
1517
- );
1518
- }
1519
- def(["toHaveBeenCalledWith", "toBeCalledWith"], function(...args) {
1520
- const spy = getSpy(this);
1521
- const spyName = spy.getMockName();
1522
- const pass = spy.mock.calls.some((callArg) => equalsArgumentArray(callArg, args));
1523
- const isNot = utils.flag(this, "negate");
1524
- const msg = utils.getMessage(this, [
1525
- pass,
1526
- `expected "${spyName}" to be called with arguments: #{exp}`,
1527
- `expected "${spyName}" to not be called with arguments: #{exp}`,
1528
- args
1529
- ]);
1530
- if (pass && isNot || !pass && !isNot) {
1531
- throw new AssertionError(formatCalls(spy, msg, args));
1532
- }
1533
- });
1534
- def("toHaveBeenCalledExactlyOnceWith", function(...args) {
1535
- const spy = getSpy(this);
1536
- const spyName = spy.getMockName();
1537
- const callCount = spy.mock.calls.length;
1538
- const hasCallWithArgs = spy.mock.calls.some((callArg) => equalsArgumentArray(callArg, args));
1539
- const pass = hasCallWithArgs && callCount === 1;
1540
- const isNot = utils.flag(this, "negate");
1541
- const msg = utils.getMessage(this, [
1542
- pass,
1543
- `expected "${spyName}" to be called once with arguments: #{exp}`,
1544
- `expected "${spyName}" to not be called once with arguments: #{exp}`,
1545
- args
1546
- ]);
1547
- if (pass && isNot || !pass && !isNot) {
1548
- throw new AssertionError(formatCalls(spy, msg, args));
1549
- }
1550
- });
1551
- def(
1552
- ["toHaveBeenNthCalledWith", "nthCalledWith"],
1553
- function(times, ...args) {
1554
- const spy = getSpy(this);
1555
- const spyName = spy.getMockName();
1556
- const nthCall = spy.mock.calls[times - 1];
1557
- const callCount = spy.mock.calls.length;
1558
- const isCalled = times <= callCount;
1559
- this.assert(
1560
- nthCall && equalsArgumentArray(nthCall, args),
1561
- `expected ${ordinalOf(
1562
- times
1563
- )} "${spyName}" call to have been called with #{exp}${isCalled ? `` : `, but called only ${callCount} times`}`,
1564
- `expected ${ordinalOf(
1565
- times
1566
- )} "${spyName}" call to not have been called with #{exp}`,
1567
- args,
1568
- nthCall,
1569
- isCalled
1570
- );
1571
- }
1572
- );
1573
- def(
1574
- ["toHaveBeenLastCalledWith", "lastCalledWith"],
1575
- function(...args) {
1576
- const spy = getSpy(this);
1577
- const spyName = spy.getMockName();
1578
- const lastCall = spy.mock.calls[spy.mock.calls.length - 1];
1579
- this.assert(
1580
- lastCall && equalsArgumentArray(lastCall, args),
1581
- `expected last "${spyName}" call to have been called with #{exp}`,
1582
- `expected last "${spyName}" call to not have been called with #{exp}`,
1583
- args,
1584
- lastCall
1585
- );
1586
- }
1587
- );
1588
- function isSpyCalledBeforeAnotherSpy(beforeSpy, afterSpy, failIfNoFirstInvocation) {
1589
- const beforeInvocationCallOrder = beforeSpy.mock.invocationCallOrder;
1590
- const afterInvocationCallOrder = afterSpy.mock.invocationCallOrder;
1591
- if (beforeInvocationCallOrder.length === 0) {
1592
- return !failIfNoFirstInvocation;
1593
- }
1594
- if (afterInvocationCallOrder.length === 0) {
1595
- return false;
1596
- }
1597
- return beforeInvocationCallOrder[0] < afterInvocationCallOrder[0];
1598
- }
1599
- def(
1600
- ["toHaveBeenCalledBefore"],
1601
- function(resultSpy, failIfNoFirstInvocation = true) {
1602
- const expectSpy = getSpy(this);
1603
- if (!isMockFunction(resultSpy)) {
1604
- throw new TypeError(
1605
- `${utils.inspect(resultSpy)} is not a spy or a call to a spy`
1606
- );
1607
- }
1608
- this.assert(
1609
- isSpyCalledBeforeAnotherSpy(
1610
- expectSpy,
1611
- resultSpy,
1612
- failIfNoFirstInvocation
1613
- ),
1614
- `expected "${expectSpy.getMockName()}" to have been called before "${resultSpy.getMockName()}"`,
1615
- `expected "${expectSpy.getMockName()}" to not have been called before "${resultSpy.getMockName()}"`,
1616
- resultSpy,
1617
- expectSpy
1618
- );
1619
- }
1620
- );
1621
- def(
1622
- ["toHaveBeenCalledAfter"],
1623
- function(resultSpy, failIfNoFirstInvocation = true) {
1624
- const expectSpy = getSpy(this);
1625
- if (!isMockFunction(resultSpy)) {
1626
- throw new TypeError(
1627
- `${utils.inspect(resultSpy)} is not a spy or a call to a spy`
1628
- );
1629
- }
1630
- this.assert(
1631
- isSpyCalledBeforeAnotherSpy(
1632
- resultSpy,
1633
- expectSpy,
1634
- failIfNoFirstInvocation
1635
- ),
1636
- `expected "${expectSpy.getMockName()}" to have been called after "${resultSpy.getMockName()}"`,
1637
- `expected "${expectSpy.getMockName()}" to not have been called after "${resultSpy.getMockName()}"`,
1638
- resultSpy,
1639
- expectSpy
1640
- );
1641
- }
1642
- );
1643
- def(
1644
- ["toThrow", "toThrowError"],
1645
- function(expected) {
1646
- if (typeof expected === "string" || typeof expected === "undefined" || expected instanceof RegExp) {
1647
- return this.throws(expected === "" ? /^$/ : expected);
1648
- }
1649
- const obj = this._obj;
1650
- const promise = utils.flag(this, "promise");
1651
- const isNot = utils.flag(this, "negate");
1652
- let thrown = null;
1653
- if (promise === "rejects") {
1654
- thrown = obj;
1655
- } else if (promise === "resolves" && typeof obj !== "function") {
1656
- if (!isNot) {
1657
- const message = utils.flag(this, "message") || "expected promise to throw an error, but it didn't";
1658
- const error = {
1659
- showDiff: false
1660
- };
1661
- throw new AssertionError(message, error, utils.flag(this, "ssfi"));
1662
- } else {
1663
- return;
1664
- }
1665
- } else {
1666
- let isThrow = false;
1667
- try {
1668
- obj();
1669
- } catch (err) {
1670
- isThrow = true;
1671
- thrown = err;
1672
- }
1673
- if (!isThrow && !isNot) {
1674
- const message = utils.flag(this, "message") || "expected function to throw an error, but it didn't";
1675
- const error = {
1676
- showDiff: false
1677
- };
1678
- throw new AssertionError(message, error, utils.flag(this, "ssfi"));
1679
- }
1680
- }
1681
- if (typeof expected === "function") {
1682
- const name = expected.name || expected.prototype.constructor.name;
1683
- return this.assert(
1684
- thrown && thrown instanceof expected,
1685
- `expected error to be instance of ${name}`,
1686
- `expected error not to be instance of ${name}`,
1687
- expected,
1688
- thrown
1689
- );
1690
- }
1691
- if (expected instanceof Error) {
1692
- const equal = equals(thrown, expected, [
1693
- ...customTesters,
1694
- iterableEquality
1695
- ]);
1696
- return this.assert(
1697
- equal,
1698
- "expected a thrown error to be #{exp}",
1699
- "expected a thrown error not to be #{exp}",
1700
- expected,
1701
- thrown
1702
- );
1703
- }
1704
- if (typeof expected === "object" && "asymmetricMatch" in expected && typeof expected.asymmetricMatch === "function") {
1705
- const matcher = expected;
1706
- return this.assert(
1707
- thrown && matcher.asymmetricMatch(thrown),
1708
- "expected error to match asymmetric matcher",
1709
- "expected error not to match asymmetric matcher",
1710
- matcher,
1711
- thrown
1712
- );
1713
- }
1714
- throw new Error(
1715
- `"toThrow" expects string, RegExp, function, Error instance or asymmetric matcher, got "${typeof expected}"`
1716
- );
1717
- }
1718
- );
1719
- [
1720
- {
1721
- name: "toHaveResolved",
1722
- condition: (spy) => spy.mock.settledResults.length > 0 && spy.mock.settledResults.some(({ type }) => type === "fulfilled"),
1723
- action: "resolved"
1724
- },
1725
- {
1726
- name: ["toHaveReturned", "toReturn"],
1727
- condition: (spy) => spy.mock.calls.length > 0 && spy.mock.results.some(({ type }) => type !== "throw"),
1728
- action: "called"
1729
- }
1730
- ].forEach(({ name, condition, action }) => {
1731
- def(name, function() {
1732
- const spy = getSpy(this);
1733
- const spyName = spy.getMockName();
1734
- const pass = condition(spy);
1735
- this.assert(
1736
- pass,
1737
- `expected "${spyName}" to be successfully ${action} at least once`,
1738
- `expected "${spyName}" to not be successfully ${action}`,
1739
- pass,
1740
- !pass,
1741
- false
1742
- );
1743
- });
1744
- });
1745
- [
1746
- {
1747
- name: "toHaveResolvedTimes",
1748
- condition: (spy, times) => spy.mock.settledResults.reduce(
1749
- (s, { type }) => type === "fulfilled" ? ++s : s,
1750
- 0
1751
- ) === times,
1752
- action: "resolved"
1753
- },
1754
- {
1755
- name: ["toHaveReturnedTimes", "toReturnTimes"],
1756
- condition: (spy, times) => spy.mock.results.reduce(
1757
- (s, { type }) => type === "throw" ? s : ++s,
1758
- 0
1759
- ) === times,
1760
- action: "called"
1761
- }
1762
- ].forEach(({ name, condition, action }) => {
1763
- def(name, function(times) {
1764
- const spy = getSpy(this);
1765
- const spyName = spy.getMockName();
1766
- const pass = condition(spy, times);
1767
- this.assert(
1768
- pass,
1769
- `expected "${spyName}" to be successfully ${action} ${times} times`,
1770
- `expected "${spyName}" to not be successfully ${action} ${times} times`,
1771
- `expected resolved times: ${times}`,
1772
- `received resolved times: ${pass}`,
1773
- false
1774
- );
1775
- });
1776
- });
1777
- [
1778
- {
1779
- name: "toHaveResolvedWith",
1780
- condition: (spy, value) => spy.mock.settledResults.some(
1781
- ({ type, value: result }) => type === "fulfilled" && equals(value, result)
1782
- ),
1783
- action: "resolve"
1784
- },
1785
- {
1786
- name: ["toHaveReturnedWith", "toReturnWith"],
1787
- condition: (spy, value) => spy.mock.results.some(
1788
- ({ type, value: result }) => type === "return" && equals(value, result)
1789
- ),
1790
- action: "return"
1791
- }
1792
- ].forEach(({ name, condition, action }) => {
1793
- def(name, function(value) {
1794
- const spy = getSpy(this);
1795
- const pass = condition(spy, value);
1796
- const isNot = utils.flag(this, "negate");
1797
- if (pass && isNot || !pass && !isNot) {
1798
- const spyName = spy.getMockName();
1799
- const msg = utils.getMessage(this, [
1800
- pass,
1801
- `expected "${spyName}" to ${action} with: #{exp} at least once`,
1802
- `expected "${spyName}" to not ${action} with: #{exp}`,
1803
- value
1804
- ]);
1805
- const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1806
- throw new AssertionError(formatReturns(spy, results, msg, value));
1807
- }
1808
- });
1809
- });
1810
- [
1811
- {
1812
- name: "toHaveLastResolvedWith",
1813
- condition: (spy, value) => {
1814
- const result = spy.mock.settledResults[spy.mock.settledResults.length - 1];
1815
- return result && result.type === "fulfilled" && equals(result.value, value);
1816
- },
1817
- action: "resolve"
1818
- },
1819
- {
1820
- name: ["toHaveLastReturnedWith", "lastReturnedWith"],
1821
- condition: (spy, value) => {
1822
- const result = spy.mock.results[spy.mock.results.length - 1];
1823
- return result && result.type === "return" && equals(result.value, value);
1824
- },
1825
- action: "return"
1826
- }
1827
- ].forEach(({ name, condition, action }) => {
1828
- def(name, function(value) {
1829
- const spy = getSpy(this);
1830
- const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1831
- const result = results[results.length - 1];
1832
- const spyName = spy.getMockName();
1833
- this.assert(
1834
- condition(spy, value),
1835
- `expected last "${spyName}" call to ${action} #{exp}`,
1836
- `expected last "${spyName}" call to not ${action} #{exp}`,
1837
- value,
1838
- result == null ? void 0 : result.value
1839
- );
1840
- });
1841
- });
1842
- [
1843
- {
1844
- name: "toHaveNthResolvedWith",
1845
- condition: (spy, index, value) => {
1846
- const result = spy.mock.settledResults[index - 1];
1847
- return result && result.type === "fulfilled" && equals(result.value, value);
1848
- },
1849
- action: "resolve"
1850
- },
1851
- {
1852
- name: ["toHaveNthReturnedWith", "nthReturnedWith"],
1853
- condition: (spy, index, value) => {
1854
- const result = spy.mock.results[index - 1];
1855
- return result && result.type === "return" && equals(result.value, value);
1856
- },
1857
- action: "return"
1858
- }
1859
- ].forEach(({ name, condition, action }) => {
1860
- def(name, function(nthCall, value) {
1861
- const spy = getSpy(this);
1862
- const spyName = spy.getMockName();
1863
- const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1864
- const result = results[nthCall - 1];
1865
- const ordinalCall = `${ordinalOf(nthCall)} call`;
1866
- this.assert(
1867
- condition(spy, nthCall, value),
1868
- `expected ${ordinalCall} "${spyName}" call to ${action} #{exp}`,
1869
- `expected ${ordinalCall} "${spyName}" call to not ${action} #{exp}`,
1870
- value,
1871
- result == null ? void 0 : result.value
1872
- );
1873
- });
1874
- });
1875
- def("withContext", function(context) {
1876
- for (const key in context) {
1877
- utils.flag(this, key, context[key]);
1878
- }
1879
- return this;
1880
- });
1881
- utils.addProperty(
1882
- chai.Assertion.prototype,
1883
- "resolves",
1884
- function __VITEST_RESOLVES__() {
1885
- const error = new Error("resolves");
1886
- utils.flag(this, "promise", "resolves");
1887
- utils.flag(this, "error", error);
1888
- const test = utils.flag(this, "vitest-test");
1889
- const obj = utils.flag(this, "object");
1890
- if (utils.flag(this, "poll")) {
1891
- throw new SyntaxError(
1892
- `expect.poll() is not supported in combination with .resolves`
1893
- );
1894
- }
1895
- if (typeof (obj == null ? void 0 : obj.then) !== "function") {
1896
- throw new TypeError(
1897
- `You must provide a Promise to expect() when using .resolves, not '${typeof obj}'.`
1898
- );
1899
- }
1900
- const proxy = new Proxy(this, {
1901
- get: (target, key, receiver) => {
1902
- const result = Reflect.get(target, key, receiver);
1903
- if (typeof result !== "function") {
1904
- return result instanceof chai.Assertion ? proxy : result;
1905
- }
1906
- return (...args) => {
1907
- utils.flag(this, "_name", key);
1908
- const promise = obj.then(
1909
- (value) => {
1910
- utils.flag(this, "object", value);
1911
- return result.call(this, ...args);
1912
- },
1913
- (err) => {
1914
- const _error = new AssertionError(
1915
- `promise rejected "${utils.inspect(
1916
- err
1917
- )}" instead of resolving`,
1918
- { showDiff: false }
1919
- );
1920
- _error.cause = err;
1921
- _error.stack = error.stack.replace(
1922
- error.message,
1923
- _error.message
1924
- );
1925
- throw _error;
1926
- }
1927
- );
1928
- return recordAsyncExpect(
1929
- test,
1930
- promise,
1931
- createAssertionMessage(utils, this, !!args.length),
1932
- error
1933
- );
1934
- };
1935
- }
1936
- });
1937
- return proxy;
1938
- }
1939
- );
1940
- utils.addProperty(
1941
- chai.Assertion.prototype,
1942
- "rejects",
1943
- function __VITEST_REJECTS__() {
1944
- const error = new Error("rejects");
1945
- utils.flag(this, "promise", "rejects");
1946
- utils.flag(this, "error", error);
1947
- const test = utils.flag(this, "vitest-test");
1948
- const obj = utils.flag(this, "object");
1949
- const wrapper = typeof obj === "function" ? obj() : obj;
1950
- if (utils.flag(this, "poll")) {
1951
- throw new SyntaxError(
1952
- `expect.poll() is not supported in combination with .rejects`
1953
- );
1954
- }
1955
- if (typeof (wrapper == null ? void 0 : wrapper.then) !== "function") {
1956
- throw new TypeError(
1957
- `You must provide a Promise to expect() when using .rejects, not '${typeof wrapper}'.`
1958
- );
1959
- }
1960
- const proxy = new Proxy(this, {
1961
- get: (target, key, receiver) => {
1962
- const result = Reflect.get(target, key, receiver);
1963
- if (typeof result !== "function") {
1964
- return result instanceof chai.Assertion ? proxy : result;
1965
- }
1966
- return (...args) => {
1967
- utils.flag(this, "_name", key);
1968
- const promise = wrapper.then(
1969
- (value) => {
1970
- const _error = new AssertionError(
1971
- `promise resolved "${utils.inspect(
1972
- value
1973
- )}" instead of rejecting`,
1974
- {
1975
- showDiff: true,
1976
- expected: new Error("rejected promise"),
1977
- actual: value
1978
- }
1979
- );
1980
- _error.stack = error.stack.replace(
1981
- error.message,
1982
- _error.message
1983
- );
1984
- throw _error;
1985
- },
1986
- (err) => {
1987
- utils.flag(this, "object", err);
1988
- return result.call(this, ...args);
1989
- }
1990
- );
1991
- return recordAsyncExpect(
1992
- test,
1993
- promise,
1994
- createAssertionMessage(utils, this, !!args.length),
1995
- error
1996
- );
1997
- };
1998
- }
1999
- });
2000
- return proxy;
2001
- }
2002
- );
956
+ const { AssertionError } = chai;
957
+ const customTesters = getCustomEqualityTesters();
958
+ function def(name, fn) {
959
+ const addMethod = (n) => {
960
+ const softWrapper = wrapAssertion(utils, n, fn);
961
+ utils.addMethod(chai.Assertion.prototype, n, softWrapper);
962
+ utils.addMethod(globalThis[JEST_MATCHERS_OBJECT].matchers, n, softWrapper);
963
+ };
964
+ if (Array.isArray(name)) {
965
+ name.forEach((n) => addMethod(n));
966
+ } else {
967
+ addMethod(name);
968
+ }
969
+ }
970
+ [
971
+ "throw",
972
+ "throws",
973
+ "Throw"
974
+ ].forEach((m) => {
975
+ utils.overwriteMethod(chai.Assertion.prototype, m, (_super) => {
976
+ return function(...args) {
977
+ const promise = utils.flag(this, "promise");
978
+ const object = utils.flag(this, "object");
979
+ const isNot = utils.flag(this, "negate");
980
+ if (promise === "rejects") {
981
+ utils.flag(this, "object", () => {
982
+ throw object;
983
+ });
984
+ } else if (promise === "resolves" && typeof object !== "function") {
985
+ if (!isNot) {
986
+ const message = utils.flag(this, "message") || "expected promise to throw an error, but it didn't";
987
+ const error = { showDiff: false };
988
+ throw new AssertionError(message, error, utils.flag(this, "ssfi"));
989
+ } else {
990
+ return;
991
+ }
992
+ }
993
+ _super.apply(this, args);
994
+ };
995
+ });
996
+ });
997
+ def("withTest", function(test) {
998
+ utils.flag(this, "vitest-test", test);
999
+ return this;
1000
+ });
1001
+ def("toEqual", function(expected) {
1002
+ const actual = utils.flag(this, "object");
1003
+ const equal = equals(actual, expected, [...customTesters, iterableEquality]);
1004
+ return this.assert(equal, "expected #{this} to deeply equal #{exp}", "expected #{this} to not deeply equal #{exp}", expected, actual);
1005
+ });
1006
+ def("toStrictEqual", function(expected) {
1007
+ const obj = utils.flag(this, "object");
1008
+ const equal = equals(obj, expected, [
1009
+ ...customTesters,
1010
+ iterableEquality,
1011
+ typeEquality,
1012
+ sparseArrayEquality,
1013
+ arrayBufferEquality
1014
+ ], true);
1015
+ return this.assert(equal, "expected #{this} to strictly equal #{exp}", "expected #{this} to not strictly equal #{exp}", expected, obj);
1016
+ });
1017
+ def("toBe", function(expected) {
1018
+ const actual = this._obj;
1019
+ const pass = Object.is(actual, expected);
1020
+ let deepEqualityName = "";
1021
+ if (!pass) {
1022
+ const toStrictEqualPass = equals(actual, expected, [
1023
+ ...customTesters,
1024
+ iterableEquality,
1025
+ typeEquality,
1026
+ sparseArrayEquality,
1027
+ arrayBufferEquality
1028
+ ], true);
1029
+ if (toStrictEqualPass) {
1030
+ deepEqualityName = "toStrictEqual";
1031
+ } else {
1032
+ const toEqualPass = equals(actual, expected, [...customTesters, iterableEquality]);
1033
+ if (toEqualPass) {
1034
+ deepEqualityName = "toEqual";
1035
+ }
1036
+ }
1037
+ }
1038
+ return this.assert(pass, generateToBeMessage(deepEqualityName), "expected #{this} not to be #{exp} // Object.is equality", expected, actual);
1039
+ });
1040
+ def("toMatchObject", function(expected) {
1041
+ const actual = this._obj;
1042
+ const pass = equals(actual, expected, [
1043
+ ...customTesters,
1044
+ iterableEquality,
1045
+ subsetEquality
1046
+ ]);
1047
+ const isNot = utils.flag(this, "negate");
1048
+ const { subset: actualSubset, stripped } = getObjectSubset(actual, expected, customTesters);
1049
+ if (pass && isNot || !pass && !isNot) {
1050
+ const msg = utils.getMessage(this, [
1051
+ pass,
1052
+ "expected #{this} to match object #{exp}",
1053
+ "expected #{this} to not match object #{exp}",
1054
+ expected,
1055
+ actualSubset,
1056
+ false
1057
+ ]);
1058
+ const message = stripped === 0 ? msg : `${msg}\n(${stripped} matching ${stripped === 1 ? "property" : "properties"} omitted from actual)`;
1059
+ throw new AssertionError(message, {
1060
+ showDiff: true,
1061
+ expected,
1062
+ actual: actualSubset
1063
+ });
1064
+ }
1065
+ });
1066
+ def("toMatch", function(expected) {
1067
+ const actual = this._obj;
1068
+ if (typeof actual !== "string") {
1069
+ throw new TypeError(`.toMatch() expects to receive a string, but got ${typeof actual}`);
1070
+ }
1071
+ return this.assert(typeof expected === "string" ? actual.includes(expected) : actual.match(expected), `expected #{this} to match #{exp}`, `expected #{this} not to match #{exp}`, expected, actual);
1072
+ });
1073
+ def("toContain", function(item) {
1074
+ const actual = this._obj;
1075
+ if (typeof Node !== "undefined" && actual instanceof Node) {
1076
+ if (!(item instanceof Node)) {
1077
+ throw new TypeError(`toContain() expected a DOM node as the argument, but got ${typeof item}`);
1078
+ }
1079
+ return this.assert(actual.contains(item), "expected #{this} to contain element #{exp}", "expected #{this} not to contain element #{exp}", item, actual);
1080
+ }
1081
+ if (typeof DOMTokenList !== "undefined" && actual instanceof DOMTokenList) {
1082
+ assertTypes(item, "class name", ["string"]);
1083
+ const isNot = utils.flag(this, "negate");
1084
+ const expectedClassList = isNot ? actual.value.replace(item, "").trim() : `${actual.value} ${item}`;
1085
+ return this.assert(actual.contains(item), `expected "${actual.value}" to contain "${item}"`, `expected "${actual.value}" not to contain "${item}"`, expectedClassList, actual.value);
1086
+ }
1087
+ if (typeof actual === "string" && typeof item === "string") {
1088
+ return this.assert(actual.includes(item), `expected #{this} to contain #{exp}`, `expected #{this} not to contain #{exp}`, item, actual);
1089
+ }
1090
+ if (actual != null && typeof actual !== "string") {
1091
+ utils.flag(this, "object", Array.from(actual));
1092
+ }
1093
+ return this.contain(item);
1094
+ });
1095
+ def("toContainEqual", function(expected) {
1096
+ const obj = utils.flag(this, "object");
1097
+ const index = Array.from(obj).findIndex((item) => {
1098
+ return equals(item, expected, customTesters);
1099
+ });
1100
+ this.assert(index !== -1, "expected #{this} to deep equally contain #{exp}", "expected #{this} to not deep equally contain #{exp}", expected);
1101
+ });
1102
+ def("toBeTruthy", function() {
1103
+ const obj = utils.flag(this, "object");
1104
+ this.assert(Boolean(obj), "expected #{this} to be truthy", "expected #{this} to not be truthy", true, obj);
1105
+ });
1106
+ def("toBeFalsy", function() {
1107
+ const obj = utils.flag(this, "object");
1108
+ this.assert(!obj, "expected #{this} to be falsy", "expected #{this} to not be falsy", false, obj);
1109
+ });
1110
+ def("toBeGreaterThan", function(expected) {
1111
+ const actual = this._obj;
1112
+ assertTypes(actual, "actual", ["number", "bigint"]);
1113
+ assertTypes(expected, "expected", ["number", "bigint"]);
1114
+ return this.assert(actual > expected, `expected ${actual} to be greater than ${expected}`, `expected ${actual} to be not greater than ${expected}`, expected, actual, false);
1115
+ });
1116
+ def("toBeGreaterThanOrEqual", function(expected) {
1117
+ const actual = this._obj;
1118
+ assertTypes(actual, "actual", ["number", "bigint"]);
1119
+ assertTypes(expected, "expected", ["number", "bigint"]);
1120
+ return this.assert(actual >= expected, `expected ${actual} to be greater than or equal to ${expected}`, `expected ${actual} to be not greater than or equal to ${expected}`, expected, actual, false);
1121
+ });
1122
+ def("toBeLessThan", function(expected) {
1123
+ const actual = this._obj;
1124
+ assertTypes(actual, "actual", ["number", "bigint"]);
1125
+ assertTypes(expected, "expected", ["number", "bigint"]);
1126
+ return this.assert(actual < expected, `expected ${actual} to be less than ${expected}`, `expected ${actual} to be not less than ${expected}`, expected, actual, false);
1127
+ });
1128
+ def("toBeLessThanOrEqual", function(expected) {
1129
+ const actual = this._obj;
1130
+ assertTypes(actual, "actual", ["number", "bigint"]);
1131
+ assertTypes(expected, "expected", ["number", "bigint"]);
1132
+ return this.assert(actual <= expected, `expected ${actual} to be less than or equal to ${expected}`, `expected ${actual} to be not less than or equal to ${expected}`, expected, actual, false);
1133
+ });
1134
+ def("toBeNaN", function() {
1135
+ const obj = utils.flag(this, "object");
1136
+ this.assert(Number.isNaN(obj), "expected #{this} to be NaN", "expected #{this} not to be NaN", Number.NaN, obj);
1137
+ });
1138
+ def("toBeUndefined", function() {
1139
+ const obj = utils.flag(this, "object");
1140
+ this.assert(undefined === obj, "expected #{this} to be undefined", "expected #{this} not to be undefined", undefined, obj);
1141
+ });
1142
+ def("toBeNull", function() {
1143
+ const obj = utils.flag(this, "object");
1144
+ this.assert(obj === null, "expected #{this} to be null", "expected #{this} not to be null", null, obj);
1145
+ });
1146
+ def("toBeDefined", function() {
1147
+ const obj = utils.flag(this, "object");
1148
+ this.assert(typeof obj !== "undefined", "expected #{this} to be defined", "expected #{this} to be undefined", obj);
1149
+ });
1150
+ def("toBeTypeOf", function(expected) {
1151
+ const actual = typeof this._obj;
1152
+ const equal = expected === actual;
1153
+ return this.assert(equal, "expected #{this} to be type of #{exp}", "expected #{this} not to be type of #{exp}", expected, actual);
1154
+ });
1155
+ def("toBeInstanceOf", function(obj) {
1156
+ return this.instanceOf(obj);
1157
+ });
1158
+ def("toHaveLength", function(length) {
1159
+ return this.have.length(length);
1160
+ });
1161
+ def("toHaveProperty", function(...args) {
1162
+ if (Array.isArray(args[0])) {
1163
+ args[0] = args[0].map((key) => String(key).replace(/([.[\]])/g, "\\$1")).join(".");
1164
+ }
1165
+ const actual = this._obj;
1166
+ const [propertyName, expected] = args;
1167
+ const getValue = () => {
1168
+ const hasOwn = Object.prototype.hasOwnProperty.call(actual, propertyName);
1169
+ if (hasOwn) {
1170
+ return {
1171
+ value: actual[propertyName],
1172
+ exists: true
1173
+ };
1174
+ }
1175
+ return utils.getPathInfo(actual, propertyName);
1176
+ };
1177
+ const { value, exists } = getValue();
1178
+ const pass = exists && (args.length === 1 || equals(expected, value, customTesters));
1179
+ const valueString = args.length === 1 ? "" : ` with value ${utils.objDisplay(expected)}`;
1180
+ return this.assert(pass, `expected #{this} to have property "${propertyName}"${valueString}`, `expected #{this} to not have property "${propertyName}"${valueString}`, expected, exists ? value : undefined);
1181
+ });
1182
+ def("toBeCloseTo", function(received, precision = 2) {
1183
+ const expected = this._obj;
1184
+ let pass = false;
1185
+ let expectedDiff = 0;
1186
+ let receivedDiff = 0;
1187
+ if (received === Number.POSITIVE_INFINITY && expected === Number.POSITIVE_INFINITY) {
1188
+ pass = true;
1189
+ } else if (received === Number.NEGATIVE_INFINITY && expected === Number.NEGATIVE_INFINITY) {
1190
+ pass = true;
1191
+ } else {
1192
+ expectedDiff = 10 ** -precision / 2;
1193
+ receivedDiff = Math.abs(expected - received);
1194
+ pass = receivedDiff < expectedDiff;
1195
+ }
1196
+ return this.assert(pass, `expected #{this} to be close to #{exp}, received difference is ${receivedDiff}, but expected ${expectedDiff}`, `expected #{this} to not be close to #{exp}, received difference is ${receivedDiff}, but expected ${expectedDiff}`, received, expected, false);
1197
+ });
1198
+ function assertIsMock(assertion) {
1199
+ if (!isMockFunction(assertion._obj)) {
1200
+ throw new TypeError(`${utils.inspect(assertion._obj)} is not a spy or a call to a spy!`);
1201
+ }
1202
+ }
1203
+ function getSpy(assertion) {
1204
+ assertIsMock(assertion);
1205
+ return assertion._obj;
1206
+ }
1207
+ def(["toHaveBeenCalledTimes", "toBeCalledTimes"], function(number) {
1208
+ const spy = getSpy(this);
1209
+ const spyName = spy.getMockName();
1210
+ const callCount = spy.mock.calls.length;
1211
+ return this.assert(callCount === number, `expected "${spyName}" to be called #{exp} times, but got ${callCount} times`, `expected "${spyName}" to not be called #{exp} times`, number, callCount, false);
1212
+ });
1213
+ def("toHaveBeenCalledOnce", function() {
1214
+ const spy = getSpy(this);
1215
+ const spyName = spy.getMockName();
1216
+ const callCount = spy.mock.calls.length;
1217
+ return this.assert(callCount === 1, `expected "${spyName}" to be called once, but got ${callCount} times`, `expected "${spyName}" to not be called once`, 1, callCount, false);
1218
+ });
1219
+ def(["toHaveBeenCalled", "toBeCalled"], function() {
1220
+ const spy = getSpy(this);
1221
+ const spyName = spy.getMockName();
1222
+ const callCount = spy.mock.calls.length;
1223
+ const called = callCount > 0;
1224
+ const isNot = utils.flag(this, "negate");
1225
+ let msg = utils.getMessage(this, [
1226
+ called,
1227
+ `expected "${spyName}" to be called at least once`,
1228
+ `expected "${spyName}" to not be called at all, but actually been called ${callCount} times`,
1229
+ true,
1230
+ called
1231
+ ]);
1232
+ if (called && isNot) {
1233
+ msg = formatCalls(spy, msg);
1234
+ }
1235
+ if (called && isNot || !called && !isNot) {
1236
+ throw new AssertionError(msg);
1237
+ }
1238
+ });
1239
+ function equalsArgumentArray(a, b) {
1240
+ return a.length === b.length && a.every((aItem, i) => equals(aItem, b[i], [...customTesters, iterableEquality]));
1241
+ }
1242
+ def(["toHaveBeenCalledWith", "toBeCalledWith"], function(...args) {
1243
+ const spy = getSpy(this);
1244
+ const spyName = spy.getMockName();
1245
+ const pass = spy.mock.calls.some((callArg) => equalsArgumentArray(callArg, args));
1246
+ const isNot = utils.flag(this, "negate");
1247
+ const msg = utils.getMessage(this, [
1248
+ pass,
1249
+ `expected "${spyName}" to be called with arguments: #{exp}`,
1250
+ `expected "${spyName}" to not be called with arguments: #{exp}`,
1251
+ args
1252
+ ]);
1253
+ if (pass && isNot || !pass && !isNot) {
1254
+ throw new AssertionError(formatCalls(spy, msg, args));
1255
+ }
1256
+ });
1257
+ def("toHaveBeenCalledExactlyOnceWith", function(...args) {
1258
+ const spy = getSpy(this);
1259
+ const spyName = spy.getMockName();
1260
+ const callCount = spy.mock.calls.length;
1261
+ const hasCallWithArgs = spy.mock.calls.some((callArg) => equalsArgumentArray(callArg, args));
1262
+ const pass = hasCallWithArgs && callCount === 1;
1263
+ const isNot = utils.flag(this, "negate");
1264
+ const msg = utils.getMessage(this, [
1265
+ pass,
1266
+ `expected "${spyName}" to be called once with arguments: #{exp}`,
1267
+ `expected "${spyName}" to not be called once with arguments: #{exp}`,
1268
+ args
1269
+ ]);
1270
+ if (pass && isNot || !pass && !isNot) {
1271
+ throw new AssertionError(formatCalls(spy, msg, args));
1272
+ }
1273
+ });
1274
+ def(["toHaveBeenNthCalledWith", "nthCalledWith"], function(times, ...args) {
1275
+ const spy = getSpy(this);
1276
+ const spyName = spy.getMockName();
1277
+ const nthCall = spy.mock.calls[times - 1];
1278
+ const callCount = spy.mock.calls.length;
1279
+ const isCalled = times <= callCount;
1280
+ this.assert(nthCall && equalsArgumentArray(nthCall, args), `expected ${ordinalOf(times)} "${spyName}" call to have been called with #{exp}${isCalled ? `` : `, but called only ${callCount} times`}`, `expected ${ordinalOf(times)} "${spyName}" call to not have been called with #{exp}`, args, nthCall, isCalled);
1281
+ });
1282
+ def(["toHaveBeenLastCalledWith", "lastCalledWith"], function(...args) {
1283
+ const spy = getSpy(this);
1284
+ const spyName = spy.getMockName();
1285
+ const lastCall = spy.mock.calls[spy.mock.calls.length - 1];
1286
+ this.assert(lastCall && equalsArgumentArray(lastCall, args), `expected last "${spyName}" call to have been called with #{exp}`, `expected last "${spyName}" call to not have been called with #{exp}`, args, lastCall);
1287
+ });
1288
+ /**
1289
+ * Used for `toHaveBeenCalledBefore` and `toHaveBeenCalledAfter` to determine if the expected spy was called before the result spy.
1290
+ */
1291
+ function isSpyCalledBeforeAnotherSpy(beforeSpy, afterSpy, failIfNoFirstInvocation) {
1292
+ const beforeInvocationCallOrder = beforeSpy.mock.invocationCallOrder;
1293
+ const afterInvocationCallOrder = afterSpy.mock.invocationCallOrder;
1294
+ if (beforeInvocationCallOrder.length === 0) {
1295
+ return !failIfNoFirstInvocation;
1296
+ }
1297
+ if (afterInvocationCallOrder.length === 0) {
1298
+ return false;
1299
+ }
1300
+ return beforeInvocationCallOrder[0] < afterInvocationCallOrder[0];
1301
+ }
1302
+ def(["toHaveBeenCalledBefore"], function(resultSpy, failIfNoFirstInvocation = true) {
1303
+ const expectSpy = getSpy(this);
1304
+ if (!isMockFunction(resultSpy)) {
1305
+ throw new TypeError(`${utils.inspect(resultSpy)} is not a spy or a call to a spy`);
1306
+ }
1307
+ this.assert(isSpyCalledBeforeAnotherSpy(expectSpy, resultSpy, failIfNoFirstInvocation), `expected "${expectSpy.getMockName()}" to have been called before "${resultSpy.getMockName()}"`, `expected "${expectSpy.getMockName()}" to not have been called before "${resultSpy.getMockName()}"`, resultSpy, expectSpy);
1308
+ });
1309
+ def(["toHaveBeenCalledAfter"], function(resultSpy, failIfNoFirstInvocation = true) {
1310
+ const expectSpy = getSpy(this);
1311
+ if (!isMockFunction(resultSpy)) {
1312
+ throw new TypeError(`${utils.inspect(resultSpy)} is not a spy or a call to a spy`);
1313
+ }
1314
+ this.assert(isSpyCalledBeforeAnotherSpy(resultSpy, expectSpy, failIfNoFirstInvocation), `expected "${expectSpy.getMockName()}" to have been called after "${resultSpy.getMockName()}"`, `expected "${expectSpy.getMockName()}" to not have been called after "${resultSpy.getMockName()}"`, resultSpy, expectSpy);
1315
+ });
1316
+ def(["toThrow", "toThrowError"], function(expected) {
1317
+ if (typeof expected === "string" || typeof expected === "undefined" || expected instanceof RegExp) {
1318
+ return this.throws(expected === "" ? /^$/ : expected);
1319
+ }
1320
+ const obj = this._obj;
1321
+ const promise = utils.flag(this, "promise");
1322
+ const isNot = utils.flag(this, "negate");
1323
+ let thrown = null;
1324
+ if (promise === "rejects") {
1325
+ thrown = obj;
1326
+ } else if (promise === "resolves" && typeof obj !== "function") {
1327
+ if (!isNot) {
1328
+ const message = utils.flag(this, "message") || "expected promise to throw an error, but it didn't";
1329
+ const error = { showDiff: false };
1330
+ throw new AssertionError(message, error, utils.flag(this, "ssfi"));
1331
+ } else {
1332
+ return;
1333
+ }
1334
+ } else {
1335
+ let isThrow = false;
1336
+ try {
1337
+ obj();
1338
+ } catch (err) {
1339
+ isThrow = true;
1340
+ thrown = err;
1341
+ }
1342
+ if (!isThrow && !isNot) {
1343
+ const message = utils.flag(this, "message") || "expected function to throw an error, but it didn't";
1344
+ const error = { showDiff: false };
1345
+ throw new AssertionError(message, error, utils.flag(this, "ssfi"));
1346
+ }
1347
+ }
1348
+ if (typeof expected === "function") {
1349
+ const name = expected.name || expected.prototype.constructor.name;
1350
+ return this.assert(thrown && thrown instanceof expected, `expected error to be instance of ${name}`, `expected error not to be instance of ${name}`, expected, thrown);
1351
+ }
1352
+ if (expected instanceof Error) {
1353
+ const equal = equals(thrown, expected, [...customTesters, iterableEquality]);
1354
+ return this.assert(equal, "expected a thrown error to be #{exp}", "expected a thrown error not to be #{exp}", expected, thrown);
1355
+ }
1356
+ if (typeof expected === "object" && "asymmetricMatch" in expected && typeof expected.asymmetricMatch === "function") {
1357
+ const matcher = expected;
1358
+ return this.assert(thrown && matcher.asymmetricMatch(thrown), "expected error to match asymmetric matcher", "expected error not to match asymmetric matcher", matcher, thrown);
1359
+ }
1360
+ throw new Error(`"toThrow" expects string, RegExp, function, Error instance or asymmetric matcher, got "${typeof expected}"`);
1361
+ });
1362
+ [{
1363
+ name: "toHaveResolved",
1364
+ condition: (spy) => spy.mock.settledResults.length > 0 && spy.mock.settledResults.some(({ type }) => type === "fulfilled"),
1365
+ action: "resolved"
1366
+ }, {
1367
+ name: ["toHaveReturned", "toReturn"],
1368
+ condition: (spy) => spy.mock.calls.length > 0 && spy.mock.results.some(({ type }) => type !== "throw"),
1369
+ action: "called"
1370
+ }].forEach(({ name, condition, action }) => {
1371
+ def(name, function() {
1372
+ const spy = getSpy(this);
1373
+ const spyName = spy.getMockName();
1374
+ const pass = condition(spy);
1375
+ this.assert(pass, `expected "${spyName}" to be successfully ${action} at least once`, `expected "${spyName}" to not be successfully ${action}`, pass, !pass, false);
1376
+ });
1377
+ });
1378
+ [{
1379
+ name: "toHaveResolvedTimes",
1380
+ condition: (spy, times) => spy.mock.settledResults.reduce((s, { type }) => type === "fulfilled" ? ++s : s, 0) === times,
1381
+ action: "resolved"
1382
+ }, {
1383
+ name: ["toHaveReturnedTimes", "toReturnTimes"],
1384
+ condition: (spy, times) => spy.mock.results.reduce((s, { type }) => type === "throw" ? s : ++s, 0) === times,
1385
+ action: "called"
1386
+ }].forEach(({ name, condition, action }) => {
1387
+ def(name, function(times) {
1388
+ const spy = getSpy(this);
1389
+ const spyName = spy.getMockName();
1390
+ const pass = condition(spy, times);
1391
+ this.assert(pass, `expected "${spyName}" to be successfully ${action} ${times} times`, `expected "${spyName}" to not be successfully ${action} ${times} times`, `expected resolved times: ${times}`, `received resolved times: ${pass}`, false);
1392
+ });
1393
+ });
1394
+ [{
1395
+ name: "toHaveResolvedWith",
1396
+ condition: (spy, value) => spy.mock.settledResults.some(({ type, value: result }) => type === "fulfilled" && equals(value, result)),
1397
+ action: "resolve"
1398
+ }, {
1399
+ name: ["toHaveReturnedWith", "toReturnWith"],
1400
+ condition: (spy, value) => spy.mock.results.some(({ type, value: result }) => type === "return" && equals(value, result)),
1401
+ action: "return"
1402
+ }].forEach(({ name, condition, action }) => {
1403
+ def(name, function(value) {
1404
+ const spy = getSpy(this);
1405
+ const pass = condition(spy, value);
1406
+ const isNot = utils.flag(this, "negate");
1407
+ if (pass && isNot || !pass && !isNot) {
1408
+ const spyName = spy.getMockName();
1409
+ const msg = utils.getMessage(this, [
1410
+ pass,
1411
+ `expected "${spyName}" to ${action} with: #{exp} at least once`,
1412
+ `expected "${spyName}" to not ${action} with: #{exp}`,
1413
+ value
1414
+ ]);
1415
+ const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1416
+ throw new AssertionError(formatReturns(spy, results, msg, value));
1417
+ }
1418
+ });
1419
+ });
1420
+ [{
1421
+ name: "toHaveLastResolvedWith",
1422
+ condition: (spy, value) => {
1423
+ const result = spy.mock.settledResults[spy.mock.settledResults.length - 1];
1424
+ return result && result.type === "fulfilled" && equals(result.value, value);
1425
+ },
1426
+ action: "resolve"
1427
+ }, {
1428
+ name: ["toHaveLastReturnedWith", "lastReturnedWith"],
1429
+ condition: (spy, value) => {
1430
+ const result = spy.mock.results[spy.mock.results.length - 1];
1431
+ return result && result.type === "return" && equals(result.value, value);
1432
+ },
1433
+ action: "return"
1434
+ }].forEach(({ name, condition, action }) => {
1435
+ def(name, function(value) {
1436
+ const spy = getSpy(this);
1437
+ const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1438
+ const result = results[results.length - 1];
1439
+ const spyName = spy.getMockName();
1440
+ this.assert(
1441
+ condition(spy, value),
1442
+ `expected last "${spyName}" call to ${action} #{exp}`,
1443
+ `expected last "${spyName}" call to not ${action} #{exp}`,
1444
+ value,
1445
+ // for jest compat
1446
+ result === null || result === void 0 ? void 0 : result.value
1447
+ );
1448
+ });
1449
+ });
1450
+ [{
1451
+ name: "toHaveNthResolvedWith",
1452
+ condition: (spy, index, value) => {
1453
+ const result = spy.mock.settledResults[index - 1];
1454
+ return result && result.type === "fulfilled" && equals(result.value, value);
1455
+ },
1456
+ action: "resolve"
1457
+ }, {
1458
+ name: ["toHaveNthReturnedWith", "nthReturnedWith"],
1459
+ condition: (spy, index, value) => {
1460
+ const result = spy.mock.results[index - 1];
1461
+ return result && result.type === "return" && equals(result.value, value);
1462
+ },
1463
+ action: "return"
1464
+ }].forEach(({ name, condition, action }) => {
1465
+ def(name, function(nthCall, value) {
1466
+ const spy = getSpy(this);
1467
+ const spyName = spy.getMockName();
1468
+ const results = action === "return" ? spy.mock.results : spy.mock.settledResults;
1469
+ const result = results[nthCall - 1];
1470
+ const ordinalCall = `${ordinalOf(nthCall)} call`;
1471
+ this.assert(condition(spy, nthCall, value), `expected ${ordinalCall} "${spyName}" call to ${action} #{exp}`, `expected ${ordinalCall} "${spyName}" call to not ${action} #{exp}`, value, result === null || result === void 0 ? void 0 : result.value);
1472
+ });
1473
+ });
1474
+ def("withContext", function(context) {
1475
+ for (const key in context) {
1476
+ utils.flag(this, key, context[key]);
1477
+ }
1478
+ return this;
1479
+ });
1480
+ utils.addProperty(chai.Assertion.prototype, "resolves", function __VITEST_RESOLVES__() {
1481
+ const error = new Error("resolves");
1482
+ utils.flag(this, "promise", "resolves");
1483
+ utils.flag(this, "error", error);
1484
+ const test = utils.flag(this, "vitest-test");
1485
+ const obj = utils.flag(this, "object");
1486
+ if (utils.flag(this, "poll")) {
1487
+ throw new SyntaxError(`expect.poll() is not supported in combination with .resolves`);
1488
+ }
1489
+ if (typeof (obj === null || obj === void 0 ? void 0 : obj.then) !== "function") {
1490
+ throw new TypeError(`You must provide a Promise to expect() when using .resolves, not '${typeof obj}'.`);
1491
+ }
1492
+ const proxy = new Proxy(this, { get: (target, key, receiver) => {
1493
+ const result = Reflect.get(target, key, receiver);
1494
+ if (typeof result !== "function") {
1495
+ return result instanceof chai.Assertion ? proxy : result;
1496
+ }
1497
+ return (...args) => {
1498
+ utils.flag(this, "_name", key);
1499
+ const promise = obj.then((value) => {
1500
+ utils.flag(this, "object", value);
1501
+ return result.call(this, ...args);
1502
+ }, (err) => {
1503
+ const _error = new AssertionError(`promise rejected "${utils.inspect(err)}" instead of resolving`, { showDiff: false });
1504
+ _error.cause = err;
1505
+ _error.stack = error.stack.replace(error.message, _error.message);
1506
+ throw _error;
1507
+ });
1508
+ return recordAsyncExpect(test, promise, createAssertionMessage(utils, this, !!args.length), error);
1509
+ };
1510
+ } });
1511
+ return proxy;
1512
+ });
1513
+ utils.addProperty(chai.Assertion.prototype, "rejects", function __VITEST_REJECTS__() {
1514
+ const error = new Error("rejects");
1515
+ utils.flag(this, "promise", "rejects");
1516
+ utils.flag(this, "error", error);
1517
+ const test = utils.flag(this, "vitest-test");
1518
+ const obj = utils.flag(this, "object");
1519
+ const wrapper = typeof obj === "function" ? obj() : obj;
1520
+ if (utils.flag(this, "poll")) {
1521
+ throw new SyntaxError(`expect.poll() is not supported in combination with .rejects`);
1522
+ }
1523
+ if (typeof (wrapper === null || wrapper === void 0 ? void 0 : wrapper.then) !== "function") {
1524
+ throw new TypeError(`You must provide a Promise to expect() when using .rejects, not '${typeof wrapper}'.`);
1525
+ }
1526
+ const proxy = new Proxy(this, { get: (target, key, receiver) => {
1527
+ const result = Reflect.get(target, key, receiver);
1528
+ if (typeof result !== "function") {
1529
+ return result instanceof chai.Assertion ? proxy : result;
1530
+ }
1531
+ return (...args) => {
1532
+ utils.flag(this, "_name", key);
1533
+ const promise = wrapper.then((value) => {
1534
+ const _error = new AssertionError(`promise resolved "${utils.inspect(value)}" instead of rejecting`, {
1535
+ showDiff: true,
1536
+ expected: new Error("rejected promise"),
1537
+ actual: value
1538
+ });
1539
+ _error.stack = error.stack.replace(error.message, _error.message);
1540
+ throw _error;
1541
+ }, (err) => {
1542
+ utils.flag(this, "object", err);
1543
+ return result.call(this, ...args);
1544
+ });
1545
+ return recordAsyncExpect(test, promise, createAssertionMessage(utils, this, !!args.length), error);
1546
+ };
1547
+ } });
1548
+ return proxy;
1549
+ });
2003
1550
  };
2004
1551
  function ordinalOf(i) {
2005
- const j = i % 10;
2006
- const k = i % 100;
2007
- if (j === 1 && k !== 11) {
2008
- return `${i}st`;
2009
- }
2010
- if (j === 2 && k !== 12) {
2011
- return `${i}nd`;
2012
- }
2013
- if (j === 3 && k !== 13) {
2014
- return `${i}rd`;
2015
- }
2016
- return `${i}th`;
1552
+ const j = i % 10;
1553
+ const k = i % 100;
1554
+ if (j === 1 && k !== 11) {
1555
+ return `${i}st`;
1556
+ }
1557
+ if (j === 2 && k !== 12) {
1558
+ return `${i}nd`;
1559
+ }
1560
+ if (j === 3 && k !== 13) {
1561
+ return `${i}rd`;
1562
+ }
1563
+ return `${i}th`;
2017
1564
  }
2018
1565
  function formatCalls(spy, msg, showActualCall) {
2019
- if (spy.mock.calls) {
2020
- msg += c.gray(
2021
- `
2022
-
2023
- Received:
2024
-
2025
- ${spy.mock.calls.map((callArg, i) => {
2026
- let methodCall = c.bold(
2027
- ` ${ordinalOf(i + 1)} ${spy.getMockName()} call:
2028
-
2029
- `
2030
- );
2031
- if (showActualCall) {
2032
- methodCall += diff(showActualCall, callArg, {
2033
- omitAnnotationLines: true
2034
- });
2035
- } else {
2036
- methodCall += stringify(callArg).split("\n").map((line) => ` ${line}`).join("\n");
2037
- }
2038
- methodCall += "\n";
2039
- return methodCall;
2040
- }).join("\n")}`
2041
- );
2042
- }
2043
- msg += c.gray(
2044
- `
2045
-
2046
- Number of calls: ${c.bold(spy.mock.calls.length)}
2047
- `
2048
- );
2049
- return msg;
1566
+ if (spy.mock.calls) {
1567
+ msg += c.gray(`\n\nReceived: \n\n${spy.mock.calls.map((callArg, i) => {
1568
+ let methodCall = c.bold(` ${ordinalOf(i + 1)} ${spy.getMockName()} call:\n\n`);
1569
+ if (showActualCall) {
1570
+ methodCall += diff(showActualCall, callArg, { omitAnnotationLines: true });
1571
+ } else {
1572
+ methodCall += stringify(callArg).split("\n").map((line) => ` ${line}`).join("\n");
1573
+ }
1574
+ methodCall += "\n";
1575
+ return methodCall;
1576
+ }).join("\n")}`);
1577
+ }
1578
+ msg += c.gray(`\n\nNumber of calls: ${c.bold(spy.mock.calls.length)}\n`);
1579
+ return msg;
2050
1580
  }
2051
1581
  function formatReturns(spy, results, msg, showActualReturn) {
2052
- msg += c.gray(
2053
- `
2054
-
2055
- Received:
2056
-
2057
- ${results.map((callReturn, i) => {
2058
- let methodCall = c.bold(
2059
- ` ${ordinalOf(i + 1)} ${spy.getMockName()} call return:
2060
-
2061
- `
2062
- );
2063
- if (showActualReturn) {
2064
- methodCall += diff(showActualReturn, callReturn.value, {
2065
- omitAnnotationLines: true
2066
- });
2067
- } else {
2068
- methodCall += stringify(callReturn).split("\n").map((line) => ` ${line}`).join("\n");
2069
- }
2070
- methodCall += "\n";
2071
- return methodCall;
2072
- }).join("\n")}`
2073
- );
2074
- msg += c.gray(
2075
- `
2076
-
2077
- Number of calls: ${c.bold(spy.mock.calls.length)}
2078
- `
2079
- );
2080
- return msg;
1582
+ msg += c.gray(`\n\nReceived: \n\n${results.map((callReturn, i) => {
1583
+ let methodCall = c.bold(` ${ordinalOf(i + 1)} ${spy.getMockName()} call return:\n\n`);
1584
+ if (showActualReturn) {
1585
+ methodCall += diff(showActualReturn, callReturn.value, { omitAnnotationLines: true });
1586
+ } else {
1587
+ methodCall += stringify(callReturn).split("\n").map((line) => ` ${line}`).join("\n");
1588
+ }
1589
+ methodCall += "\n";
1590
+ return methodCall;
1591
+ }).join("\n")}`);
1592
+ msg += c.gray(`\n\nNumber of calls: ${c.bold(spy.mock.calls.length)}\n`);
1593
+ return msg;
2081
1594
  }
2082
1595
 
2083
1596
  function getMatcherState(assertion, expect) {
2084
- const obj = assertion._obj;
2085
- const isNot = util.flag(assertion, "negate");
2086
- const promise = util.flag(assertion, "promise") || "";
2087
- const jestUtils = {
2088
- ...getMatcherUtils(),
2089
- diff,
2090
- stringify,
2091
- iterableEquality,
2092
- subsetEquality
2093
- };
2094
- const matcherState = {
2095
- ...getState(expect),
2096
- customTesters: getCustomEqualityTesters(),
2097
- isNot,
2098
- utils: jestUtils,
2099
- promise,
2100
- equals,
2101
- // needed for built-in jest-snapshots, but we don't use it
2102
- suppressedErrors: [],
2103
- soft: util.flag(assertion, "soft"),
2104
- poll: util.flag(assertion, "poll")
2105
- };
2106
- return {
2107
- state: matcherState,
2108
- isNot,
2109
- obj
2110
- };
1597
+ const obj = assertion._obj;
1598
+ const isNot = util.flag(assertion, "negate");
1599
+ const promise = util.flag(assertion, "promise") || "";
1600
+ const jestUtils = {
1601
+ ...getMatcherUtils(),
1602
+ diff,
1603
+ stringify,
1604
+ iterableEquality,
1605
+ subsetEquality
1606
+ };
1607
+ const matcherState = {
1608
+ ...getState(expect),
1609
+ customTesters: getCustomEqualityTesters(),
1610
+ isNot,
1611
+ utils: jestUtils,
1612
+ promise,
1613
+ equals,
1614
+ suppressedErrors: [],
1615
+ soft: util.flag(assertion, "soft"),
1616
+ poll: util.flag(assertion, "poll")
1617
+ };
1618
+ return {
1619
+ state: matcherState,
1620
+ isNot,
1621
+ obj
1622
+ };
2111
1623
  }
2112
1624
  class JestExtendError extends Error {
2113
- constructor(message, actual, expected) {
2114
- super(message);
2115
- this.actual = actual;
2116
- this.expected = expected;
2117
- }
1625
+ constructor(message, actual, expected) {
1626
+ super(message);
1627
+ this.actual = actual;
1628
+ this.expected = expected;
1629
+ }
2118
1630
  }
2119
1631
  function JestExtendPlugin(c, expect, matchers) {
2120
- return (_, utils) => {
2121
- Object.entries(matchers).forEach(
2122
- ([expectAssertionName, expectAssertion]) => {
2123
- function expectWrapper(...args) {
2124
- const { state, isNot, obj } = getMatcherState(this, expect);
2125
- const result = expectAssertion.call(state, obj, ...args);
2126
- if (result && typeof result === "object" && result instanceof Promise) {
2127
- return result.then(({ pass: pass2, message: message2, actual: actual2, expected: expected2 }) => {
2128
- if (pass2 && isNot || !pass2 && !isNot) {
2129
- throw new JestExtendError(message2(), actual2, expected2);
2130
- }
2131
- });
2132
- }
2133
- const { pass, message, actual, expected } = result;
2134
- if (pass && isNot || !pass && !isNot) {
2135
- throw new JestExtendError(message(), actual, expected);
2136
- }
2137
- }
2138
- const softWrapper = wrapAssertion(utils, expectAssertionName, expectWrapper);
2139
- utils.addMethod(
2140
- globalThis[JEST_MATCHERS_OBJECT].matchers,
2141
- expectAssertionName,
2142
- softWrapper
2143
- );
2144
- utils.addMethod(
2145
- c.Assertion.prototype,
2146
- expectAssertionName,
2147
- softWrapper
2148
- );
2149
- class CustomMatcher extends AsymmetricMatcher {
2150
- constructor(inverse = false, ...sample) {
2151
- super(sample, inverse);
2152
- }
2153
- asymmetricMatch(other) {
2154
- const { pass } = expectAssertion.call(
2155
- this.getMatcherContext(expect),
2156
- other,
2157
- ...this.sample
2158
- );
2159
- return this.inverse ? !pass : pass;
2160
- }
2161
- toString() {
2162
- return `${this.inverse ? "not." : ""}${expectAssertionName}`;
2163
- }
2164
- getExpectedType() {
2165
- return "any";
2166
- }
2167
- toAsymmetricMatcher() {
2168
- return `${this.toString()}<${this.sample.map((item) => stringify(item)).join(", ")}>`;
2169
- }
2170
- }
2171
- const customMatcher = (...sample) => new CustomMatcher(false, ...sample);
2172
- Object.defineProperty(expect, expectAssertionName, {
2173
- configurable: true,
2174
- enumerable: true,
2175
- value: customMatcher,
2176
- writable: true
2177
- });
2178
- Object.defineProperty(expect.not, expectAssertionName, {
2179
- configurable: true,
2180
- enumerable: true,
2181
- value: (...sample) => new CustomMatcher(true, ...sample),
2182
- writable: true
2183
- });
2184
- Object.defineProperty(
2185
- globalThis[ASYMMETRIC_MATCHERS_OBJECT],
2186
- expectAssertionName,
2187
- {
2188
- configurable: true,
2189
- enumerable: true,
2190
- value: customMatcher,
2191
- writable: true
2192
- }
2193
- );
2194
- }
2195
- );
2196
- };
1632
+ return (_, utils) => {
1633
+ Object.entries(matchers).forEach(([expectAssertionName, expectAssertion]) => {
1634
+ function expectWrapper(...args) {
1635
+ const { state, isNot, obj } = getMatcherState(this, expect);
1636
+ const result = expectAssertion.call(state, obj, ...args);
1637
+ if (result && typeof result === "object" && result instanceof Promise) {
1638
+ return result.then(({ pass, message, actual, expected }) => {
1639
+ if (pass && isNot || !pass && !isNot) {
1640
+ throw new JestExtendError(message(), actual, expected);
1641
+ }
1642
+ });
1643
+ }
1644
+ const { pass, message, actual, expected } = result;
1645
+ if (pass && isNot || !pass && !isNot) {
1646
+ throw new JestExtendError(message(), actual, expected);
1647
+ }
1648
+ }
1649
+ const softWrapper = wrapAssertion(utils, expectAssertionName, expectWrapper);
1650
+ utils.addMethod(globalThis[JEST_MATCHERS_OBJECT].matchers, expectAssertionName, softWrapper);
1651
+ utils.addMethod(c.Assertion.prototype, expectAssertionName, softWrapper);
1652
+ class CustomMatcher extends AsymmetricMatcher {
1653
+ constructor(inverse = false, ...sample) {
1654
+ super(sample, inverse);
1655
+ }
1656
+ asymmetricMatch(other) {
1657
+ const { pass } = expectAssertion.call(this.getMatcherContext(expect), other, ...this.sample);
1658
+ return this.inverse ? !pass : pass;
1659
+ }
1660
+ toString() {
1661
+ return `${this.inverse ? "not." : ""}${expectAssertionName}`;
1662
+ }
1663
+ getExpectedType() {
1664
+ return "any";
1665
+ }
1666
+ toAsymmetricMatcher() {
1667
+ return `${this.toString()}<${this.sample.map((item) => stringify(item)).join(", ")}>`;
1668
+ }
1669
+ }
1670
+ const customMatcher = (...sample) => new CustomMatcher(false, ...sample);
1671
+ Object.defineProperty(expect, expectAssertionName, {
1672
+ configurable: true,
1673
+ enumerable: true,
1674
+ value: customMatcher,
1675
+ writable: true
1676
+ });
1677
+ Object.defineProperty(expect.not, expectAssertionName, {
1678
+ configurable: true,
1679
+ enumerable: true,
1680
+ value: (...sample) => new CustomMatcher(true, ...sample),
1681
+ writable: true
1682
+ });
1683
+ Object.defineProperty(globalThis[ASYMMETRIC_MATCHERS_OBJECT], expectAssertionName, {
1684
+ configurable: true,
1685
+ enumerable: true,
1686
+ value: customMatcher,
1687
+ writable: true
1688
+ });
1689
+ });
1690
+ };
2197
1691
  }
2198
1692
  const JestExtend = (chai, utils) => {
2199
- utils.addMethod(
2200
- chai.expect,
2201
- "extend",
2202
- (expect, expects) => {
2203
- use(JestExtendPlugin(chai, expect, expects));
2204
- }
2205
- );
1693
+ utils.addMethod(chai.expect, "extend", (expect, expects) => {
1694
+ use(JestExtendPlugin(chai, expect, expects));
1695
+ });
2206
1696
  };
2207
1697
 
2208
1698
  export { ASYMMETRIC_MATCHERS_OBJECT, Any, Anything, ArrayContaining, AsymmetricMatcher, GLOBAL_EXPECT, JEST_MATCHERS_OBJECT, JestAsymmetricMatchers, JestChaiExpect, JestExtend, MATCHERS_OBJECT, ObjectContaining, StringContaining, StringMatching, addCustomEqualityTesters, arrayBufferEquality, customMatchers, equals, fnNameFor, generateToBeMessage, getObjectKeys, getObjectSubset, getState, hasAsymmetric, hasProperty, isA, isAsymmetric, isImmutableUnorderedKeyed, isImmutableUnorderedSet, iterableEquality, pluralize, setState, sparseArrayEquality, subsetEquality, typeEquality };