Skip to content

Commit 75decd6

Browse files
committed
feat: zodmint/tanstack-query adapter (v2.6.0)
- mockQueryClient() — pre-populate QueryClient cache synchronously - mockQueryFn() — queryFn replacement for use inside useQuery - mockInfiniteQueryClient() — infinite query cache with v5 page shape - Framework-agnostic: @tanstack/query-core only, works with React/Vue/Svelte/Solid - 12 new tests, 546 total passing
1 parent c2bebb9 commit 75decd6

8 files changed

Lines changed: 450 additions & 5 deletions

File tree

CHANGELOG.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,17 @@ All notable changes to zodmint are documented here. This project follows [Keep a
44

55
---
66

7+
## [2.6.0] - 2026-06-03
8+
9+
### Added
10+
- **`zodmint/tanstack-query`** — new sub-entry for pre-populating `QueryClient` cache in tests. Framework-agnostic: imports only from `@tanstack/query-core`, works with React, Vue, Svelte, and Solid.
11+
- `mockQueryClient(entries, defaultOptions?)` — creates a `QueryClient` with synchronously pre-populated cache via `setQueryData`. Applies test-friendly defaults (`retry: false`, `staleTime: Infinity`, `gcTime: Infinity`). Each entry maps a query key array to a Zod schema plus optional `MockOptions`.
12+
- `mockQueryFn(schema, options?)` — returns a `queryFn`-compatible function for use directly inside `useQuery`. Useful when you want zodmint data without bypassing the query lifecycle.
13+
- `mockInfiniteQueryClient(entries, defaultOptions?)` — same as `mockQueryClient` but produces TanStack Query v5 infinite data shape (`{ pages: [items[]], pageParams: [undefined] }`). Configurable `pageSize` per entry.
14+
- `@tanstack/query-core >= 5.0.0` added as optional peer dependency.
15+
16+
---
17+
718
## [2.5.1] - 2026-06-03
819

920
### Fixed

README.md

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1292,6 +1292,68 @@ Control mapping:
12921292

12931293
---
12941294

1295+
### TanStack Query — `zodmint/tanstack-query`
1296+
1297+
zodmint ships a `zodmint/tanstack-query` sub-entry for pre-populating a `QueryClient` cache in tests. No network, no `fetch` mock, no MSW — the data is injected directly into the cache before your component renders.
1298+
1299+
Works with any TanStack Query framework adapter (React, Vue, Svelte, Solid) — imports only from `@tanstack/query-core`.
1300+
1301+
```bash
1302+
npm install @tanstack/query-core
1303+
```
1304+
1305+
```typescript
1306+
import { mockQueryClient } from "zodmint/tanstack-query";
1307+
```
1308+
1309+
**`mockQueryClient(entries, defaultOptions?)`** — creates a `QueryClient` with synchronously pre-populated cache:
1310+
1311+
```typescript
1312+
const client = mockQueryClient([
1313+
{ queryKey: ["user", "1"], schema: UserSchema, options: { seed: 1 } },
1314+
{ queryKey: ["posts"], schema: z.array(PostSchema) },
1315+
]);
1316+
1317+
// In a React test (vitest + @testing-library/react):
1318+
render(
1319+
<QueryClientProvider client={client}>
1320+
<UserProfile userId="1" />
1321+
</QueryClientProvider>
1322+
);
1323+
// component renders immediately with valid data — no fetch, no loading state
1324+
```
1325+
1326+
The client has test-friendly defaults applied automatically: `retry: false`, `staleTime: Infinity`, `gcTime: Infinity`. Override via the second argument:
1327+
1328+
```typescript
1329+
const client = mockQueryClient(entries, { defaultOptions: { queries: { retry: 2 } } });
1330+
```
1331+
1332+
**`mockQueryFn(schema, options?)`** — returns a `queryFn`-compatible function for use directly inside `useQuery`:
1333+
1334+
```typescript
1335+
const { result } = renderHook(() =>
1336+
useQuery({
1337+
queryKey: ["user", "1"],
1338+
queryFn: mockQueryFn(UserSchema, { seed: 42 }),
1339+
})
1340+
);
1341+
// result.current.data is a valid User, same value on every run
1342+
```
1343+
1344+
**`mockInfiniteQueryClient(entries, defaultOptions?)`** — same as `mockQueryClient` but produces the TanStack Query v5 infinite data shape:
1345+
1346+
```typescript
1347+
const client = mockInfiniteQueryClient([
1348+
{ queryKey: ["feed"], schema: PostSchema, pageSize: 10 },
1349+
]);
1350+
1351+
const feed = client.getQueryData(["feed"]);
1352+
// { pages: [Post[10]], pageParams: [undefined] }
1353+
```
1354+
1355+
---
1356+
12951357
## Prior art
12961358

12971359
zodmint was built with an eye on the existing ecosystem. Three libraries were studied for orientation:

examples/17-tanstack-query.ts

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,35 @@
1+
// 17-tanstack-query.ts — zodmint/tanstack-query: pre-populate QueryClient cache for tests
2+
import { z } from "zod";
3+
import { mockQueryClient, mockQueryFn, mockInfiniteQueryClient } from "../src/tanstack-query.js";
4+
5+
const UserSchema = z.object({
6+
id: z.string().uuid(),
7+
name: z.string(),
8+
email: z.string().email(),
9+
});
10+
11+
const PostSchema = z.object({
12+
id: z.string().uuid(),
13+
title: z.string(),
14+
userId: z.string().uuid(),
15+
});
16+
17+
// Pre-populate cache — no network, no fetch mock needed
18+
const client = mockQueryClient([
19+
{ queryKey: ["user", "1"], schema: UserSchema, options: { seed: 1 } },
20+
{ queryKey: ["posts"], schema: z.array(PostSchema), options: { seed: 2 } },
21+
]);
22+
23+
console.log("user:", client.getQueryData(["user", "1"]));
24+
console.log("posts:", client.getQueryData(["posts"]));
25+
26+
// queryFn replacement — use inside useQuery in tests
27+
const queryFn = mockQueryFn(UserSchema, { seed: 42 });
28+
console.log("queryFn result:", queryFn());
29+
30+
// Infinite query
31+
const infiniteClient = mockInfiniteQueryClient([
32+
{ queryKey: ["feed"], schema: PostSchema, pageSize: 3 },
33+
]);
34+
const feed = infiniteClient.getQueryData(["feed"]) as { pages: unknown[][]; pageParams: unknown[] };
35+
console.log("pages:", feed.pages.length, "items per page:", feed.pages[0].length);

package-lock.json

Lines changed: 22 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "zodmint",
3-
"version": "2.5.1",
3+
"version": "2.6.0",
44
"description": "TypeScript-first schema-valid test fixture generator for Zod schemas",
55
"type": "module",
66
"main": "./dist/index.cjs",
@@ -36,6 +36,11 @@
3636
"types": "./dist/storybook.d.ts",
3737
"import": "./dist/storybook.js",
3838
"require": "./dist/storybook.cjs"
39+
},
40+
"./tanstack-query": {
41+
"types": "./dist/tanstack-query.d.ts",
42+
"import": "./dist/tanstack-query.js",
43+
"require": "./dist/tanstack-query.cjs"
3944
}
4045
},
4146
"bin": {
@@ -67,7 +72,8 @@
6772
"drizzle-orm": ">=0.29.0",
6873
"fast-check": ">=3.0.0",
6974
"msw": ">=2.0.0",
70-
"zod": ">=3.23.0"
75+
"zod": ">=3.23.0",
76+
"@tanstack/query-core": ">=5.0.0"
7177
},
7278
"peerDependenciesMeta": {
7379
"@prisma/client": {
@@ -81,9 +87,13 @@
8187
},
8288
"msw": {
8389
"optional": true
90+
},
91+
"@tanstack/query-core": {
92+
"optional": true
8493
}
8594
},
8695
"devDependencies": {
96+
"@tanstack/query-core": "^5.101.0",
8797
"@types/node": "^20.0.0",
8898
"fast-check": "^3.22.0",
8999
"msw": "^2.14.6",
@@ -133,7 +143,7 @@
133143
"url": "https://github.com/gonll/zodmint.git"
134144
},
135145
"homepage": "https://github.com/gonll/zodmint#readme",
136-
"bugs": {
146+
"bugs": {
137147
"url": "https://github.com/gonll/zodmint/issues"
138148
}
139149
}

0 commit comments

Comments
 (0)