0
# TanStack Query Core
1
2
TanStack Query Core is the framework-agnostic foundation that powers TanStack Query, providing sophisticated data fetching, caching, synchronization, and server state management. It implements intelligent caching strategies, automatic background updates, optimistic updates, and handles complex scenarios like query deduplication, infinite queries, and mutation management.
3
4
## Package Information
5
6
- **Package Name**: @tanstack/query-core
7
- **Package Type**: npm
8
- **Language**: TypeScript
9
- **Installation**: `npm install @tanstack/query-core`
10
11
## Core Imports
12
13
```typescript
14
import { QueryClient, QueryCache, MutationCache } from "@tanstack/query-core";
15
```
16
17
For CommonJS:
18
19
```javascript
20
const { QueryClient, QueryCache, MutationCache } = require("@tanstack/query-core");
21
```
22
23
## Basic Usage
24
25
```typescript
26
import { QueryClient, QueryObserver } from "@tanstack/query-core";
27
28
// Create a client
29
const queryClient = new QueryClient();
30
31
// Create and use a query observer
32
const observer = new QueryObserver(queryClient, {
33
queryKey: ['user', 123],
34
queryFn: async () => {
35
const response = await fetch('/api/user/123');
36
return response.json();
37
},
38
});
39
40
// Subscribe to results
41
const unsubscribe = observer.subscribe((result) => {
42
console.log(result.data); // User data
43
console.log(result.isLoading); // Loading state
44
console.log(result.error); // Error state
45
});
46
47
// Cleanup
48
unsubscribe();
49
```
50
51
## Architecture
52
53
TanStack Query Core is built around several key architectural components:
54
55
- **QueryClient**: Central orchestrator managing all queries and mutations, with configuration and lifecycle control
56
- **Cache Management**: Separate `QueryCache` and `MutationCache` systems providing intelligent storage and retrieval
57
- **Observer Pattern**: `QueryObserver`, `InfiniteQueryObserver`, and `MutationObserver` classes for reactive state management
58
- **Manager Services**: `focusManager`, `onlineManager`, and `notifyManager` for handling browser events and notification batching
59
- **Query/Mutation Instances**: Core `Query` and `Mutation` classes managing individual request lifecycles
60
- **Utility System**: Comprehensive utilities for key hashing, data replacement, retrying, and hydration/dehydration
61
62
## Capabilities
63
64
### Client Management
65
66
Central client for orchestrating all query and mutation operations with intelligent defaults, caching strategies, and lifecycle management.
67
68
```typescript { .api }
69
class QueryClient {
70
constructor(config?: QueryClientConfig);
71
mount(): void;
72
unmount(): void;
73
getQueryCache(): QueryCache;
74
getMutationCache(): MutationCache;
75
}
76
77
interface QueryClientConfig {
78
queryCache?: QueryCache;
79
mutationCache?: MutationCache;
80
defaultOptions?: DefaultOptions;
81
}
82
```
83
84
[Client Management](./client-management.md)
85
86
### Query Operations
87
88
Core query functionality including data fetching, caching, invalidation, and state management with automatic background updates.
89
90
```typescript { .api }
91
fetchQuery<T>(options: FetchQueryOptions<T>): Promise<T>;
92
prefetchQuery<T>(options: FetchQueryOptions<T>): Promise<void>;
93
getQueryData<T>(queryKey: QueryKey): T | undefined;
94
setQueryData<T>(queryKey: QueryKey, updater: Updater<T>, options?: SetDataOptions): T | undefined;
95
invalidateQueries(filters?: InvalidateQueryFilters, options?: InvalidateOptions): Promise<void>;
96
97
interface FetchQueryOptions<T> {
98
queryKey: QueryKey;
99
queryFn: QueryFunction<T>;
100
staleTime?: number;
101
gcTime?: number;
102
}
103
```
104
105
[Query Operations](./query-operations.md)
106
107
### Query Observers
108
109
Reactive observers for tracking query state changes with automatic updates, optimistic results, and lifecycle management.
110
111
```typescript { .api }
112
class QueryObserver<T> {
113
constructor(client: QueryClient, options: QueryObserverOptions<T>);
114
getCurrentResult(): QueryObserverResult<T>;
115
subscribe(onStoreChange: (result: QueryObserverResult<T>) => void): () => void;
116
refetch(options?: RefetchOptions): Promise<QueryObserverResult<T>>;
117
}
118
119
interface QueryObserverResult<T> {
120
data: T | undefined;
121
error: Error | null;
122
isLoading: boolean;
123
isFetching: boolean;
124
isSuccess: boolean;
125
isError: boolean;
126
status: 'pending' | 'error' | 'success';
127
}
128
```
129
130
[Query Observers](./query-observers.md)
131
132
### Infinite Queries
133
134
Specialized functionality for paginated data with automatic page management, bi-directional fetching, and cursor-based pagination.
135
136
```typescript { .api }
137
class InfiniteQueryObserver<T> extends QueryObserver<InfiniteData<T>> {
138
fetchNextPage(options?: FetchNextPageOptions): Promise<InfiniteQueryObserverResult<T>>;
139
fetchPreviousPage(options?: FetchPreviousPageOptions): Promise<InfiniteQueryObserverResult<T>>;
140
}
141
142
interface InfiniteData<T> {
143
pages: T[];
144
pageParams: unknown[];
145
}
146
147
interface InfiniteQueryObserverResult<T> extends QueryObserverResult<InfiniteData<T>> {
148
hasNextPage: boolean;
149
hasPreviousPage: boolean;
150
isFetchingNextPage: boolean;
151
isFetchingPreviousPage: boolean;
152
}
153
```
154
155
[Infinite Queries](./infinite-queries.md)
156
157
### Mutations
158
159
Mutation management for data modifications with optimistic updates, rollback capabilities, and side effect handling.
160
161
```typescript { .api }
162
class MutationObserver<T, TVariables> {
163
constructor(client: QueryClient, options: MutationObserverOptions<T, TVariables>);
164
mutate(variables: TVariables, options?: MutateOptions<T, TVariables>): Promise<T>;
165
reset(): void;
166
getCurrentResult(): MutationObserverResult<T>;
167
}
168
169
interface MutationObserverResult<T> {
170
data: T | undefined;
171
error: Error | null;
172
isIdle: boolean;
173
isPending: boolean;
174
isSuccess: boolean;
175
isError: boolean;
176
status: 'idle' | 'pending' | 'success' | 'error';
177
}
178
```
179
180
[Mutations](./mutations.md)
181
182
### Cache Management
183
184
Low-level cache operations for direct query and mutation cache manipulation with events, filtering, and batch operations.
185
186
```typescript { .api }
187
class QueryCache {
188
constructor(config?: QueryCacheConfig);
189
find<T>(filters: QueryFilters): Query<T> | undefined;
190
findAll(filters?: QueryFilters): Array<Query>;
191
clear(): void;
192
subscribe(callback: (event: QueryCacheNotifyEvent) => void): () => void;
193
}
194
195
interface QueryFilters {
196
queryKey?: QueryKey;
197
exact?: boolean;
198
stale?: boolean;
199
active?: boolean;
200
inactive?: boolean;
201
}
202
```
203
204
[Cache Management](./cache-management.md)
205
206
### Hydration & Serialization
207
208
Server-side rendering support with serialization and deserialization of client state for hydration across client-server boundaries.
209
210
```typescript { .api }
211
function dehydrate(client: QueryClient, options?: DehydrateOptions): DehydratedState;
212
function hydrate(client: QueryClient, dehydratedState: unknown, options?: HydrateOptions): void;
213
214
interface DehydratedState {
215
mutations: Array<DehydratedMutation>;
216
queries: Array<DehydratedQuery>;
217
}
218
```
219
220
[Hydration & Serialization](./hydration.md)
221
222
### Browser Integration
223
224
Browser event management for automatic refetching on focus and network reconnection with customizable event handling.
225
226
```typescript { .api }
227
const focusManager: {
228
setEventListener(setup: SetupFn): void;
229
setFocused(focused?: boolean): void;
230
isFocused(): boolean;
231
};
232
233
const onlineManager: {
234
setEventListener(setup: SetupFn): void;
235
setOnline(online: boolean): void;
236
isOnline(): boolean;
237
};
238
```
239
240
[Browser Integration](./browser-integration.md)
241
242
### Utilities
243
244
Core utility functions for key hashing, data manipulation, query matching, and functional programming patterns.
245
246
```typescript { .api }
247
function hashKey(key: QueryKey): string;
248
function matchQuery(filters: QueryFilters, query: Query): boolean;
249
function replaceEqualDeep<T>(a: unknown, b: T): T;
250
const keepPreviousData: <T>(previousData: T) => T;
251
const skipToken: Symbol;
252
```
253
254
[Utilities](./utilities.md)
255
256
### Low-level Query & Mutation Classes
257
258
Direct access to the underlying Query and Mutation class instances for advanced use cases.
259
260
```typescript { .api }
261
class Query<TQueryFnData, TError, TData, TQueryKey extends QueryKey> {
262
queryKey: TQueryKey;
263
queryHash: string;
264
state: QueryState<TData, TError>;
265
setData(data: TData): void;
266
setState(state: Partial<QueryState<TData, TError>>): void;
267
}
268
269
class Mutation<TData, TError, TVariables, TContext> {
270
mutationId: number;
271
state: MutationState<TData, TError, TVariables, TContext>;
272
setData(data: TData): void;
273
setState(state: Partial<MutationState<TData, TError, TVariables, TContext>>): void;
274
}
275
```
276
277
### Experimental Features
278
279
Experimental functionality that may change in future versions.
280
281
```typescript { .api }
282
function experimental_streamedQuery<
283
TQueryFnData = unknown,
284
TData = Array<TQueryFnData>,
285
TQueryKey extends QueryKey = QueryKey
286
>(params: StreamedQueryParams<TQueryFnData, TData, TQueryKey>): QueryFunction<TData, TQueryKey>;
287
288
type StreamedQueryParams<TQueryFnData, TData, TQueryKey extends QueryKey> =
289
| SimpleStreamedQueryParams<TQueryFnData, TQueryKey>
290
| ReducibleStreamedQueryParams<TQueryFnData, TData, TQueryKey>;
291
292
interface SimpleStreamedQueryParams<TQueryFnData, TQueryKey extends QueryKey> {
293
streamFn: (context: QueryFunctionContext<TQueryKey>) => AsyncIterable<TQueryFnData> | Promise<AsyncIterable<TQueryFnData>>;
294
refetchMode?: 'append' | 'reset' | 'replace';
295
}
296
297
interface ReducibleStreamedQueryParams<TQueryFnData, TData, TQueryKey extends QueryKey> {
298
streamFn: (context: QueryFunctionContext<TQueryKey>) => AsyncIterable<TQueryFnData> | Promise<AsyncIterable<TQueryFnData>>;
299
refetchMode?: 'append' | 'reset' | 'replace';
300
reducer: (acc: TData, chunk: TQueryFnData) => TData;
301
initialValue: TData;
302
}
303
```
304
305
## Core Types
306
307
```typescript { .api }
308
// QueryKey with module augmentation support
309
type QueryKey = Register extends {
310
queryKey: infer TQueryKey
311
}
312
? TQueryKey extends ReadonlyArray<unknown>
313
? TQueryKey
314
: TQueryKey extends Array<unknown>
315
? TQueryKey
316
: ReadonlyArray<unknown>
317
: ReadonlyArray<unknown>;
318
319
// QueryFunction with pagination support
320
type QueryFunction<
321
T = unknown,
322
TQueryKey extends QueryKey = QueryKey,
323
TPageParam = never
324
> = (context: QueryFunctionContext<TQueryKey, TPageParam>) => T | Promise<T>;
325
326
// Complete QueryFunctionContext with all properties
327
type QueryFunctionContext<
328
TQueryKey extends QueryKey = QueryKey,
329
TPageParam = never
330
> = [TPageParam] extends [never]
331
? {
332
client: QueryClient;
333
queryKey: TQueryKey;
334
signal: AbortSignal;
335
meta: QueryMeta | undefined;
336
pageParam?: unknown;
337
direction?: unknown; // @deprecated
338
}
339
: {
340
client: QueryClient;
341
queryKey: TQueryKey;
342
signal: AbortSignal;
343
pageParam: TPageParam;
344
direction: FetchDirection; // @deprecated
345
meta: QueryMeta | undefined;
346
};
347
348
type QueryStatus = 'pending' | 'error' | 'success';
349
type FetchStatus = 'fetching' | 'paused' | 'idle';
350
type MutationStatus = 'idle' | 'pending' | 'success' | 'error';
351
352
// Complete DefaultOptions interface
353
interface DefaultOptions<TError = DefaultError> {
354
queries?: OmitKeyof<QueryObserverOptions<unknown, TError>, 'suspense' | 'queryKey'>;
355
mutations?: MutationObserverOptions<unknown, TError, unknown, unknown>;
356
hydrate?: HydrateOptions['defaultOptions'];
357
dehydrate?: DehydrateOptions;
358
}
359
360
type Updater<T> = T | ((old: T) => T);
361
362
// Module augmentation interface
363
interface Register {
364
// Empty by default, can be augmented by users
365
}
366
367
type DefaultError = Error;
368
type FetchDirection = 'forward' | 'backward';
369
type QueryMeta = Record<string, unknown>;
370
```