strong-mock 8.0.0-beta.0 → 8.0.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.
package/README.md CHANGED
@@ -44,14 +44,16 @@ console.log(foo.bar(23)); // 'I am strong!'
44
44
  - [Verifying expectations](#verifying-expectations)
45
45
  - [Resetting expectations](#resetting-expectations)
46
46
  - [Argument matchers](#argument-matchers)
47
- - [Overriding default matcher](#overriding-default-matcher)
47
+ - [Mock options](#mock-options)
48
+ - [Unexpected property return value](#unexpected-property-return-value)
49
+ - [Exact params](#exact-params)
50
+ - [Concrete matcher](#concrete-matcher)
48
51
  - [FAQ](#faq)
49
52
  - [Why do I have to set all expectations first?](#why-do-i-have-to-set-all-expectations-first)
50
- - [Can I mock an existing object/function?](#can-i-mock-an-existing-objectfunction)
53
+ - [Can I partially mock an existing object/function?](#can-i-partially-mock-an-existing-objectfunction)
51
54
  - [How do I set expectations on setters?](#how-do-i-set-expectations-on-setters)
52
55
  - [Why do I have to set a return value even if it's `undefined`?](#why-do-i-have-to-set-a-return-value-even-if-its-undefined)
53
56
  - [How do I provide a function for the mock to call?](#how-do-i-provide-a-function-for-the-mock-to-call)
54
- - [Why does accessing an unused method throw?](#why-does-accessing-an-unused-method-throw)
55
57
  - [Can I spread/enumerate a mock?](#can-i-spreadenumerate-a-mock)
56
58
  - [How can I ignore `undefined` keys when setting expectations on objects?](#how-can-i-ignore-undefined-keys-when-setting-expectations-on-objects)
57
59
 
@@ -61,29 +63,39 @@ console.log(foo.bar(23)); // 'I am strong!'
61
63
 
62
64
  ### Type safety
63
65
 
64
- The created mock matches the mocked type so all expectations are type safe. Moreover, refactorings in an IDE will also cover your expectations.
66
+ The mock expectations will share the same type guarantees as your production code, and you can safely refactor in an IDE knowing that all usages will be updated.
65
67
 
66
- ![rename-interface](media/rename-interface.gif)
68
+ ![Renaming production code and test code](media/rename-refactor.gif)
67
69
 
68
70
  ### Useful error messages
69
71
 
70
72
  Error messages include the property that has been accessed, any arguments passed to it and any remaining unmet expectations.
71
73
 
72
- ![error messages](media/error-messages.png)
74
+ ```typescript
75
+ import { mock, when } from 'strong-mock';
76
+
77
+ const fn = mock<(a: number, b: number, c: number) => number>();
78
+
79
+ when(() => fn(1, 2, 3)).thenReturn(42);
80
+
81
+ fn(4, 5, 6);
82
+ ```
83
+
84
+ ![Test output showing details about mock expectations](media/error-messages.png)
73
85
 
74
86
  ### Type safe argument matchers
75
87
 
76
- Optional argument matchers allow you to create complex expectations, while still maintaining type safety.
88
+ You can use argument matchers to partially match values, or create complex expectations, while still maintaining type safety.
77
89
 
78
- ![type safe matchers](./media/type-safe-matchers.png)
90
+ ![Type safe matcher showing a type error](media/type-safe-matchers.png)
79
91
 
80
92
  ## Installation
81
93
 
82
- ```
94
+ ```shell
83
95
  npm i -D strong-mock
84
96
  ```
85
97
 
86
- ```
98
+ ```shell
87
99
  yarn add -D strong-mock
88
100
  ```
89
101
 
@@ -113,11 +125,9 @@ console.log(foo.bar(23)); // awesome
113
125
  console.log(foo.bar(23)); // even more awesome
114
126
  ```
115
127
 
116
- By default, each call is expected to be called only once. You can expect a call to be made multiple times using the [invocation count](#setting-invocation-count-expectations) helpers.
117
-
118
128
  ### Setting invocation count expectations
119
129
 
120
- You can expect a call to be made multiple times by using the invocation count helpers `between`, `atLeast`, `times`, `anyTimes` etc.:
130
+ By default, each call is expected to be called only once. You can expect a call to be made multiple times by using the invocation count helpers `between`, `atLeast`, `times`, `anyTimes` etc.:
121
131
 
122
132
  ```typescript
123
133
  const fn = mock<(x: number) => number>();
@@ -130,6 +140,8 @@ console.log(fn(1)); // 1
130
140
  console.log(fn(1)); // throws because the expectation is finished
131
141
  ```
132
142
 
143
+ You'll notice there is no `never()` helper - if you expect a call to not be made simply don't set an expectation on it and the mock will throw if the call happens.
144
+
133
145
  ### Mocking interfaces
134
146
 
135
147
  Pass in the interface to the generic argument of `mock`:
@@ -149,8 +161,6 @@ console.log(foo.bar(23)); // 'awesome'
149
161
  console.log(foo.baz); // 100
150
162
  ```
151
163
 
152
- Since the mock is type safe the compiler will guarantee that you're only mocking things that actually exist on the interface.
153
-
154
164
  ### Mocking functions
155
165
 
156
166
  You can also mock functions similarly to interfaces:
@@ -192,18 +202,16 @@ when(() => fn(1)).thenThrow();
192
202
  when(() => fnWithPromise(1)).thenReject();
193
203
  ```
194
204
 
195
- You'll notice there is no `never()` helper - if you expect a call to not be made simply don't set an expectation on it and the mock will throw if the call happens.
196
-
197
205
  ### Verifying expectations
198
206
 
199
- Calling `verify(mock)` will make sure that all expectations set on `mock` have been met. If not, the function will throw an error and print the unmet expectations.
207
+ Calling `verify(myMock)` will make sure that all expectations set on the mock have been met, and that no additional calls have been made.
200
208
 
201
209
  ```typescript
202
210
  const fn = mock<(x: number) => number>();
203
211
 
204
212
  when(() => fn(1)).thenReturn(1).between(2, 10);
205
213
 
206
- verify(fn); // throws
214
+ verify(fn); // throws UnmetExpectations
207
215
  ```
208
216
 
209
217
  It will also throw if any unexpected calls happened that were maybe caught in the code under test.
@@ -217,10 +225,16 @@ try {
217
225
  // your code might transition to an error state here
218
226
  }
219
227
 
220
- verify(fn); // throws
228
+ verify(fn); // throws UnexpectedCalls
221
229
  ```
222
230
 
223
- It is recommended that you call `verify()` on your mocks at the end of every test. This will make sure you don't have any unused expectations in your tests and that your code did not silently catch any of the errors that are thrown when an unexpected call happens. You can use `verifyAll()` to check all existing mocks e.g. in an `afterEach` hook.
231
+ It is recommended that you call `verify()` on your mocks at the end of every test. This will make sure you don't have any unused expectations in your tests and that your code did not silently catch any of the errors that are thrown when an unexpected call happens. You can use `verifyAll()` to check all existing mocks.
232
+
233
+ ```typescript
234
+ afterEach(() => {
235
+ verifyAll();
236
+ })
237
+ ```
224
238
 
225
239
  ![verify error](./media/verify.png)
226
240
 
@@ -238,11 +252,17 @@ reset(fn);
238
252
  fn(1); // throws
239
253
  ```
240
254
 
241
- If you create common mocks that are shared by multiple tests you should reset them before using them e.g. in a `beforeEach` hook. You can use `resetAll()` to reset all existing mocks.
255
+ If you create common mocks that are shared by multiple tests you should reset them before each test. You can use `resetAll()` to reset all existing mocks.
256
+
257
+ ```typescript
258
+ beforeEach(() => {
259
+ resetAll();
260
+ })
261
+ ```
242
262
 
243
263
  ### Argument matchers
244
264
 
245
- Sometimes you're not interested in specifying all the arguments in an expectation. Maybe they've been covered in another test, maybe they're hard to specify e.g. callbacks. In those cases you can use argument matchers to either ignore some arguments or use custom matchers to check them.
265
+ Sometimes you're not interested in specifying all the arguments in an expectation. Maybe they've been covered in another test, maybe they're hard to specify e.g. callbacks, or maybe you want to match just a property from an argument.
246
266
 
247
267
  ```typescript
248
268
  const fn = mock<
@@ -260,6 +280,12 @@ console.log(fn(
260
280
  ); // 'matched!'
261
281
  ```
262
282
 
283
+ You can mix argument matchers with concrete arguments:
284
+
285
+ ```typescript
286
+ when(() => fn(42, It.isObject())).thenReturn('matched');
287
+ ```
288
+
263
289
  Available matchers:
264
290
  - `deepEquals` - the default, uses deep equality,
265
291
  - `is` - uses `Object.is` for comparison,
@@ -275,7 +301,7 @@ The following table illustrates the differences between the equality matchers:
275
301
 
276
302
  | expected | actual | `It.is` | `It.deepEquals` | `It.deepEquals({ strict: false })` |
277
303
  |--------------------|----------------------|-----------|-----------------|------------------------------------|
278
- | `"foo"` | `"bar"` | equal | equal | equal |
304
+ | `"foo"` | `"foo"` | equal | equal | equal |
279
305
  | `{ foo: "bar" }` | `{ foo: "bar" }` | not equal | equal | equal |
280
306
  | `{ }` | `{ foo: undefined }` | not equal | not equal | equal |
281
307
  | `new (class {})()` | `new (class {})()` | not equal | not equal | equal |
@@ -315,22 +341,100 @@ console.log(fn(23, (x) => x + 1)); // 42
315
341
  console.log(matcher.value?.(3)); // 4
316
342
  ```
317
343
 
318
- ### Overriding default matcher
344
+ ## Mock options
319
345
 
320
- You can override the default matcher that will be used when setting expectations with non-matcher values e.g. `42` or `{ foo: "bar" }`.
346
+ The following options can be set per mock, or globally with `setDefaults`.
321
347
 
322
- ```ts
323
- import { mock, when, It, setDefaults } from 'strong-mock';
348
+ ```typescript
349
+ import { mock, when, setDefaults } from 'strong-mock';
324
350
 
325
- // Use strict equality instead of deep equality.
326
351
  setDefaults({
327
- matcher: It.is
328
- })
352
+ exactParams: true
353
+ });
354
+
355
+ // Uses the new default.
356
+ const superStrictMock = mock<() => void>();
357
+ // Overrides the default.
358
+ const strictMock = mock<() => void>({ exactParams: false });
359
+ ```
360
+
361
+ ### Unexpected property return value
362
+
363
+ You can control what happens whenever an unexpected property is accessed, or an unexpected call is made.
364
+
365
+ ```typescript
366
+ import { mock, when, UnexpectedProperty } from 'strong-mock';
367
+
368
+ type Foo = {
369
+ bar: (value: number) => number;
370
+ }
371
+
372
+ // This is the default.
373
+ const callsThrow = mock<Foo>({
374
+ unexpectedProperty: UnexpectedProperty.CALL_THROW
375
+ });
376
+
377
+ // Accessing properties with no expectations is fine.
378
+ callsThrow.bar;
379
+ // Throws "Didn't expect bar(42) to be called".
380
+ callsThrow.bar(42);
381
+
382
+ const propertiesThrow = mock<Foo>({
383
+ unexpectedProperty: UnexpectedProperty.THROW
384
+ });
385
+
386
+ // Throws "Didn't expect property bar to be accessed".
387
+ propertiesThrow.bar;
388
+ // Throws "Didn't expect property bar to be accessed".
389
+ propertiesThrow.bar(42);
390
+ ```
391
+
392
+ ### Exact params
329
393
 
330
- const fn = mock<(x: number[]) => boolean>();
394
+ By default, function/method expectations will allow more arguments to be received than expected. Since the expectations are type safe, the TypeScript compiler will never allow expecting less arguments than required. Unspecified optional arguments will be considered ignored, as if they've been replaced with [argument matchers](#argument-matchers).
395
+
396
+ ```typescript
397
+ import { mock } from 'strong-mock';
398
+
399
+ const fn = mock<(value?: number) => number>();
400
+
401
+ when(() => fn()).thenReturn(42).twice();
402
+
403
+ // Since the expectation doesn't expect any arguments,
404
+ // both of the following are fine
405
+ console.log(fn()); // 42
406
+ console.log(fn(1)); // 42
407
+ ```
408
+
409
+ If you're not using TypeScript, or you want to be super strict, you can set `exactParams: true`.
410
+
411
+ ```typescript
412
+ import { mock } from 'strong-mock';
413
+
414
+ const fn = mock<(optionalValue?: number) => number>({
415
+ exactParams: true
416
+ });
417
+
418
+ when(() => fn()).thenReturn(42).twice();
419
+
420
+ console.log(fn()); // 42
421
+ console.log(fn(1)); // throws
422
+ ```
423
+
424
+ ### Concrete matcher
425
+
426
+ You can set the matcher that will be used in expectations with concrete values e.g. `42` or `{ foo: "bar" }`. Passing in a [matcher argument](#argument-matchers) will always take priority.
427
+
428
+ ```typescript
429
+ import { mock, when, It } from 'strong-mock';
430
+
431
+ // Use strict equality instead of deep equality.
432
+ const fn = mock<(x: number[]) => boolean>({
433
+ concreteMatcher: It.is
434
+ });
331
435
  when(() => fn([1, 2, 3])).thenReturn(true);
332
436
 
333
- fn([1, 2, 3]); // throws because different arrays
437
+ fn([1, 2, 3]); // throws because different array instances
334
438
  ```
335
439
 
336
440
  ## FAQ
@@ -341,11 +445,11 @@ This library is different from other mocking/spying libraries you might have use
341
445
 
342
446
  This design decision has a few reasons behind it. First, it forces you to be aware of what your code needs from its dependencies. Spying libraries encourage checking those needs at the end of the test after the code has already called the mocks. This can lead to tests missing dependency calls that just happen to not throw any error at runtime with the dummy values that the spies return.
343
447
 
344
- Secondly, it will highlight potential design problems such as violations of the SOLID principles. If you find yourself duplicating expectations between tests and passing dummy values to them because your test is not concerned with them then you might want to look into splitting the code to only depend on things it really needs.
448
+ Secondly, it will highlight potential design problems such as violations of the SOLID principles. If you find yourself duplicating expectations between tests and passing dummy values to them because your test is not concerned with them, then you might want to look into splitting the code to only depend on things it really needs.
345
449
 
346
- ### Can I mock an existing object/function?
450
+ ### Can I partially mock an existing object/function?
347
451
 
348
- No, although you can pass its type to `mock()` and set expectations on it as you would with a type.
452
+ No, passing a concrete implementation to `mock()` will be the same as passing a type: all properties will be mocked, and you have to set expectations on the ones that will be accessed.
349
453
 
350
454
  ### How do I set expectations on setters?
351
455
 
@@ -353,7 +457,7 @@ You currently can't do that. Please use a normal method instead e.g. `setFoo()`
353
457
 
354
458
  ### Why do I have to set a return value even if it's `undefined`?
355
459
 
356
- To make side effects explicit and to prevent future refactoring headaches. If you had just `when(() => fn())` and you later changed `fn()` to return a `number` then your expectation would become incorrect and the compiler couldn't check that for you.
460
+ To make side effects explicit and to prevent future refactoring headaches. If you had just `when(() => fn())`, and you later changed `fn()` to return a `number`, then your expectation would become incorrect and the compiler couldn't check that for you.
357
461
 
358
462
  ### How do I provide a function for the mock to call?
359
463
 
@@ -373,54 +477,6 @@ console.log(foo.bar(23)); // 'called 23'
373
477
 
374
478
  The function in `thenReturn()` will be type checked against the actual interface, so you can make sure you're passing in an implementation that makes sense. Moreover, refactoring the interface will also refactor the expectation (in a capable IDE).
375
479
 
376
- ![call-rename](media/rename-args.gif)
377
-
378
- ### Why does accessing an unused method throw?
379
-
380
- Any unexpected property access will throw an error, even if the property is a method, and you never call it. This can sometimes be inconvenient if your code e.g. destructures your mock and only calls parts of it inside your test.
381
-
382
- ```typescript
383
- interface Foo {
384
- bar: () => number;
385
- baz: () => number;
386
- }
387
-
388
- function doFoo(foo: Foo, { callBaz }: { callBaz: boolean }) {
389
- // Will throw here with unexpected access on `baz`.
390
- const { bar, baz } = foo;
391
-
392
- bar();
393
-
394
- if (callBaz) {
395
- baz();
396
- }
397
- }
398
-
399
- const foo = mock<Foo>();
400
- when(() => foo.bar()).thenReturn(42);
401
-
402
- // Throws with unexpected access on `baz`.
403
- doFoo(foo, { callBaz: false });
404
- ```
405
-
406
- To work around this, either change your code to avoid destructuring
407
-
408
- ```typescript
409
- function doFoo(foo: Foo, callBaz: boolean) {
410
- foo.bar();
411
-
412
- if (callBaz) {
413
- foo.baz();
414
- }
415
- }
416
- ```
417
-
418
- or set a dummy expectation on the methods you're not interested in during the test.
419
-
420
- ```typescript
421
- when(() => foo.baz()).thenThrow('should not be called').anyTimes();
422
- ```
423
-
424
480
  ### Can I spread/enumerate a mock?
425
481
 
426
482
  Yes, and you will only get the properties that have expectations on them.
@@ -437,7 +493,6 @@ console.log(foo2.bar); // 42
437
493
  console.log(foo2.baz); // undefined
438
494
  ```
439
495
 
440
-
441
496
  ### How can I ignore `undefined` keys when setting expectations on objects?
442
497
 
443
498
  Use the `It.deepEquals` matcher explicitly inside `when` and pass `{ strict: false }`:
@@ -445,15 +500,17 @@ Use the `It.deepEquals` matcher explicitly inside `when` and pass `{ strict: fal
445
500
  ```ts
446
501
  const fn = mock<(x: { foo: string }) => boolean>();
447
502
 
448
- when(() => fn(It.deepEquals({ foo: "bar" }, { strict: false }))).thenReturn(true);
503
+ when(() => fn(
504
+ It.deepEquals({ foo: "bar" }, { strict: false }))
505
+ ).thenReturn(true);
449
506
 
450
507
  fn({ foo: "bar", baz: undefined }) === true
451
508
  ```
452
509
 
453
- You can also set this behavior to be the default by using [`setDefaults`](#overriding-default-matcher):
510
+ You can set this behavior to be the default by configuring the [concrete matcher](#concrete-matcher).
454
511
 
455
512
  ```ts
456
513
  setDefaults({
457
- matcher: (expected) => It.deepEquals(expected, { strict: false })
514
+ concreteMatcher: (expected) => It.deepEquals(expected, { strict: false })
458
515
  });
459
516
  ```
package/dist/errors.d.ts CHANGED
@@ -1,7 +1,7 @@
1
- import { Expectation } from './expectation/expectation';
2
- import { CallMap } from './expectation/repository/expectation-repository';
3
- import { Property } from './proxy';
4
- import { PendingExpectation } from './when/pending-expectation';
1
+ import type { Expectation } from './expectation/expectation';
2
+ import type { CallMap } from './expectation/repository/expectation-repository';
3
+ import type { Property } from './proxy';
4
+ import type { PendingExpectation } from './when/pending-expectation';
5
5
  export declare class UnfinishedExpectation extends Error {
6
6
  constructor(pendingExpectation: PendingExpectation);
7
7
  }
@@ -1,10 +1,6 @@
1
- import { Property } from '../proxy';
2
- import { Matcher } from './matcher';
3
- export declare type ReturnValue = {
4
- value: any;
5
- isPromise?: boolean;
6
- isError?: boolean;
7
- };
1
+ import type { Property } from '../proxy';
2
+ import type { Matcher } from './matcher';
3
+ import type { ReturnValue } from './repository/return-value';
8
4
  /**
9
5
  * Compare received arguments against matchers.
10
6
  */
@@ -1,4 +1,4 @@
1
- import { Matcher, TypeMatcher } from './matcher';
1
+ import type { Matcher, TypeMatcher } from './matcher';
2
2
  declare type DeepPartial<T> = T extends object ? {
3
3
  [K in keyof T]?: DeepPartial<T[K]>;
4
4
  } : T;
@@ -1,5 +1,5 @@
1
- import { Expectation, ReturnValue } from '../expectation';
2
- import { Property } from '../../proxy';
1
+ import type { Property } from '../../proxy';
2
+ import type { Expectation } from '../expectation';
3
3
  export declare type Call = {
4
4
  arguments: any[] | undefined;
5
5
  };
@@ -31,7 +31,7 @@ export interface ExpectationRepository {
31
31
  /**
32
32
  * Get a return value for the given property.
33
33
  *
34
- * The value might be a non-callable e.g. a number or a string or it might
34
+ * The value might be a non-callable e.g. a number or a string, or it might
35
35
  * be a function that, upon receiving arguments, will start a new search and
36
36
  * return a value again.
37
37
  *
@@ -41,17 +41,32 @@ export interface ExpectationRepository {
41
41
  *
42
42
  * @example
43
43
  * add(new Expectation('getData', [1, 2], 23);
44
- * get('getData').value(1, 2) === 23
44
+ * get('getData')(1, 2) === 23
45
45
  *
46
46
  * @example
47
47
  * add(new Expectation('hasData', undefined, true);
48
- * get('hasData').value === true
48
+ * get('hasData') === true
49
49
  *
50
50
  * @example
51
51
  * add(new Expectation('getData', undefined, () => 42);
52
- * get('getData').value(1, 2, '3', false, NaN) === 42
52
+ * get('getData')(1, 2, '3', false, NaN) === 42
53
53
  */
54
- get(property: Property): ReturnValue;
54
+ get(property: Property): unknown;
55
+ /**
56
+ * Get a return value for a function call.
57
+ *
58
+ * Note: this will only be invoked if the mocked type is a function. For
59
+ * method property calls {@link get} will be called instead.
60
+ *
61
+ * The list of expectations should be consulted from first to last when
62
+ * getting a return value. If none of them match it is up to the
63
+ * implementation to decide what to do.
64
+ *
65
+ * @example
66
+ * add(new Expectation(ApplyProp, [1, 2], 23);
67
+ * apply(1, 2) === 23
68
+ */
69
+ apply(args: unknown[]): unknown;
55
70
  /**
56
71
  * Get all the properties that have expectations.
57
72
  *
@@ -0,0 +1,38 @@
1
+ import { UnexpectedProperty } from '../../mock/options';
2
+ import type { Property } from '../../proxy';
3
+ import type { Expectation } from '../expectation';
4
+ import type { CallMap, ExpectationRepository } from './expectation-repository';
5
+ declare type CountableExpectation = {
6
+ expectation: Expectation;
7
+ matchCount: number;
8
+ };
9
+ /**
10
+ * An expectation repository with a configurable behavior for
11
+ * unexpected property access.
12
+ */
13
+ export declare class FlexibleRepository implements ExpectationRepository {
14
+ private unexpectedProperty;
15
+ constructor(unexpectedProperty?: UnexpectedProperty);
16
+ protected readonly expectations: Map<Property, CountableExpectation[]>;
17
+ private readonly expectedCallStats;
18
+ private readonly unexpectedCallStats;
19
+ add(expectation: Expectation): void;
20
+ clear(): void;
21
+ apply: (args: unknown[]) => unknown;
22
+ get(property: Property): any;
23
+ private handlePropertyWithMatchingExpectations;
24
+ private handlePropertyWithNoExpectations;
25
+ getAllProperties(): Property[];
26
+ getCallStats(): {
27
+ expected: CallMap;
28
+ unexpected: CallMap;
29
+ };
30
+ getUnmet(): Expectation[];
31
+ private recordExpected;
32
+ private recordUnexpected;
33
+ private countAndConsume;
34
+ private consumeExpectation;
35
+ private getValueForUnexpectedCall;
36
+ private getValueForUnexpectedAccess;
37
+ }
38
+ export {};
@@ -0,0 +1,13 @@
1
+ export declare type ReturnValue = {
2
+ value: any;
3
+ isPromise?: boolean;
4
+ isError?: boolean;
5
+ };
6
+ /**
7
+ * Unbox the expectation's return value.
8
+ *
9
+ * If the value is an error then throw it.
10
+ *
11
+ * If the value is a promise then resolve/reject it.
12
+ */
13
+ export declare const unboxReturnValue: ({ isError, isPromise, value, }: ReturnValue) => any;
@@ -1,6 +1,7 @@
1
- import { Property } from '../proxy';
2
- import { Expectation, ReturnValue } from './expectation';
3
- import { Matcher } from './matcher';
1
+ import type { Property } from '../proxy';
2
+ import type { Expectation } from './expectation';
3
+ import type { Matcher } from './matcher';
4
+ import type { ReturnValue } from './repository/return-value';
4
5
  /**
5
6
  * Matches a call with more parameters than expected because it is assumed the
6
7
  * compiler will check that those parameters are optional.
@@ -16,10 +17,11 @@ export declare class StrongExpectation implements Expectation {
16
17
  property: Property;
17
18
  args: Matcher[] | undefined;
18
19
  returnValue: ReturnValue;
20
+ private exactParams;
19
21
  private matched;
20
22
  min: number;
21
23
  max: number;
22
- constructor(property: Property, args: Matcher[] | undefined, returnValue: ReturnValue);
24
+ constructor(property: Property, args: Matcher[] | undefined, returnValue: ReturnValue, exactParams?: boolean);
23
25
  setInvocationCount(min: number, max?: number): void;
24
26
  matches(args: any[] | undefined): boolean;
25
27
  isUnmet(): boolean;
package/dist/index.d.ts CHANGED
@@ -5,4 +5,5 @@ export { verify, verifyAll } from './verify/verify';
5
5
  export { It } from './expectation/it';
6
6
  export { setDefaults } from './mock/defaults';
7
7
  export type { Matcher } from './expectation/matcher';
8
- export type { StrongMockDefaults } from './mock/defaults';
8
+ export type { MockOptions } from './mock/options';
9
+ export { UnexpectedProperty } from './mock/options';