Check shapes with schemas and matchers
Some values change on every run, like ids and dates. For those, check the shape
instead of the exact value. In the expected body of assert, any value can be
replaced with:
- a schema from any Standard Schema library: Zod, Valibot, ArkType, Effect Schema. eberly does not depend on any of them;
- a vitest or jest asymmetric matcher:
expect.any(Number),expect.stringMatching(/@/).
You can mix them with exact values at any depth
(posts.test.ts):
const created = await alice.posts.create({ body: { title: 'Hello', content: 'First post' } })
created.assert(201, { title: 'Hello', // exact value id: z.number().int().positive(), // any Standard Schema: Zod, Valibot, ArkType… createdAt: z.iso.datetime(), publishedAt: null, authorId: expect.any(Number), // a vitest asymmetric matcher works too})
// A schema can check the whole body; fields it does not list are ignoredcreated.assert(201, z.object({ id: z.number(), title: z.string().min(1) }))- Schemas are typed. The output type of a schema must fit the field:
id: z.email()on a numericidis a type error. Matchers are typed asany, so TypeScript does not check them. - The check stays partial. A schema for the whole body passes when the body
has fields the schema does not list. To reject extra fields, use a strict
schema, such as
z.strictObject. - Errors point at the field. A failed schema reports the path, the message
from the schema and the actual value:
mismatch at "title": expected a value matching the zod schema (Invalid email address), got "Hello". - Schemas must be sync. An async schema, such as Zod with an async
refine, throws an error.
Privacy-friendly analytics, no cookies.