Custom matcher context soft property
The soft property in matcher context indicates whether the assertion was called as a soft assertion. Vitest always catches the error regardless of this value, so the matcher implementation does not need to respect it.
Custom matcher context assertion property
The assertion property in matcher context (available since version 5.0.0) contains the underlying Chai assertion object. This is the same instance that Chai plugins receive, giving access to Chai's flag system and chainable methods for building custom matchers that interact with Chai's internals.
expect.getState() access to matcher context
The current test context properties available as this in matcher functions can also be retrieved by calling expect.getState().
Custom snapshot matchers
To build custom snapshot matchers (wrappers around toMatchSnapshot() / toMatchInlineSnapshot() / toMatchFileSnapshot()), use the Snapshots type exported from vitest.
Chai compatibility for extending matchers
Vitest is compatible with both Chai and Jest. You can use either the chai.use API or expect.extend to extend matchers.
Matcher function arrow vs function declaration
Use function declaration instead of arrow function in matcher implementation to have access to the this context.
TypeScript ambient declaration file requirement
When extending the Matchers interface, include the ambient declaration file in tsconfig.json. Importing vitest in the declaration file makes TypeScript treat it as an ES module, which is required for the type declaration to work.
Extending Matchers interface adds types to multiple methods
Extending the Matchers interface will add a type to expect.extend, expect().* methods, and expect.* methods at the same time.
Example expect.extend custom matcher implementation
expect.extend({
toBeFoo(received) {
const { isNot } = this
return {
// do not alter your "pass" based on isNot. Vitest does it for you
pass: received === 'foo',
message: () => `${received} is${isNot ? ' not' : ''} foo`
}
}
})
This example shows a simple custom matcher that checks if a received value equals 'foo' and returns appropriate message with isNot handling.
Example Matcher type with generic arguments
const customMatcher: Matcher<MatcherState, [arg1: unknown, arg2: unknown]> = function (received, arg1, arg2) {
// ...
}
This example shows how to use the Matcher type with generic arguments to define a custom matcher that takes multiple arguments.
Example async custom matcher with types
expect.extend({
async toBeAsyncAssertion(received) {
return {
pass: received === 'foo',
message: () => `expected ${received} to be foo`,
}
}
})
declare module 'vitest' {
interface Matchers<R, T> {
toBeAsyncAssertion: () => Promise<void>
}
}
await expect('foo').toBeAsyncAssertion()
This example shows a complete async custom matcher implementation with TypeScript types and proper await usage in the test.
Custom matcher context promise property
The promise property in matcher context contains the name of the modifier if the matcher was called on resolved/rejected (such as expect(promise).resolves.toBeFoo()), otherwise it is an empty string.
Vitest exposed matcher types
Since version 4.1, Vitest exposes Matcher (the function type), MatcherResult (the return value), and MatcherState (state available as this) types that can be used in custom matcher implementations.
expect.extend basic usage
To extend default matchers in Vitest, call expect.extend with an object containing your matchers. The matcher function receives the received value as its first argument and returns an object with pass (boolean) and message (function returning string) properties.
Custom matcher return type SyncMatcherResult
A matcher's return value should be compatible with SyncMatcherResult interface which contains: pass (boolean, required), message (function returning string, required), actual (unknown, optional), expected (unknown, optional), and meta (object, optional). Actual and expected properties will automatically appear in a diff when the matcher does not pass.
Custom matcher return type MatcherResult
MatcherResult is a union type that can be either SyncMatcherResult or Promise<SyncMatcherResult>, supporting both synchronous and asynchronous matchers.
TypeScript Matchers interface extension
To extend the Matchers interface for TypeScript in an ambient declaration file (e.g. vitest.d.ts), import 'vitest' and declare a module 'vitest' with interface Matchers<R, T>. R is the assertion return type (void for regular assertions, Promise<void> for .resolves, .rejects, expect.poll, or expect.element), and T is the type of the received value.
Async custom matcher implementation
For asynchronous matcher implementations, declare the return type as Promise<void> instead of R in the Matchers interface, and use async/await in both the implementation and test call.
Custom matcher context isNot property
The isNot property in matcher context returns true if the matcher was called on not (expect(received).not.toBeFoo()). Vitest automatically reverses the pass value based on isNot, so the matcher implementation does not need to handle it.
Custom matcher context equals utility
The equals utility function in matcher context allows comparing two values for equality, returning true if they are equal and false otherwise. It is used internally for almost every matcher and supports objects with asymmetric matchers by default.
Custom matcher context utils property
The utils property in matcher context contains a set of utility functions that can be used to display messages.
Custom matcher context currentTestName property
The currentTestName property in matcher context provides the full name of the current test including describe block.
Custom matcher context task property
The task property in matcher context (available since version 4.1.0) contains a reference to the Test runner task when available. When using global expect with concurrent tests, task is undefined; use context.expect instead to ensure task is available in custom matchers.
Custom matcher context testPath property
The testPath property in matcher context provides the file path to the current test.
Custom matcher context environment property
The environment property in matcher context provides the name of the current environment (for example, jsdom).
Pitfall with toBeTruthy when toBeDefined intended
Using toBeTruthy when you really mean toBeDefined can hide bugs because 0 and empty string are both defined but falsy.
Pitfall with floating point equality
In JavaScript, 0.1 + 0.2 doesn't equal 0.3 exactly, resulting in 0.30000000000000004, so toBe(0.3) will fail on floating point arithmetic. Use toBeCloseTo instead.
toBeNull matcher
The toBeNull matcher matches only null values.
Pitfall with unwrapped function in toThrow
If you write expect(compileCode('')).toThrow() without wrapping the call in a function, the error would be thrown before expect gets a chance to catch it, causing the test to fail with an unhandled error.
toBeUndefined matcher
The toBeUndefined matcher matches only undefined values.
toBeDefined matcher
The toBeDefined matcher is the opposite of toBeUndefined and passes for anything that isn't undefined.
toBeTruthy matcher
The toBeTruthy matcher matches anything that an if statement would treat as true.
toBeFalsy matcher
The toBeFalsy matcher matches anything that an if statement would treat as false.
toBeGreaterThanOrEqual matcher
The toBeGreaterThanOrEqual matcher checks if a number is greater than or equal to the expected value.
toBeLessThanOrEqual matcher
The toBeLessThanOrEqual matcher checks if a number is less than or equal to the expected value.
toBeCloseTo matcher for floating point comparisons
The toBeCloseTo matcher compares numbers within a small rounding error, useful for floating point arithmetic where exact equality cannot be guaranteed.
toMatch matcher for regex testing
The toMatch matcher tests strings against regular expressions, useful when checking patterns rather than exact values like error messages or URL formats.
toContain matcher for arrays and iterables
The toContain matcher checks that an array or iterable (like a Set) includes a particular item using === comparison, working well for primitives.
toContainEqual matcher for array objects
The toContainEqual matcher checks that an array contains an object with a particular structure, working like toEqual but for individual items inside an array.
toMatchObject matcher for partial object matching
The toMatchObject matcher verifies that an object contains at least the properties specified, ignoring any additional ones. Used when checking only important fields without specifying every property.
toStrictEqual matcher stricter than toEqual
The toStrictEqual matcher is stricter than toEqual in three ways: it checks undefined properties, distinguishes sparse arrays from undefined values, and verifies that objects have the same type, not just the same shape.
Using .not to negate matchers
Any matcher can be negated by inserting .not before it to verify that something is not the case.
toBe matcher for exact equality
The toBe matcher checks that a value is exactly equal using Object.is, typically used for primitive values like numbers, strings, and booleans. It checks identity, not structure.
toEqual matcher for structure comparison
The toEqual matcher recursively compares every field of an object or element of an array, ignoring object identity. It is used when comparing objects or arrays for the same shape rather than exact memory reference.
toHaveProperty matcher for checking properties
The toHaveProperty matcher checks for individual properties using a dot-separated path and optionally an expected value, useful for nested property checks.
expect.any asymmetric matcher
The expect.any(Constructor) asymmetric matcher matches any value created with the given constructor like Number, String, or Array, used in deep comparison matchers like toEqual or toMatchObject.
expect.stringContaining asymmetric matcher
The expect.stringContaining(str) asymmetric matcher matches a string that includes the given substring, used in deep comparison matchers like toEqual.
expect.stringMatching asymmetric matcher
The expect.stringMatching(regex) asymmetric matcher matches a string against a regular expression, used in deep comparison matchers like toEqual.
expect.arrayContaining asymmetric matcher
The expect.arrayContaining(arr) asymmetric matcher matches an array that includes all items in the expected array, where order doesn't matter and extra items are allowed.
expect.objectContaining asymmetric matcher
The expect.objectContaining(obj) asymmetric matcher matches an object that includes at least the specified properties, used in deep comparison matchers.
toThrow matcher for exception verification
The toThrow matcher verifies that a function throws an error. The function call must be wrapped in another function so that Vitest can catch the error instead of letting it crash the test.
expect.soft for soft assertions
The expect.soft matcher records assertion failures but lets the test keep running, allowing multiple independent things to be checked and all failures reported at once rather than stopping at the first failure.
Matcher selection guideline for equality
Use toBe for primitives (numbers, strings, booleans), toEqual for comparing structure, and toStrictEqual when also caring about types and explicit undefined values.