@veams/status-quo-query 0.8.1 → 0.10.0

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
@@ -400,10 +400,10 @@ Use `dependsOn` when a query needs data from other queries before it can run.
400
400
 
401
401
  `dependsOn` accepts a `QueryDependencyTuple`:
402
402
 
403
- - an ordered list of source query keys to observe
403
+ - an ordered list of source query services
404
404
  - a `deriveOptions(...)` callback that returns only `queryKey` and/or `enabled`
405
405
 
406
- The watcher starts on the first `subscribe(...)` or `refetch()`, reads the current cache immediately, and stops after the last unsubscribe.
406
+ The watcher starts on the first `subscribe(...)` or `refetch()`, reads the current source snapshots immediately, and stops after the last unsubscribe. A downstream `refetch()` refetches all source services first, then refetches the derived query.
407
407
 
408
408
  Untracked example:
409
409
 
@@ -416,8 +416,8 @@ type Config = { region: string; companyProfileEnabled: boolean };
416
416
 
417
417
  const queryClient = new QueryClient();
418
418
  const createQuery = setupQuery(queryClient);
419
- const userKey = ['user', 42] as const;
420
- const configKey = ['config', 'global'] as const;
419
+ const userQuery = createQuery(['user', 42] as const, () => fetchUser(42), { enabled: false });
420
+ const configQuery = createQuery(['config', 'global'] as const, fetchConfig, { enabled: false });
421
421
 
422
422
  const companyProfileQuery = createQuery(
423
423
  ['company-profile', { companyId: undefined as string | undefined, region: undefined as string | undefined }],
@@ -425,7 +425,7 @@ const companyProfileQuery = createQuery(
425
425
  {
426
426
  enabled: false,
427
427
  dependsOn: <QueryDependencyTuple<[User, Config]>>[
428
- [userKey, configKey],
428
+ [userQuery, configQuery],
429
429
  ([userSnapshot, configSnapshot]) => {
430
430
  if (!userSnapshot.data?.companyId || !configSnapshot.data?.region) {
431
431
  return { enabled: false };
@@ -455,7 +455,11 @@ import { setupQueryManager } from '@veams/status-quo-query';
455
455
 
456
456
  const queryClient = new QueryClient();
457
457
  const manager = setupQueryManager(queryClient);
458
- const selectionKey = ['selection'] as const;
458
+ const selectionQuery = manager.createUntrackedQuery(
459
+ ['selection'] as const,
460
+ fetchSelection,
461
+ { enabled: false }
462
+ );
459
463
 
460
464
  const productQuery = manager.createQuery(
461
465
  ['product', { deps: { applicationId: 'pending' }, view: { page: 0 } }],
@@ -463,7 +467,7 @@ const productQuery = manager.createQuery(
463
467
  {
464
468
  enabled: false,
465
469
  dependsOn: [
466
- [selectionKey],
470
+ [selectionQuery],
467
471
  ([selectionSnapshot]) =>
468
472
  selectionSnapshot.data?.applicationId
469
473
  ? {
@@ -610,7 +614,7 @@ It also adds:
610
614
 
611
615
  - `dependsOn?: QueryDependencyTuple<[...sources]>`
612
616
 
613
- `dependsOn` observes the listed source keys through TanStack `QueriesObserver` and lets the downstream query derive only `queryKey` and `enabled`. The public `QueryService` API does not change when this option is used.
617
+ `dependsOn` observes the listed source query services and lets the downstream query derive only `queryKey` and `enabled`. Source services are activated while the downstream query is active, and downstream `refetch()` refetches the sources first. The public `QueryService` API does not change when this option is used.
614
618
 
615
619
  `QueryService` methods:
616
620
 
package/dist/index.d.ts CHANGED
@@ -1,4 +1,5 @@
1
1
  export * from './mutation.js';
2
2
  export * from './query.js';
3
3
  export * from './provider.js';
4
+ export * from './query-registry.js';
4
5
  export type { TrackedDependencyRecord, TrackedDependencyValue, TrackedInvalidateOn, TrackedMatchMode, TrackedQueryKey, TrackedQueryKeySegment, } from './tracking.js';
package/dist/index.js CHANGED
@@ -4,4 +4,6 @@ export * from './mutation.js';
4
4
  export * from './query.js';
5
5
  // Re-export all provider-related types and functions for cache management.
6
6
  export * from './provider.js';
7
+ // Re-export query registry helpers for memoizing query services by key.
8
+ export * from './query-registry.js';
7
9
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,cAAc,eAAe,CAAC;AAC9B,mDAAmD;AACnD,cAAc,YAAY,CAAC;AAC3B,2EAA2E;AAC3E,cAAc,eAAe,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,cAAc,eAAe,CAAC;AAC9B,mDAAmD;AACnD,cAAc,YAAY,CAAC;AAC3B,2EAA2E;AAC3E,cAAc,eAAe,CAAC;AAC9B,wEAAwE;AACxE,cAAc,qBAAqB,CAAC"}
@@ -0,0 +1,9 @@
1
+ import type { QueryService } from './query.js';
2
+ export interface QueryRegistry<TParams, TKey extends readonly unknown[]> {
3
+ clear: () => void;
4
+ getKey: (params: TParams) => TKey;
5
+ name: string;
6
+ resolve: <TData, TError = Error>(params: TParams, create: (queryKey: TKey) => QueryService<TData, TError>) => QueryService<TData, TError>;
7
+ }
8
+ export declare function createQueryRegistry<TParams, TKey extends readonly unknown[]>(name: string, createKey: (params: TParams) => TKey): QueryRegistry<TParams, TKey>;
9
+ export declare function serializeQueryKey(queryKey: readonly unknown[]): string;
@@ -0,0 +1,28 @@
1
+ import { hashKey } from '@tanstack/query-core';
2
+ export function createQueryRegistry(name, createKey) {
3
+ const entries = new Map();
4
+ return {
5
+ name,
6
+ clear() {
7
+ entries.clear();
8
+ },
9
+ getKey(params) {
10
+ return createKey(params);
11
+ },
12
+ resolve(params, create) {
13
+ const queryKey = createKey(params);
14
+ const cacheKey = serializeQueryKey(queryKey);
15
+ const existingEntry = entries.get(cacheKey);
16
+ if (existingEntry) {
17
+ return existingEntry;
18
+ }
19
+ const nextEntry = create(queryKey);
20
+ entries.set(cacheKey, nextEntry);
21
+ return nextEntry;
22
+ },
23
+ };
24
+ }
25
+ export function serializeQueryKey(queryKey) {
26
+ return hashKey(queryKey);
27
+ }
28
+ //# sourceMappingURL=query-registry.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"query-registry.js","sourceRoot":"","sources":["../src/query-registry.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,sBAAsB,CAAC;AAc/C,MAAM,UAAU,mBAAmB,CACjC,IAAY,EACZ,SAAoC;IAEpC,MAAM,OAAO,GAAG,IAAI,GAAG,EAA0C,CAAC;IAElE,OAAO;QACL,IAAI;QACJ,KAAK;YACH,OAAO,CAAC,KAAK,EAAE,CAAC;QAClB,CAAC;QACD,MAAM,CAAC,MAAM;YACX,OAAO,SAAS,CAAC,MAAM,CAAC,CAAC;QAC3B,CAAC;QACD,OAAO,CACL,MAAe,EACf,MAAuD;YAEvD,MAAM,QAAQ,GAAG,SAAS,CAAC,MAAM,CAAC,CAAC;YACnC,MAAM,QAAQ,GAAG,iBAAiB,CAAC,QAAQ,CAAC,CAAC;YAC7C,MAAM,aAAa,GAAG,OAAO,CAAC,GAAG,CAAC,QAAQ,CAA4C,CAAC;YAEvF,IAAI,aAAa,EAAE,CAAC;gBAClB,OAAO,aAAa,CAAC;YACvB,CAAC;YAED,MAAM,SAAS,GAAG,MAAM,CAAC,QAAQ,CAAC,CAAC;YAEnC,OAAO,CAAC,GAAG,CAAC,QAAQ,EAAE,SAA2C,CAAC,CAAC;YAEnE,OAAO,SAAS,CAAC;QACnB,CAAC;KACF,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,iBAAiB,CAAC,QAA4B;IAC5D,OAAO,OAAO,CAAC,QAAQ,CAAC,CAAC;AAC3B,CAAC"}
package/dist/query.d.ts CHANGED
@@ -42,8 +42,8 @@ type QueryDependencyDerivedOptions<TQueryKey extends QueryKey = QueryKey> = {
42
42
  queryKey?: TQueryKey;
43
43
  };
44
44
  export type QueryDependencyTuple<TSources extends readonly unknown[], TQueryKey extends QueryKey = QueryKey> = readonly [
45
- sourceKeys: {
46
- readonly [K in keyof TSources]: QueryKey;
45
+ sources: {
46
+ readonly [K in keyof TSources]: QueryService<TSources[K], Error>;
47
47
  },
48
48
  deriveOptions: (sourceSnapshots: {
49
49
  readonly [K in keyof TSources]: QueryServiceSnapshot<TSources[K], Error>;
package/dist/query.js CHANGED
@@ -1,6 +1,6 @@
1
1
  import {
2
2
  // Import QueryObserver to monitor and manage individual queries.
3
- QueryObserver, QueriesObserver, } from '@tanstack/query-core';
3
+ QueryObserver, } from '@tanstack/query-core';
4
4
  import { extractTrackedDependencies, } from './tracking.js';
5
5
  /**
6
6
  * Extracts and maps status and fetchStatus to our QueryMetaState interface.
@@ -30,7 +30,7 @@ export function setupQuery(queryClient) {
30
30
  if (!dependsOn) {
31
31
  return service.service;
32
32
  }
33
- return bindQueryDependencies(queryClient, service, queryKey, dependsOn);
33
+ return bindQueryDependencies(service, queryKey, dependsOn);
34
34
  };
35
35
  }
36
36
  /**
@@ -63,7 +63,7 @@ export function setupTrackedQuery(queryClient, trackingRegistry) {
63
63
  trackingRegistry.register(nextQueryHash, extractTrackedDependencies(service.getCurrentQueryKey()));
64
64
  };
65
65
  const dependencyController = dependsOn
66
- ? createDependencyController(queryClient, queryKey, applyTrackedDerivedState, dependsOn)
66
+ ? createDependencyController(queryKey, applyTrackedDerivedState, dependsOn)
67
67
  : undefined;
68
68
  const ensureRegistered = () => {
69
69
  // Build resolves the current live TanStack query for the stored observer options. This is
@@ -79,7 +79,7 @@ export function setupTrackedQuery(queryClient, trackingRegistry) {
79
79
  return {
80
80
  ...service.service,
81
81
  refetch: async (refetchOptions) => {
82
- dependencyController?.evaluateOnce();
82
+ await dependencyController?.evaluateForRefetch();
83
83
  // Refetch is one of the two explicit reactivation paths agreed on in the design.
84
84
  ensureRegistered();
85
85
  return service.service.refetch(refetchOptions);
@@ -158,13 +158,13 @@ function createQueryService(queryClient, queryKey, queryFn, options) {
158
158
  },
159
159
  };
160
160
  }
161
- function bindQueryDependencies(queryClient, queryService, queryKey, dependsOn) {
162
- const dependencyController = createDependencyController(queryClient, queryKey, queryService.setDerivedState, dependsOn);
161
+ function bindQueryDependencies(queryService, queryKey, dependsOn) {
162
+ const dependencyController = createDependencyController(queryKey, queryService.setDerivedState, dependsOn);
163
163
  let subscriberCount = 0;
164
164
  return {
165
165
  ...queryService.service,
166
166
  refetch: async (refetchOptions) => {
167
- dependencyController.evaluateOnce();
167
+ await dependencyController.evaluateForRefetch();
168
168
  return queryService.service.refetch(refetchOptions);
169
169
  },
170
170
  subscribe: (listener) => {
@@ -183,44 +183,59 @@ function bindQueryDependencies(queryClient, queryService, queryKey, dependsOn) {
183
183
  },
184
184
  };
185
185
  }
186
- function createDependencyController(queryClient, baseQueryKey, setDerivedState, dependsOn) {
187
- const [sourceKeys, deriveOptions] = dependsOn;
188
- let queriesObserver;
189
- let unsubscribe;
190
- const evaluateBinding = (results) => {
191
- const snapshots = results.map((result) => toQueryServiceSnapshot(result));
186
+ function createDependencyController(baseQueryKey, setDerivedState, dependsOn) {
187
+ const [sources, deriveOptions] = dependsOn;
188
+ let isActive = false;
189
+ let scheduledEvaluation = false;
190
+ let sourceUnsubscribers = [];
191
+ const evaluateBinding = () => {
192
+ const snapshots = sources.map((source) => source.getSnapshot());
192
193
  const derivedOptions = deriveOptions(snapshots);
193
194
  setDerivedState({
194
195
  queryKey: derivedOptions.queryKey ?? baseQueryKey,
195
196
  ...(derivedOptions.enabled === undefined ? {} : { enabled: derivedOptions.enabled }),
196
197
  });
197
198
  };
198
- const createObserver = () => new QueriesObserver(queryClient, sourceKeys.map((sourceKey) => ({
199
- enabled: false,
200
- queryKey: sourceKey,
201
- })));
199
+ const scheduleEvaluate = () => {
200
+ if (scheduledEvaluation) {
201
+ return;
202
+ }
203
+ scheduledEvaluation = true;
204
+ queueMicrotask(() => {
205
+ scheduledEvaluation = false;
206
+ if (!isActive) {
207
+ return;
208
+ }
209
+ evaluateBinding();
210
+ });
211
+ };
202
212
  return {
203
213
  activate: () => {
204
- if (queriesObserver) {
214
+ if (isActive) {
205
215
  return;
206
216
  }
207
- queriesObserver = createObserver();
208
- evaluateBinding(queriesObserver.getCurrentResult());
209
- unsubscribe = queriesObserver.subscribe(evaluateBinding);
217
+ isActive = true;
218
+ sourceUnsubscribers = sources.map((source) => source.subscribe(() => {
219
+ scheduleEvaluate();
220
+ }));
221
+ evaluateBinding();
210
222
  },
211
223
  deactivate: () => {
212
- unsubscribe?.();
213
- unsubscribe = undefined;
214
- queriesObserver = undefined;
224
+ isActive = false;
225
+ sourceUnsubscribers.forEach((unsubscribe) => {
226
+ unsubscribe();
227
+ });
228
+ sourceUnsubscribers = [];
215
229
  },
216
- evaluateOnce: () => {
217
- if (queriesObserver) {
218
- evaluateBinding(queriesObserver.getCurrentResult());
230
+ evaluateForRefetch: async () => {
231
+ await Promise.all(sources.map(async (source) => {
232
+ await source.refetch();
233
+ }));
234
+ if (isActive) {
235
+ scheduleEvaluate();
219
236
  return;
220
237
  }
221
- const transientObserver = createObserver();
222
- evaluateBinding(transientObserver.getCurrentResult());
223
- transientObserver.destroy();
238
+ evaluateBinding();
224
239
  },
225
240
  };
226
241
  }
package/dist/query.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"query.js","sourceRoot":"","sources":["../src/query.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"query.js","sourceRoot":"","sources":["../src/query.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@veams/status-quo-query",
3
- "version": "0.8.1",
3
+ "version": "0.10.0",
4
4
  "description": "TanStack Query service layer for the VEAMS StatusQuo ecosystem.",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.js",
@@ -32,6 +32,13 @@
32
32
  "default": "./dist/provider.js"
33
33
  },
34
34
  "require": "./dist/provider.js"
35
+ },
36
+ "./query-registry": {
37
+ "import": {
38
+ "types": "./dist/query-registry.d.ts",
39
+ "default": "./dist/query-registry.js"
40
+ },
41
+ "require": "./dist/query-registry.js"
35
42
  }
36
43
  },
37
44
  "types": "dist/index.d.ts",
@@ -0,0 +1,101 @@
1
+ import type { QueryService } from '../query';
2
+ import { createQueryRegistry, serializeQueryKey } from '../query-registry';
3
+
4
+ describe('createQueryRegistry', () => {
5
+ it('reuses the same entry for identical params', () => {
6
+ const registry = createQueryRegistry('branches', (params: { branchId: string }) => [
7
+ 'branch',
8
+ {
9
+ deps: {
10
+ branchId: params.branchId,
11
+ },
12
+ },
13
+ ] as const);
14
+ const createEntry = jest.fn((queryKey) => ({ queryKey }));
15
+
16
+ const firstEntry = registry.resolve({ branchId: 'branch-1' }, createEntry as never);
17
+ const secondEntry = registry.resolve({ branchId: 'branch-1' }, createEntry as never);
18
+
19
+ expect(firstEntry).toBe(secondEntry);
20
+ expect(createEntry).toHaveBeenCalledTimes(1);
21
+ });
22
+
23
+ it('creates separate entries for different params', () => {
24
+ const registry = createQueryRegistry('branches', (params: { branchId: string }) => [
25
+ 'branch',
26
+ {
27
+ deps: {
28
+ branchId: params.branchId,
29
+ },
30
+ },
31
+ ] as const);
32
+ const createEntry = jest.fn((queryKey) => ({ queryKey }));
33
+
34
+ const firstEntry = registry.resolve({ branchId: 'branch-1' }, createEntry as never);
35
+ const secondEntry = registry.resolve({ branchId: 'branch-2' }, createEntry as never);
36
+
37
+ expect(firstEntry).not.toBe(secondEntry);
38
+ expect(createEntry).toHaveBeenCalledTimes(2);
39
+ });
40
+
41
+ it('exposes the generated query key', () => {
42
+ const registry = createQueryRegistry('branches', (params: { branchId: string }) => [
43
+ 'branch',
44
+ {
45
+ deps: {
46
+ branchId: params.branchId,
47
+ },
48
+ },
49
+ ] as const);
50
+
51
+ expect(registry.getKey({ branchId: 'branch-1' })).toEqual([
52
+ 'branch',
53
+ {
54
+ deps: {
55
+ branchId: 'branch-1',
56
+ },
57
+ },
58
+ ]);
59
+ });
60
+
61
+ it('uses TanStack-compatible stable hashing for object keys', () => {
62
+ const firstKey = ['branch', { deps: { branchId: 'branch-1', companyId: 'company-1' } }] as const;
63
+ const secondKey = ['branch', { deps: { companyId: 'company-1', branchId: 'branch-1' } }] as const;
64
+
65
+ expect(serializeQueryKey(firstKey)).toBe(serializeQueryKey(secondKey));
66
+ });
67
+
68
+ it('infers the query service type from the creator callback', () => {
69
+ const registry = createQueryRegistry('branches', (params: { branchId: string }) => [
70
+ 'branch',
71
+ {
72
+ deps: {
73
+ branchId: params.branchId,
74
+ },
75
+ },
76
+ ] as const);
77
+
78
+ const query = registry.resolve({ branchId: 'branch-1' }, () => {
79
+ return {
80
+ getSnapshot: () => ({
81
+ data: { id: 'branch-1' },
82
+ error: null,
83
+ fetchStatus: 'idle',
84
+ isError: false,
85
+ isFetching: false,
86
+ isPending: false,
87
+ isSuccess: true,
88
+ status: 'success',
89
+ }),
90
+ invalidate: jest.fn(),
91
+ refetch: jest.fn(),
92
+ subscribe: jest.fn(),
93
+ unsafe_getResult: jest.fn(),
94
+ } as unknown as QueryService<{ id: string }, Error>;
95
+ });
96
+
97
+ const typedQuery: QueryService<{ id: string }, Error> = query;
98
+
99
+ expect(typedQuery).toBe(query);
100
+ });
101
+ });
@@ -68,6 +68,12 @@ describe('Query Service', () => {
68
68
  const createQuery = setupQuery(queryClient);
69
69
  const userKey = ['user', 42] as const;
70
70
  const configKey = ['config', 'global'] as const;
71
+ const userQuery = createQuery(userKey, jest.fn().mockResolvedValue({ companyId: 'company-1' }), {
72
+ enabled: false,
73
+ });
74
+ const configQuery = createQuery(configKey, jest.fn().mockResolvedValue({ region: 'eu' }), {
75
+ enabled: false,
76
+ });
71
77
  const queryFn = jest
72
78
  .fn()
73
79
  .mockImplementation(({ queryKey }) => `${queryKey[1].companyId}:${queryKey[1].region}`);
@@ -78,7 +84,7 @@ describe('Query Service', () => {
78
84
  {
79
85
  enabled: false,
80
86
  dependsOn: [
81
- [userKey, configKey],
87
+ [userQuery, configQuery],
82
88
  ([userSnapshot, configSnapshot]) => {
83
89
  if (!userSnapshot.data?.companyId || !configSnapshot.data?.region) {
84
90
  return { enabled: false };
@@ -120,21 +126,21 @@ describe('Query Service', () => {
120
126
  unsubscribe();
121
127
  });
122
128
 
123
- it('uses warm upstream cache data when dependsOn is evaluated on first refetch', async () => {
129
+ it('uses source query data when dependsOn is evaluated on first refetch', async () => {
124
130
  const queryClient = new QueryClient({ defaultOptions: { queries: { retry: 0 } } });
125
131
  const createQuery = setupQuery(queryClient);
126
132
  const selectionKey = ['selection'] as const;
133
+ const selectionQueryFn = jest.fn().mockResolvedValue({ id: 'item-2' });
134
+ const selectionQuery = createQuery(selectionKey, selectionQueryFn, { enabled: false });
127
135
  const queryFn = jest.fn().mockImplementation(async ({ queryKey }) => queryKey[1].id);
128
136
 
129
- queryClient.setQueryData(selectionKey, { id: 'item-2' });
130
-
131
137
  const service = createQuery(
132
138
  ['details', { id: undefined as string | undefined }],
133
139
  queryFn,
134
140
  {
135
141
  enabled: false,
136
142
  dependsOn: [
137
- [selectionKey],
143
+ [selectionQuery],
138
144
  ([selectionSnapshot]) =>
139
145
  selectionSnapshot.data?.id
140
146
  ? {
@@ -149,6 +155,7 @@ describe('Query Service', () => {
149
155
  const result = await service.refetch();
150
156
 
151
157
  expect(result.data).toBe('item-2');
158
+ expect(selectionQueryFn).toHaveBeenCalledTimes(1);
152
159
  expect(queryFn).toHaveBeenCalledWith(
153
160
  expect.objectContaining({
154
161
  queryKey: ['details', { id: 'item-2' }],
@@ -159,20 +166,21 @@ describe('Query Service', () => {
159
166
  it('preserves source snapshot tuple order in dependsOn', async () => {
160
167
  const queryClient = new QueryClient({ defaultOptions: { queries: { retry: 0 } } });
161
168
  const createQuery = setupQuery(queryClient);
162
- const firstKey = ['source', 'first'] as const;
163
- const secondKey = ['source', 'second'] as const;
169
+ const firstQuery = createQuery(['source', 'first'] as const, jest.fn().mockResolvedValue({ label: 'first' }), {
170
+ enabled: false,
171
+ });
172
+ const secondQuery = createQuery(['source', 'second'] as const, jest.fn().mockResolvedValue({ label: 'second' }), {
173
+ enabled: false,
174
+ });
164
175
  const observedOrders: Array<[string | undefined, string | undefined]> = [];
165
176
 
166
- queryClient.setQueryData(firstKey, { label: 'first' });
167
- queryClient.setQueryData(secondKey, { label: 'second' });
168
-
169
177
  const service = createQuery(
170
178
  ['ordered', { left: undefined as string | undefined, right: undefined as string | undefined }],
171
179
  jest.fn().mockResolvedValue('ok'),
172
180
  {
173
181
  enabled: false,
174
182
  dependsOn: [
175
- [firstKey, secondKey],
183
+ [firstQuery, secondQuery],
176
184
  ([firstSnapshot, secondSnapshot]) => {
177
185
  observedOrders.push([firstSnapshot.data?.label, secondSnapshot.data?.label]);
178
186
 
@@ -201,6 +209,9 @@ describe('Query Service', () => {
201
209
  const invalidateQueriesSpy = jest.spyOn(queryClient, 'invalidateQueries');
202
210
  const createQuery = setupQuery(queryClient);
203
211
  const selectionKey = ['selection'] as const;
212
+ const selectionQuery = createQuery(selectionKey, jest.fn().mockResolvedValue({ id: 'item-3' }), {
213
+ enabled: false,
214
+ });
204
215
 
205
216
  queryClient.setQueryData(selectionKey, { id: 'item-3' });
206
217
 
@@ -210,7 +221,7 @@ describe('Query Service', () => {
210
221
  {
211
222
  enabled: false,
212
223
  dependsOn: [
213
- [selectionKey],
224
+ [selectionQuery],
214
225
  ([selectionSnapshot]) =>
215
226
  selectionSnapshot.data?.id
216
227
  ? {
@@ -240,6 +251,13 @@ describe('Query Service', () => {
240
251
  const invalidateQueriesSpy = jest.spyOn(queryClient, 'invalidateQueries');
241
252
  const createQuery = setupQuery(queryClient);
242
253
  const selectionKey = ['selection'] as const;
254
+ const selectionQuery = createQuery(
255
+ selectionKey,
256
+ jest.fn().mockResolvedValue({ id: 'item-2' }),
257
+ {
258
+ enabled: false,
259
+ }
260
+ );
243
261
  const queryFn = jest.fn().mockImplementation(async ({ queryKey }) => queryKey[1].id);
244
262
 
245
263
  queryClient.setQueryData(selectionKey, { id: 'item-1' });
@@ -250,7 +268,7 @@ describe('Query Service', () => {
250
268
  {
251
269
  enabled: false,
252
270
  dependsOn: [
253
- [selectionKey],
271
+ [selectionQuery],
254
272
  ([selectionSnapshot]) =>
255
273
  selectionSnapshot.data?.id
256
274
  ? {
@@ -286,6 +286,11 @@ describe('Tracked Query Invalidation', () => {
286
286
  const manager = setupQueryManager(queryClient);
287
287
  const invalidateQueriesSpy = jest.spyOn(queryClient, 'invalidateQueries');
288
288
  const selectionKey = ['selection'] as const;
289
+ const selectionQuery = manager.createUntrackedQuery(
290
+ selectionKey,
291
+ jest.fn().mockResolvedValue({ applicationId: 'app-1' }),
292
+ { enabled: false }
293
+ );
289
294
 
290
295
  queryClient.setQueryData(selectionKey, { applicationId: 'app-1' });
291
296
 
@@ -295,7 +300,7 @@ describe('Tracked Query Invalidation', () => {
295
300
  {
296
301
  enabled: false,
297
302
  dependsOn: [
298
- [selectionKey],
303
+ [selectionQuery],
299
304
  ([selectionSnapshot]) =>
300
305
  selectionSnapshot.data?.applicationId
301
306
  ? {
@@ -337,6 +342,14 @@ describe('Tracked Query Invalidation', () => {
337
342
  const manager = setupQueryManager(queryClient);
338
343
  const invalidateQueriesSpy = jest.spyOn(queryClient, 'invalidateQueries');
339
344
  const selectionKey = ['selection'] as const;
345
+ const selectionQuery = manager.createUntrackedQuery(
346
+ selectionKey,
347
+ jest
348
+ .fn()
349
+ .mockResolvedValueOnce({ applicationId: 'app-1' })
350
+ .mockResolvedValueOnce({ applicationId: 'app-2' }),
351
+ { enabled: false }
352
+ );
340
353
  const initialDerivedKey = [
341
354
  'product',
342
355
  { deps: { applicationId: 'app-1' }, view: { page: 1 } },
@@ -354,7 +367,7 @@ describe('Tracked Query Invalidation', () => {
354
367
  {
355
368
  enabled: false,
356
369
  dependsOn: [
357
- [selectionKey],
370
+ [selectionQuery],
358
371
  ([selectionSnapshot]) =>
359
372
  selectionSnapshot.data?.applicationId
360
373
  ? {
package/src/index.ts CHANGED
@@ -4,6 +4,8 @@ export * from './mutation.js';
4
4
  export * from './query.js';
5
5
  // Re-export all provider-related types and functions for cache management.
6
6
  export * from './provider.js';
7
+ // Re-export query registry helpers for memoizing query services by key.
8
+ export * from './query-registry.js';
7
9
  // Re-export tracked dependency types used by the additive tracked facade.
8
10
  export type {
9
11
  TrackedDependencyRecord,
@@ -0,0 +1,52 @@
1
+ import { hashKey } from '@tanstack/query-core';
2
+
3
+ import type { QueryService } from './query.js';
4
+
5
+ export interface QueryRegistry<TParams, TKey extends readonly unknown[]> {
6
+ clear: () => void;
7
+ getKey: (params: TParams) => TKey;
8
+ name: string;
9
+ resolve: <TData, TError = Error>(
10
+ params: TParams,
11
+ create: (queryKey: TKey) => QueryService<TData, TError>
12
+ ) => QueryService<TData, TError>;
13
+ }
14
+
15
+ export function createQueryRegistry<TParams, TKey extends readonly unknown[]>(
16
+ name: string,
17
+ createKey: (params: TParams) => TKey
18
+ ): QueryRegistry<TParams, TKey> {
19
+ const entries = new Map<string, QueryService<unknown, unknown>>();
20
+
21
+ return {
22
+ name,
23
+ clear() {
24
+ entries.clear();
25
+ },
26
+ getKey(params) {
27
+ return createKey(params);
28
+ },
29
+ resolve<TData, TError = Error>(
30
+ params: TParams,
31
+ create: (queryKey: TKey) => QueryService<TData, TError>
32
+ ) {
33
+ const queryKey = createKey(params);
34
+ const cacheKey = serializeQueryKey(queryKey);
35
+ const existingEntry = entries.get(cacheKey) as QueryService<TData, TError> | undefined;
36
+
37
+ if (existingEntry) {
38
+ return existingEntry;
39
+ }
40
+
41
+ const nextEntry = create(queryKey);
42
+
43
+ entries.set(cacheKey, nextEntry as QueryService<unknown, unknown>);
44
+
45
+ return nextEntry;
46
+ },
47
+ };
48
+ }
49
+
50
+ export function serializeQueryKey(queryKey: readonly unknown[]): string {
51
+ return hashKey(queryKey);
52
+ }
package/src/query.ts CHANGED
@@ -13,7 +13,6 @@ import {
13
13
  type QueryKey,
14
14
  // Import QueryObserver to monitor and manage individual queries.
15
15
  QueryObserver,
16
- QueriesObserver,
17
16
  type QueryOptions,
18
17
  // Import configuration options for the query observer.
19
18
  type QueryObserverOptions,
@@ -109,7 +108,7 @@ export type QueryDependencyTuple<
109
108
  TSources extends readonly unknown[],
110
109
  TQueryKey extends QueryKey = QueryKey,
111
110
  > = readonly [
112
- sourceKeys: { readonly [K in keyof TSources]: QueryKey },
111
+ sources: { readonly [K in keyof TSources]: QueryService<TSources[K], Error> },
113
112
  deriveOptions: (
114
113
  sourceSnapshots: { readonly [K in keyof TSources]: QueryServiceSnapshot<TSources[K], Error> }
115
114
  ) => QueryDependencyDerivedOptions<TQueryKey>,
@@ -221,7 +220,7 @@ export function setupQuery(queryClient: QueryClient): CreateUntrackedQuery {
221
220
  return service.service;
222
221
  }
223
222
 
224
- return bindQueryDependencies(queryClient, service, queryKey, dependsOn);
223
+ return bindQueryDependencies(service, queryKey, dependsOn);
225
224
  };
226
225
  }
227
226
 
@@ -281,7 +280,6 @@ export function setupTrackedQuery(
281
280
 
282
281
  const dependencyController = dependsOn
283
282
  ? createDependencyController(
284
- queryClient,
285
283
  queryKey,
286
284
  applyTrackedDerivedState,
287
285
  dependsOn
@@ -307,7 +305,7 @@ export function setupTrackedQuery(
307
305
  return {
308
306
  ...service.service,
309
307
  refetch: async (refetchOptions) => {
310
- dependencyController?.evaluateOnce();
308
+ await dependencyController?.evaluateForRefetch();
311
309
  // Refetch is one of the two explicit reactivation paths agreed on in the design.
312
310
  ensureRegistered();
313
311
  return service.service.refetch(refetchOptions);
@@ -435,7 +433,6 @@ function bindQueryDependencies<
435
433
  TQueryData = TQueryFnData,
436
434
  TQueryKey extends QueryKey = QueryKey,
437
435
  >(
438
- queryClient: QueryClient,
439
436
  queryService: ReturnType<
440
437
  typeof createQueryService<TQueryFnData, TError, TData, TQueryData, TQueryKey>
441
438
  >,
@@ -443,7 +440,6 @@ function bindQueryDependencies<
443
440
  dependsOn: QueryDependencyTuple<TSources, TQueryKey>
444
441
  ): QueryService<TData, TError> {
445
442
  const dependencyController = createDependencyController(
446
- queryClient,
447
443
  queryKey,
448
444
  queryService.setDerivedState,
449
445
  dependsOn
@@ -453,7 +449,7 @@ function bindQueryDependencies<
453
449
  return {
454
450
  ...queryService.service,
455
451
  refetch: async (refetchOptions) => {
456
- dependencyController.evaluateOnce();
452
+ await dependencyController.evaluateForRefetch();
457
453
  return queryService.service.refetch(refetchOptions);
458
454
  },
459
455
  subscribe: (listener) => {
@@ -484,19 +480,17 @@ function createDependencyController<
484
480
  TQueryData = TQueryFnData,
485
481
  TQueryKey extends QueryKey = QueryKey,
486
482
  >(
487
- queryClient: QueryClient,
488
483
  baseQueryKey: TQueryKey,
489
484
  setDerivedState: (derivedOptions: QueryDependencyDerivedOptions<TQueryKey>) => void,
490
485
  dependsOn: QueryDependencyTuple<TSources, TQueryKey>
491
486
  ) {
492
- const [sourceKeys, deriveOptions] = dependsOn;
493
- let queriesObserver: QueriesObserver | undefined;
494
- let unsubscribe: (() => void) | undefined;
495
-
496
- const evaluateBinding = (results: QueryObserverResult[]) => {
497
- const snapshots = results.map((result) =>
498
- toQueryServiceSnapshot(result)
499
- ) as Parameters<typeof deriveOptions>[0];
487
+ const [sources, deriveOptions] = dependsOn;
488
+ let isActive = false;
489
+ let scheduledEvaluation = false;
490
+ let sourceUnsubscribers: Array<() => void> = [];
491
+
492
+ const evaluateBinding = () => {
493
+ const snapshots = sources.map((source) => source.getSnapshot()) as Parameters<typeof deriveOptions>[0];
500
494
  const derivedOptions = deriveOptions(snapshots);
501
495
 
502
496
  setDerivedState({
@@ -505,39 +499,58 @@ function createDependencyController<
505
499
  });
506
500
  };
507
501
 
508
- const createObserver = () =>
509
- new QueriesObserver(
510
- queryClient,
511
- sourceKeys.map((sourceKey) => ({
512
- enabled: false,
513
- queryKey: sourceKey,
514
- }))
515
- );
502
+ const scheduleEvaluate = () => {
503
+ if (scheduledEvaluation) {
504
+ return;
505
+ }
506
+
507
+ scheduledEvaluation = true;
508
+
509
+ queueMicrotask(() => {
510
+ scheduledEvaluation = false;
511
+
512
+ if (!isActive) {
513
+ return;
514
+ }
515
+
516
+ evaluateBinding();
517
+ });
518
+ };
516
519
 
517
520
  return {
518
521
  activate: () => {
519
- if (queriesObserver) {
522
+ if (isActive) {
520
523
  return;
521
524
  }
522
525
 
523
- queriesObserver = createObserver();
524
- evaluateBinding(queriesObserver.getCurrentResult());
525
- unsubscribe = queriesObserver.subscribe(evaluateBinding);
526
+ isActive = true;
527
+ sourceUnsubscribers = sources.map((source) =>
528
+ source.subscribe(() => {
529
+ scheduleEvaluate();
530
+ })
531
+ );
532
+ evaluateBinding();
526
533
  },
527
534
  deactivate: () => {
528
- unsubscribe?.();
529
- unsubscribe = undefined;
530
- queriesObserver = undefined;
535
+ isActive = false;
536
+ sourceUnsubscribers.forEach((unsubscribe) => {
537
+ unsubscribe();
538
+ });
539
+ sourceUnsubscribers = [];
531
540
  },
532
- evaluateOnce: () => {
533
- if (queriesObserver) {
534
- evaluateBinding(queriesObserver.getCurrentResult());
541
+ evaluateForRefetch: async () => {
542
+ await Promise.all(
543
+ sources.map(async (source) => {
544
+ await source.refetch();
545
+ })
546
+ );
547
+
548
+ if (isActive) {
549
+ scheduleEvaluate();
535
550
  return;
536
551
  }
537
552
 
538
- const transientObserver = createObserver();
539
- evaluateBinding(transientObserver.getCurrentResult());
540
- transientObserver.destroy();
553
+ evaluateBinding();
541
554
  },
542
555
  };
543
556
  }