@reforgium/statum 2.1.2 → 3.0.0-rc.1
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 +89 -50
- package/fesm2022/reforgium-statum.mjs +90 -75
- package/package.json +2 -1
- package/types/reforgium-statum.d.ts +100 -64
package/README.md
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
# @reforgium/statum
|
|
1
|
+
# @reforgium/statum
|
|
2
2
|
|
|
3
3
|
[](https://www.npmjs.com/package/@reforgium/statum)
|
|
4
4
|
[](https://opensource.org/licenses/MIT)
|
|
@@ -25,13 +25,29 @@ Designed for **application state**, not abstract reducers.
|
|
|
25
25
|
|
|
26
26
|
---
|
|
27
27
|
|
|
28
|
-
## Installation
|
|
29
|
-
|
|
30
|
-
```bash
|
|
31
|
-
npm install @reforgium/statum
|
|
32
|
-
```
|
|
33
|
-
|
|
34
|
-
|
|
28
|
+
## Installation
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
npm install @reforgium/statum
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
## Configuration
|
|
35
|
+
|
|
36
|
+
```ts
|
|
37
|
+
import { provideStatum } from '@reforgium/statum';
|
|
38
|
+
|
|
39
|
+
providers: [
|
|
40
|
+
provideStatum({
|
|
41
|
+
pagedQuery: {
|
|
42
|
+
defaultMethod: 'GET',
|
|
43
|
+
defaultHasCache: true,
|
|
44
|
+
defaultCacheSize: 10,
|
|
45
|
+
},
|
|
46
|
+
}),
|
|
47
|
+
];
|
|
48
|
+
```
|
|
49
|
+
|
|
50
|
+
---
|
|
35
51
|
|
|
36
52
|
## Package Structure
|
|
37
53
|
|
|
@@ -136,7 +152,7 @@ const user = await userStore.get(
|
|
|
136
152
|
);
|
|
137
153
|
```
|
|
138
154
|
|
|
139
|
-
Retry + trace example:
|
|
155
|
+
Retry + trace example:
|
|
140
156
|
|
|
141
157
|
```ts
|
|
142
158
|
import { ResourceStore } from '@reforgium/statum';
|
|
@@ -150,11 +166,22 @@ const store = new ResourceStore<{ id: number; name: string }>(
|
|
|
150
166
|
}
|
|
151
167
|
);
|
|
152
168
|
|
|
153
|
-
await store.get(
|
|
154
|
-
{ params: { id: '42' } },
|
|
155
|
-
{ retry: { attempts: 1 } } // per-call override
|
|
156
|
-
);
|
|
157
|
-
```
|
|
169
|
+
await store.get(
|
|
170
|
+
{ params: { id: '42' } },
|
|
171
|
+
{ retry: { attempts: 1 } } // per-call override
|
|
172
|
+
);
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
Profiles example:
|
|
176
|
+
|
|
177
|
+
```ts
|
|
178
|
+
import { createResourceProfile, ResourceStore } from '@reforgium/statum';
|
|
179
|
+
|
|
180
|
+
const usersStore = new ResourceStore<{ id: number; name: string }>(
|
|
181
|
+
{ GET: '/users' },
|
|
182
|
+
createResourceProfile('table', { baseUrl: '/api' })
|
|
183
|
+
);
|
|
184
|
+
```
|
|
158
185
|
|
|
159
186
|
---
|
|
160
187
|
|
|
@@ -179,9 +206,9 @@ entities.removeOne(1);
|
|
|
179
206
|
|
|
180
207
|
---
|
|
181
208
|
|
|
182
|
-
##
|
|
183
|
-
|
|
184
|
-
Lightweight store for server-side pagination with
|
|
209
|
+
## PagedQueryStore
|
|
210
|
+
|
|
211
|
+
Lightweight store for server-side pagination with filtering, dynamic query params, and page cache.
|
|
185
212
|
|
|
186
213
|
### When to use
|
|
187
214
|
|
|
@@ -200,46 +227,54 @@ Lightweight store for server-side pagination with sorting, filtering, and page c
|
|
|
200
227
|
| page | `number` | Current page (0-based) |
|
|
201
228
|
| pageSize | `number` | Page size |
|
|
202
229
|
| totalElements | `number` | Total items on server |
|
|
203
|
-
| filters | `Partial<F>` | Active filters |
|
|
204
|
-
|
|
|
230
|
+
| filters | `Partial<F>` | Active filters |
|
|
231
|
+
| query | `Record<string, unknown>` | Active query params |
|
|
205
232
|
|
|
206
233
|
### Methods
|
|
207
234
|
|
|
208
|
-
| Method | Description
|
|
209
|
-
|
|
210
|
-
|
|
|
211
|
-
|
|
|
212
|
-
|
|
|
213
|
-
|
|
|
214
|
-
|
|
|
215
|
-
|
|
|
216
|
-
|
|
|
217
|
-
|
|
|
218
|
-
|
|
|
219
|
-
|
|
220
|
-
|
|
235
|
+
| Method | Description |
|
|
236
|
+
|----------------|---------------------------------------------------------------------------|
|
|
237
|
+
| fetch | Clean first-page request: `fetch({ filters, query, routeParams })` |
|
|
238
|
+
| refetchWith | Repeat request, optional merge overrides: `refetchWith({ filters, query })` |
|
|
239
|
+
| updatePage | Change page: `updatePage(page, { ignoreCache })` |
|
|
240
|
+
| updatePageSize | Change page size and reset cache: `updatePageSize(size)` |
|
|
241
|
+
| updateByOffset | Table-event mapper: `updateByOffset({ page/first/rows }, { query })` |
|
|
242
|
+
| setRouteParams | Update route params: `setRouteParams(params, { reset, abort })` |
|
|
243
|
+
| updateConfig | Patch config: `updateConfig(config)` |
|
|
244
|
+
| copy | Copy config/meta: `copy(store)` |
|
|
245
|
+
| destroy | Manual destroying of caches and abort requests |
|
|
246
|
+
|
|
247
|
+
### Cache behavior
|
|
248
|
+
|
|
249
|
+
| Method | Cache read | Cache reset | Notes |
|
|
250
|
+
|----------------|------------|-------------|-------|
|
|
251
|
+
| fetch | no | yes | Always starts clean from page `0` |
|
|
252
|
+
| refetchWith | no | no | Uses active page/filters/query, merges overrides |
|
|
253
|
+
| updatePage | yes | no | Can bypass with `ignoreCache: true` |
|
|
254
|
+
| updatePageSize | no | yes | Prevents mixed caches for different page sizes |
|
|
255
|
+
| updateByOffset | yes | no | Internally maps to `page + size` |
|
|
221
256
|
|
|
222
257
|
Example:
|
|
223
258
|
|
|
224
259
|
```ts
|
|
225
|
-
import {
|
|
260
|
+
import { PagedQueryStore } from '@reforgium/statum';
|
|
226
261
|
|
|
227
262
|
type User = { id: number; name: string };
|
|
228
263
|
|
|
229
|
-
const store = new
|
|
230
|
-
method: 'GET',
|
|
231
|
-
debounceTime: 200,
|
|
232
|
-
});
|
|
233
|
-
|
|
234
|
-
store.
|
|
235
|
-
store.
|
|
264
|
+
const store = new PagedQueryStore<User, { search?: string }>('api/users', {
|
|
265
|
+
method: 'GET',
|
|
266
|
+
debounceTime: 200,
|
|
267
|
+
});
|
|
268
|
+
|
|
269
|
+
store.fetch({ filters: { search: 'neo' }, query: { tenant: 'kg' } });
|
|
270
|
+
store.updateByOffset({ first: 20, rows: 20 });
|
|
236
271
|
```
|
|
237
272
|
|
|
238
273
|
---
|
|
239
274
|
|
|
240
275
|
## DictStore
|
|
241
276
|
|
|
242
|
-
Helper for dictionaries/options (select/autocomplete) on top of
|
|
277
|
+
Helper for dictionaries/options (select/autocomplete) on top of PagedQueryStore.
|
|
243
278
|
|
|
244
279
|
### When to use
|
|
245
280
|
|
|
@@ -309,15 +344,15 @@ dict.search('kir'); // local search over cache
|
|
|
309
344
|
|
|
310
345
|
## Composition Patterns
|
|
311
346
|
|
|
312
|
-
###
|
|
347
|
+
### PagedQueryStore + EntityStore
|
|
313
348
|
|
|
314
349
|
```ts
|
|
315
350
|
import { effect } from '@angular/core';
|
|
316
|
-
import { EntityStore,
|
|
351
|
+
import { EntityStore, PagedQueryStore } from '@reforgium/statum';
|
|
317
352
|
|
|
318
353
|
type User = { id: number; name: string };
|
|
319
354
|
|
|
320
|
-
const pages = new
|
|
355
|
+
const pages = new PagedQueryStore<User, { search?: string }>('/api/users');
|
|
321
356
|
const entities = new EntityStore<User, 'id'>({ idKey: 'id' });
|
|
322
357
|
|
|
323
358
|
effect(() => {
|
|
@@ -325,7 +360,7 @@ effect(() => {
|
|
|
325
360
|
});
|
|
326
361
|
```
|
|
327
362
|
|
|
328
|
-
This keeps page-loading logic in `
|
|
363
|
+
This keeps page-loading logic in `PagedQueryStore` and normalized lookup/update logic in `EntityStore`.
|
|
329
364
|
|
|
330
365
|
---
|
|
331
366
|
|
|
@@ -374,11 +409,12 @@ const body = serializer.serialize({ name: ' Vasya ', active: null });
|
|
|
374
409
|
|
|
375
410
|
---
|
|
376
411
|
|
|
377
|
-
## Source Structure
|
|
378
|
-
|
|
379
|
-
- Cache: `src/cache`
|
|
380
|
-
- Stores: `src/stores`
|
|
381
|
-
- Serializer: `src/serializer`
|
|
412
|
+
## Source Structure
|
|
413
|
+
|
|
414
|
+
- Cache: `src/cache`
|
|
415
|
+
- Stores: `src/stores`
|
|
416
|
+
- Serializer: `src/serializer`
|
|
417
|
+
- Migration: `MIGRATION.md`
|
|
382
418
|
|
|
383
419
|
---
|
|
384
420
|
|
|
@@ -393,3 +429,6 @@ const body = serializer.serialize({ name: ' Vasya ', active: null });
|
|
|
393
429
|
## License
|
|
394
430
|
|
|
395
431
|
MIT
|
|
432
|
+
|
|
433
|
+
|
|
434
|
+
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { formatDate, isNullable, isDatePeriod, parseToDate, makeQuery, isNumber, isObject, parseToDatePeriod, parseQueryArray, fillUrlWithParams, deepEqual, concatArray, debounceSignal } from '@reforgium/internal';
|
|
2
2
|
import { HttpClient } from '@angular/common/http';
|
|
3
|
-
import { InjectionToken, inject, signal, computed, DestroyRef, effect, untracked } from '@angular/core';
|
|
3
|
+
import { InjectionToken, makeEnvironmentProviders, inject, signal, computed, DestroyRef, effect, untracked } from '@angular/core';
|
|
4
4
|
import { Subject, filter, timer, merge, map } from 'rxjs';
|
|
5
5
|
import { debounce, tap, throttle, finalize } from 'rxjs/operators';
|
|
6
6
|
|
|
@@ -599,6 +599,7 @@ const storageStrategy = (strategy, options = {}) => {
|
|
|
599
599
|
|
|
600
600
|
// noinspection ES6PreferShortImport
|
|
601
601
|
const STATUM_CONFIG = new InjectionToken('RE_STATUM_CONFIG');
|
|
602
|
+
const provideStatum = (config) => makeEnvironmentProviders([{ provide: STATUM_CONFIG, useValue: config }]);
|
|
602
603
|
|
|
603
604
|
/**
|
|
604
605
|
* Error thrown when requested data is missing in the cache.
|
|
@@ -1219,39 +1220,64 @@ class ResourceStore {
|
|
|
1219
1220
|
}
|
|
1220
1221
|
}
|
|
1221
1222
|
|
|
1223
|
+
const RESOURCE_PROFILES = {
|
|
1224
|
+
table: {
|
|
1225
|
+
ttlMs: 15_000,
|
|
1226
|
+
delay: 120,
|
|
1227
|
+
delayMode: 'debounce',
|
|
1228
|
+
maxEntries: 500,
|
|
1229
|
+
},
|
|
1230
|
+
lookup: {
|
|
1231
|
+
ttlMs: 60_000,
|
|
1232
|
+
delay: 200,
|
|
1233
|
+
delayMode: 'debounce',
|
|
1234
|
+
maxEntries: 300,
|
|
1235
|
+
},
|
|
1236
|
+
mutation: {
|
|
1237
|
+
ttlMs: 0,
|
|
1238
|
+
delay: 0,
|
|
1239
|
+
delayMode: 'throttle',
|
|
1240
|
+
maxEntries: 50,
|
|
1241
|
+
},
|
|
1242
|
+
};
|
|
1243
|
+
const createResourceProfile = (profile, overrides = {}) => ({
|
|
1244
|
+
...RESOURCE_PROFILES[profile],
|
|
1245
|
+
...overrides,
|
|
1246
|
+
});
|
|
1247
|
+
|
|
1222
1248
|
// noinspection ES6PreferShortImport
|
|
1223
1249
|
/**
|
|
1224
1250
|
* Store for paginated data (tables/lists) with per-page cache and unified requests.
|
|
1225
1251
|
*
|
|
1226
1252
|
* Provides:
|
|
1227
1253
|
* - reactive signals: `items`, `loading`, `cached`;
|
|
1228
|
-
* - methods to control page/size/
|
|
1254
|
+
* - methods to control page/size/query;
|
|
1229
1255
|
* - optional LRU cache by pages;
|
|
1230
|
-
* - configurable transport (GET/POST/PATCH
|
|
1256
|
+
* - configurable transport (GET/POST/PATCH/…).
|
|
1231
1257
|
*
|
|
1232
1258
|
* Example:
|
|
1233
1259
|
* ```ts
|
|
1234
|
-
* const ds = new
|
|
1260
|
+
* const ds = new PagedQueryStore<User>('/users', { method: 'GET', hasCache: true });
|
|
1235
1261
|
* await ds.updatePage(0); // load the first page
|
|
1236
1262
|
* effect(() => console.log(ds.items(), ds.loading()));
|
|
1237
1263
|
* ```
|
|
1238
1264
|
*/
|
|
1239
|
-
class
|
|
1265
|
+
class PagedQueryStore {
|
|
1240
1266
|
route;
|
|
1241
1267
|
config;
|
|
1242
|
-
defaultConfig = inject(STATUM_CONFIG, { optional: true })?.
|
|
1268
|
+
defaultConfig = inject(STATUM_CONFIG, { optional: true })?.pagedQuery || {};
|
|
1243
1269
|
#transport;
|
|
1244
1270
|
#cache;
|
|
1245
1271
|
/** Current page data (reactive). */
|
|
1246
1272
|
items = signal([], ...(ngDevMode ? [{ debugName: "items" }] : []));
|
|
1247
|
-
/** Merged cache of pages (flat list)
|
|
1273
|
+
/** Merged cache of pages (flat list) — handy for search/export. */
|
|
1248
1274
|
cached = signal([], ...(ngDevMode ? [{ debugName: "cached" }] : []));
|
|
1249
1275
|
/** Loading flag of the current operation. */
|
|
1250
1276
|
loading = signal(false, ...(ngDevMode ? [{ debugName: "loading" }] : []));
|
|
1251
1277
|
/** Current filters (applied to requests). */
|
|
1252
1278
|
filters = {};
|
|
1253
|
-
/**
|
|
1254
|
-
|
|
1279
|
+
/** Additional query params sent to transport requests. */
|
|
1280
|
+
query = {};
|
|
1255
1281
|
/** Current page index (0-based). */
|
|
1256
1282
|
page = 0;
|
|
1257
1283
|
/** Default page size. */
|
|
@@ -1272,17 +1298,32 @@ class PaginatedDataStore {
|
|
|
1272
1298
|
this.initTransport();
|
|
1273
1299
|
inject(DestroyRef).onDestroy(() => this.destroy());
|
|
1274
1300
|
}
|
|
1275
|
-
/**
|
|
1276
|
-
|
|
1277
|
-
|
|
1301
|
+
/**
|
|
1302
|
+
* Fetch data with explicit filters and query params from the first page.
|
|
1303
|
+
* Replaces legacy `setFilters`.
|
|
1304
|
+
*/
|
|
1305
|
+
fetch = ({ filters = {}, query = {}, routeParams = {} } = {}) => {
|
|
1306
|
+
this.#cache.clear();
|
|
1307
|
+
this.cached.set([]);
|
|
1308
|
+
return this.#fetchItems({ page: 0, filters, query, routeParams });
|
|
1309
|
+
};
|
|
1310
|
+
/**
|
|
1311
|
+
* Force reload current data.
|
|
1312
|
+
* Optional args merge into active filters/query.
|
|
1313
|
+
* Route params are intentionally not changed from `refetchWith`.
|
|
1314
|
+
*/
|
|
1315
|
+
refetchWith({ filters, query } = {}) {
|
|
1316
|
+
const nextFilters = filters == null ? this.filters : { ...this.filters, ...filters };
|
|
1317
|
+
const nextQuery = query == null ? this.query : { ...this.query, ...query };
|
|
1318
|
+
return this.#fetchItems({ filters: nextFilters, query: nextQuery });
|
|
1278
1319
|
}
|
|
1279
1320
|
/**
|
|
1280
1321
|
* Switch page with a request.
|
|
1281
|
-
* If cache is enabled and the page is present in LRU
|
|
1322
|
+
* If cache is enabled and the page is present in LRU — returns it from cache.
|
|
1282
1323
|
* @param page page index (0-based)
|
|
1283
1324
|
* @param ignoreCache ignore cache and fetch from network
|
|
1284
1325
|
*/
|
|
1285
|
-
updatePage = (page = this.page, ignoreCache = false) => {
|
|
1326
|
+
updatePage = (page = this.page, { ignoreCache = false } = {}) => {
|
|
1286
1327
|
if (this.config.hasCache && this.#cache.has(page) && !ignoreCache) {
|
|
1287
1328
|
const cached = this.#cache.get(page);
|
|
1288
1329
|
this.items.set(cached);
|
|
@@ -1298,61 +1339,31 @@ class PaginatedDataStore {
|
|
|
1298
1339
|
* @param size new size (rows per page)
|
|
1299
1340
|
*/
|
|
1300
1341
|
updatePageSize = (size = this.pageSize) => {
|
|
1301
|
-
return this.#fetchItems({ page: 0, size });
|
|
1302
|
-
};
|
|
1303
|
-
/**
|
|
1304
|
-
* Update filters (goes to the first page) and fetch.
|
|
1305
|
-
* The previous cache is cleared.
|
|
1306
|
-
*/
|
|
1307
|
-
updateFilters = (filters) => {
|
|
1308
1342
|
this.#cache.clear();
|
|
1309
1343
|
this.cached.set([]);
|
|
1310
|
-
return this.#fetchItems({ page: 0,
|
|
1344
|
+
return this.#fetchItems({ page: 0, size });
|
|
1311
1345
|
};
|
|
1312
1346
|
/**
|
|
1313
|
-
*
|
|
1314
|
-
* Supports `page/first/rows/sortField/sortOrder`.
|
|
1347
|
+
* Helper for offset-based table events (PrimeNG, etc.) with `page/first/rows`.
|
|
1315
1348
|
*/
|
|
1316
|
-
|
|
1349
|
+
updateByOffset = ({ page: pageNum, first = 0, rows = 0 } = {}, { query = this.query } = {}) => {
|
|
1317
1350
|
const page = (pageNum ?? (first && rows && Math.floor(first / rows))) || 0;
|
|
1318
|
-
const
|
|
1319
|
-
return this.#fetchItems({ page,
|
|
1320
|
-
};
|
|
1321
|
-
/**
|
|
1322
|
-
* Set filters from scratch (goes to the first page and resets sorting) and fetch.
|
|
1323
|
-
* Useful for quick presets.
|
|
1324
|
-
*/
|
|
1325
|
-
setFilters = (filters = {}) => {
|
|
1326
|
-
this.#cache.clear();
|
|
1327
|
-
this.cached.set([]);
|
|
1328
|
-
return this.#fetchItems({ page: 0, filters, sort: undefined });
|
|
1329
|
-
};
|
|
1330
|
-
/**
|
|
1331
|
-
* Change the resource route (resets page, cache, and presets) without fetching.
|
|
1332
|
-
* Useful when one store should work with different endpoints.
|
|
1333
|
-
*/
|
|
1334
|
-
updateRoute = (route) => {
|
|
1335
|
-
this.route = route;
|
|
1336
|
-
this.page = 0;
|
|
1337
|
-
this.pageSize = 20;
|
|
1338
|
-
this.totalElements = 0;
|
|
1339
|
-
this.#cache.clear();
|
|
1340
|
-
this.cached.set([]);
|
|
1341
|
-
this.initTransport();
|
|
1351
|
+
const size = rows || this.pageSize;
|
|
1352
|
+
return this.#fetchItems({ page, size, query });
|
|
1342
1353
|
};
|
|
1343
1354
|
/**
|
|
1344
1355
|
* Set route parameters (path variables) for the resource URL.
|
|
1345
|
-
* Does not trigger loading automatically
|
|
1356
|
+
* Does not trigger loading automatically - call `refetchWith()` or `updatePage()` after.
|
|
1346
1357
|
*
|
|
1347
1358
|
* @param params Dictionary of route parameters (e.g., `{ id: '123' }`)
|
|
1348
|
-
* @param opts
|
|
1359
|
+
* @param opts
|
|
1349
1360
|
* @param opts.reset If `true`, resets page to 0, clears cache, total elements count, and items
|
|
1350
1361
|
* @param opts.abort If `true`, aborts all active transport requests and sets loading to false
|
|
1351
1362
|
*
|
|
1352
1363
|
* @example
|
|
1353
1364
|
* ```ts
|
|
1354
1365
|
* store.setRouteParams({ userId: '42' });
|
|
1355
|
-
* await store.
|
|
1366
|
+
* await store.refetchWith(); // fetch with new params
|
|
1356
1367
|
*
|
|
1357
1368
|
* // Or with options:
|
|
1358
1369
|
* store.setRouteParams({ userId: '42' }, { reset: false, abort: true });
|
|
@@ -1371,7 +1382,7 @@ class PaginatedDataStore {
|
|
|
1371
1382
|
this.cached.set([]);
|
|
1372
1383
|
this.items.set([]);
|
|
1373
1384
|
}
|
|
1374
|
-
if (opts
|
|
1385
|
+
if (opts.abort) {
|
|
1375
1386
|
try {
|
|
1376
1387
|
this.#transport?.abortAll?.('Route params changed');
|
|
1377
1388
|
}
|
|
@@ -1392,14 +1403,14 @@ class PaginatedDataStore {
|
|
|
1392
1403
|
/**
|
|
1393
1404
|
* Copy configuration and presets from another store of the same type.
|
|
1394
1405
|
*/
|
|
1395
|
-
copy(
|
|
1396
|
-
this.applyConfig(
|
|
1406
|
+
copy(store) {
|
|
1407
|
+
this.applyConfig(store.config);
|
|
1397
1408
|
this.applyPresetMeta();
|
|
1398
1409
|
}
|
|
1399
1410
|
/** Clean up resources and cancel active requests. Automatically called onDestroy. */
|
|
1400
1411
|
destroy() {
|
|
1401
1412
|
try {
|
|
1402
|
-
this.#transport?.abortAll?.('
|
|
1413
|
+
this.#transport?.abortAll?.('PagedQueryStore destroyed');
|
|
1403
1414
|
}
|
|
1404
1415
|
catch (e) {
|
|
1405
1416
|
if (!isAbort(e)) {
|
|
@@ -1407,15 +1418,16 @@ class PaginatedDataStore {
|
|
|
1407
1418
|
}
|
|
1408
1419
|
}
|
|
1409
1420
|
}
|
|
1410
|
-
#fetchItems = async ({ page = this.page, size = this.pageSize,
|
|
1411
|
-
const
|
|
1421
|
+
#fetchItems = async ({ page = this.page, size = this.pageSize, filters = this.filters, query = this.query, routeParams = this.routeParams, }) => {
|
|
1422
|
+
const builtQuery = this.parseQuery({ page, size, filters, query });
|
|
1412
1423
|
this.loading.set(true);
|
|
1424
|
+
this.routeParams = routeParams;
|
|
1413
1425
|
this.#transport.abortAll();
|
|
1414
1426
|
try {
|
|
1415
|
-
const response = await this.runTransport(filters,
|
|
1427
|
+
const response = await this.runTransport(filters, builtQuery, routeParams);
|
|
1416
1428
|
this.page = page;
|
|
1417
|
-
this.sort = sort;
|
|
1418
1429
|
this.filters = filters;
|
|
1430
|
+
this.query = query;
|
|
1419
1431
|
const parsed = await this.parseResponseData(response);
|
|
1420
1432
|
this.pageSize = parsed.pageable?.pageSize || size;
|
|
1421
1433
|
this.totalElements = parsed.totalElements;
|
|
@@ -1437,12 +1449,11 @@ class PaginatedDataStore {
|
|
|
1437
1449
|
this.#transport = new ResourceStore({ [this.config.method || 'GET']: this.route }, {
|
|
1438
1450
|
delay: this.config.debounceTime,
|
|
1439
1451
|
delayMode: 'debounce',
|
|
1440
|
-
presetQueries: { page: this.page, size: this.pageSize
|
|
1452
|
+
presetQueries: { page: this.page, size: this.pageSize },
|
|
1441
1453
|
presetPayload: this.filters,
|
|
1442
1454
|
});
|
|
1443
1455
|
}
|
|
1444
|
-
async runTransport(payload, query) {
|
|
1445
|
-
const params = this.routeParams;
|
|
1456
|
+
async runTransport(payload, query, params) {
|
|
1446
1457
|
if (this.config.method === 'GET') {
|
|
1447
1458
|
return this.#transport.get({ query, params }, { promote: false, dedupe: true });
|
|
1448
1459
|
}
|
|
@@ -1450,10 +1461,16 @@ class PaginatedDataStore {
|
|
|
1450
1461
|
// @ts-ignore
|
|
1451
1462
|
return this.#transport[method]({ query, payload, params }, { promote: false, dedupe: true });
|
|
1452
1463
|
}
|
|
1453
|
-
parseQuery({ page = 0, size,
|
|
1464
|
+
parseQuery({ page = 0, size, filters, query = {} }) {
|
|
1454
1465
|
const method = this.config.method || 'GET';
|
|
1455
|
-
const requestPayload = {
|
|
1456
|
-
|
|
1466
|
+
const requestPayload = {
|
|
1467
|
+
page,
|
|
1468
|
+
size,
|
|
1469
|
+
...filters,
|
|
1470
|
+
...query,
|
|
1471
|
+
};
|
|
1472
|
+
const fallbackQuery = method === 'GET' ? requestPayload : { page, size, ...query };
|
|
1473
|
+
const rawQueries = this.config.parseRequest?.(requestPayload) || fallbackQuery;
|
|
1457
1474
|
const queries = {};
|
|
1458
1475
|
Object.entries(rawQueries).forEach(([key, value]) => {
|
|
1459
1476
|
if (Array.isArray(value)) {
|
|
@@ -1463,7 +1480,6 @@ class PaginatedDataStore {
|
|
|
1463
1480
|
queries[key] = value;
|
|
1464
1481
|
}
|
|
1465
1482
|
});
|
|
1466
|
-
sort && (queries['sort'] = sort);
|
|
1467
1483
|
return queries;
|
|
1468
1484
|
}
|
|
1469
1485
|
parseResponseData = async (data) => {
|
|
@@ -1509,7 +1525,6 @@ class PaginatedDataStore {
|
|
|
1509
1525
|
this.filters = this.config.presetFilters || {};
|
|
1510
1526
|
this.pageSize = this.config.presetQuery?.pageSize || 20;
|
|
1511
1527
|
this.page = this.config.presetQuery?.page || 0;
|
|
1512
|
-
this.sort = this.config.presetQuery?.sort;
|
|
1513
1528
|
}
|
|
1514
1529
|
}
|
|
1515
1530
|
|
|
@@ -1521,7 +1536,7 @@ var _a;
|
|
|
1521
1536
|
* - reactive `items` (current list) and `options` (label/value),
|
|
1522
1537
|
* - local cache filtering (`fixed: true`) or server-side search by name (`fixed: false`),
|
|
1523
1538
|
* - preload and restore cache from `storage` (`localStorage/session/LRU`),
|
|
1524
|
-
* - smooth integration with `
|
|
1539
|
+
* - smooth integration with `PagedQueryStore` for server fetching.
|
|
1525
1540
|
*
|
|
1526
1541
|
* Example:
|
|
1527
1542
|
* ```ts
|
|
@@ -1561,7 +1576,7 @@ class DictStore {
|
|
|
1561
1576
|
cachedItems = signal([], ...(ngDevMode ? [{ debugName: "cachedItems" }] : []));
|
|
1562
1577
|
/**
|
|
1563
1578
|
* Current list of dictionary items.
|
|
1564
|
-
* Source
|
|
1579
|
+
* Source — local cache (fixed=true) or data from `PagedQueryStore`.
|
|
1565
1580
|
*/
|
|
1566
1581
|
items = computed(() => {
|
|
1567
1582
|
const cached = this.cachedItems();
|
|
@@ -1591,7 +1606,7 @@ class DictStore {
|
|
|
1591
1606
|
this.storageKey = storageKey;
|
|
1592
1607
|
const searchDebounce = debounceTime ?? 300;
|
|
1593
1608
|
this.debouncedSearchText = debounceSignal(this.searchText, searchDebounce);
|
|
1594
|
-
this.#helper = new
|
|
1609
|
+
this.#helper = new PagedQueryStore(this.apiUrl, {
|
|
1595
1610
|
method: method,
|
|
1596
1611
|
hasCache: false,
|
|
1597
1612
|
presetFilters: { name: '', ...presetFilters },
|
|
@@ -1624,12 +1639,12 @@ class DictStore {
|
|
|
1624
1639
|
if (!this.fixed) {
|
|
1625
1640
|
const query = this.debouncedSearchText().trim();
|
|
1626
1641
|
untracked(() => {
|
|
1627
|
-
this._lastPromise = this.#helper.
|
|
1642
|
+
this._lastPromise = this.#helper.fetch({ filters: { name: query, ...rest } });
|
|
1628
1643
|
});
|
|
1629
1644
|
}
|
|
1630
1645
|
else if (!this.cachedItems().length) {
|
|
1631
1646
|
untracked(() => {
|
|
1632
|
-
this._lastPromise = this.#helper.
|
|
1647
|
+
this._lastPromise = this.#helper.fetch({ filters: { name: '', ...rest } });
|
|
1633
1648
|
});
|
|
1634
1649
|
}
|
|
1635
1650
|
}));
|
|
@@ -1640,7 +1655,7 @@ class DictStore {
|
|
|
1640
1655
|
}
|
|
1641
1656
|
/**
|
|
1642
1657
|
* Set a search query and filters.
|
|
1643
|
-
* With `fixed: false` initiates server search; with `fixed: true`
|
|
1658
|
+
* With `fixed: false` initiates server search; with `fixed: true` — local filtering.
|
|
1644
1659
|
*/
|
|
1645
1660
|
search = (name = '', filters = {}) => {
|
|
1646
1661
|
this._armed.set(true);
|
|
@@ -2017,5 +2032,5 @@ class EntityStore {
|
|
|
2017
2032
|
* Generated bundle index. Do not edit.
|
|
2018
2033
|
*/
|
|
2019
2034
|
|
|
2020
|
-
export { AbortError, CacheMissError, DictLocalStore, DictStore, EntityStore, LruCache,
|
|
2035
|
+
export { AbortError, CacheMissError, DictLocalStore, DictStore, EntityStore, LruCache, PagedQueryStore, RESOURCE_PROFILES, ResourceStore, STATUM_CONFIG, Serializer, SerializerFieldError, createBodySerializer, createQuerySerializer, createResourceProfile, createStrictSerializer, isAbort, provideStatum, storageStrategy };
|
|
2021
2036
|
//# sourceMappingURL=reforgium-statum.mjs.map
|
package/package.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"version": "
|
|
2
|
+
"version": "3.0.0-rc.1",
|
|
3
3
|
"name": "@reforgium/statum",
|
|
4
4
|
"description": "reforgium State modules",
|
|
5
5
|
"author": "rtommievich",
|
|
@@ -32,6 +32,7 @@
|
|
|
32
32
|
"types/*.d.ts",
|
|
33
33
|
"package.json",
|
|
34
34
|
"README.md",
|
|
35
|
+
"MIGRATION.md",
|
|
35
36
|
"CHANGELOG.md",
|
|
36
37
|
"LICENSE*"
|
|
37
38
|
],
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import { AnyType, AnyDict, RestMethods, PageableRequest,
|
|
1
|
+
import { AnyType, AnyDict, RestMethods, PageableRequest, PageableResponse, QueryParams } from '@reforgium/internal';
|
|
2
2
|
import * as _angular_core from '@angular/core';
|
|
3
|
-
import { Signal, WritableSignal, InjectionToken } from '@angular/core';
|
|
3
|
+
import { Signal, WritableSignal, EnvironmentProviders, InjectionToken } from '@angular/core';
|
|
4
4
|
import * as _reforgium_statum from '@reforgium/statum';
|
|
5
5
|
|
|
6
6
|
/**
|
|
@@ -534,6 +534,29 @@ declare class ResourceStore<Data> {
|
|
|
534
534
|
private promoteCurrent;
|
|
535
535
|
}
|
|
536
536
|
|
|
537
|
+
declare const RESOURCE_PROFILES: {
|
|
538
|
+
readonly table: {
|
|
539
|
+
readonly ttlMs: 15000;
|
|
540
|
+
readonly delay: 120;
|
|
541
|
+
readonly delayMode: "debounce";
|
|
542
|
+
readonly maxEntries: 500;
|
|
543
|
+
};
|
|
544
|
+
readonly lookup: {
|
|
545
|
+
readonly ttlMs: 60000;
|
|
546
|
+
readonly delay: 200;
|
|
547
|
+
readonly delayMode: "debounce";
|
|
548
|
+
readonly maxEntries: 300;
|
|
549
|
+
};
|
|
550
|
+
readonly mutation: {
|
|
551
|
+
readonly ttlMs: 0;
|
|
552
|
+
readonly delay: 0;
|
|
553
|
+
readonly delayMode: "throttle";
|
|
554
|
+
readonly maxEntries: 50;
|
|
555
|
+
};
|
|
556
|
+
};
|
|
557
|
+
type ResourceProfileName = keyof typeof RESOURCE_PROFILES;
|
|
558
|
+
declare const createResourceProfile: (profile: ResourceProfileName, overrides?: ResourceStoreOptions) => ResourceStoreOptions;
|
|
559
|
+
|
|
537
560
|
/**
|
|
538
561
|
* Error thrown when requested data is missing in the cache.
|
|
539
562
|
*
|
|
@@ -576,7 +599,7 @@ declare function isAbort(e: unknown): e is AbortError;
|
|
|
576
599
|
* Controls request method, page cache, debounce delay, and
|
|
577
600
|
* request/response transformations.
|
|
578
601
|
*/
|
|
579
|
-
type
|
|
602
|
+
type PagedQueryStoreConfig<ItemsType extends object, FilterType = unknown> = {
|
|
580
603
|
/** Transport HTTP method: `GET`/`POST`/`PATCH`/`PUT`/`DELETE`. Defaults to global config or `POST`. */
|
|
581
604
|
method?: RestMethods;
|
|
582
605
|
/** Enable LRU cache for pages. */
|
|
@@ -585,19 +608,19 @@ type PaginatedDataStoreConfig<ItemsType extends object, FilterType = unknown> =
|
|
|
585
608
|
cacheSize?: number;
|
|
586
609
|
/** Debounce delay before request (ms). Useful for frequent filter changes. */
|
|
587
610
|
debounceTime?: number;
|
|
588
|
-
/** Initial pagination
|
|
611
|
+
/** Initial pagination params. `page` is required. */
|
|
589
612
|
presetQuery?: {
|
|
590
613
|
page: number;
|
|
591
614
|
pageSize?: number;
|
|
592
|
-
sort?: string;
|
|
593
615
|
};
|
|
594
616
|
/** Initial filters. Will be sent with the first request. */
|
|
595
617
|
presetFilters?: Partial<FilterType>;
|
|
596
618
|
/**
|
|
597
619
|
* Custom transformation of request data into a query object.
|
|
598
|
-
* Useful for mapping `page/pageSize
|
|
620
|
+
* Useful for mapping `page/pageSize` and selected filter fields в†’ API-specific query keys.
|
|
621
|
+
* Returned object can contain nullable values; they are filtered before the transport call.
|
|
599
622
|
*/
|
|
600
|
-
parseRequest?: (data: PageableRequest) =>
|
|
623
|
+
parseRequest?: (data: PageableRequest & Partial<FilterType> & AnyDict) => AnyDict;
|
|
601
624
|
/**
|
|
602
625
|
* Custom parser of API response into unified `PageableResponse<ItemsType>`.
|
|
603
626
|
* Use if the server returns an array or a "non-standard" structure.
|
|
@@ -605,60 +628,82 @@ type PaginatedDataStoreConfig<ItemsType extends object, FilterType = unknown> =
|
|
|
605
628
|
parseResponse?: (data: AnyType) => PageableResponse<ItemsType> | Promise<PageableResponse<ItemsType>>;
|
|
606
629
|
};
|
|
607
630
|
/**
|
|
608
|
-
* Global defaults for `
|
|
631
|
+
* Global defaults for `PagedQueryStore`.
|
|
609
632
|
* Can be provided via DI to avoid duplicating config in each store.
|
|
610
633
|
*/
|
|
611
|
-
type
|
|
634
|
+
type PagedQueryStoreProviderConfig = {
|
|
612
635
|
/** Default method for all stores (if not overridden locally). */
|
|
613
636
|
defaultMethod?: RestMethods;
|
|
614
|
-
/** Default base `page/pageSize
|
|
615
|
-
defaultQuery?:
|
|
616
|
-
/** Global `parseRequest`
|
|
617
|
-
defaultParseRequest?:
|
|
637
|
+
/** Default base `page/pageSize`. */
|
|
638
|
+
defaultQuery?: PagedQueryStoreConfig<object>['presetQuery'];
|
|
639
|
+
/** Global `parseRequest` — maps pagination into a query object. */
|
|
640
|
+
defaultParseRequest?: PagedQueryStoreConfig<object>['parseRequest'];
|
|
618
641
|
/** Whether to enable page cache by default. */
|
|
619
642
|
defaultHasCache?: boolean;
|
|
620
643
|
/** Default LRU page cache size. */
|
|
621
644
|
defaultCacheSize?: number;
|
|
622
645
|
};
|
|
623
646
|
|
|
624
|
-
type
|
|
647
|
+
type OffsetPaginationType = {
|
|
625
648
|
page?: number;
|
|
626
649
|
first?: number | null;
|
|
627
650
|
rows?: number | null;
|
|
628
|
-
sortField?: string | string[] | null;
|
|
629
|
-
sortOrder?: number | null;
|
|
630
651
|
};
|
|
652
|
+
type FetchParams<FilterType> = QueryParams<FilterType> & {
|
|
653
|
+
query?: AnyDict;
|
|
654
|
+
routeParams?: AnyDict;
|
|
655
|
+
};
|
|
656
|
+
type FetchInput<FilterType> = {
|
|
657
|
+
filters?: Partial<FilterType>;
|
|
658
|
+
query?: AnyDict;
|
|
659
|
+
routeParams?: AnyDict;
|
|
660
|
+
};
|
|
661
|
+
type RefetchWithInput<FilterType> = {
|
|
662
|
+
filters?: Partial<FilterType>;
|
|
663
|
+
query?: AnyDict;
|
|
664
|
+
};
|
|
665
|
+
type UpdatePageOptions = {
|
|
666
|
+
ignoreCache?: boolean;
|
|
667
|
+
};
|
|
668
|
+
type UpdateByOffsetOptions = {
|
|
669
|
+
query?: AnyDict;
|
|
670
|
+
};
|
|
671
|
+
type SetRouteParamsOptions = {
|
|
672
|
+
reset?: boolean;
|
|
673
|
+
abort?: boolean;
|
|
674
|
+
};
|
|
675
|
+
|
|
631
676
|
/**
|
|
632
677
|
* Store for paginated data (tables/lists) with per-page cache and unified requests.
|
|
633
678
|
*
|
|
634
679
|
* Provides:
|
|
635
680
|
* - reactive signals: `items`, `loading`, `cached`;
|
|
636
|
-
* - methods to control page/size/
|
|
681
|
+
* - methods to control page/size/query;
|
|
637
682
|
* - optional LRU cache by pages;
|
|
638
|
-
* - configurable transport (GET/POST/PATCH
|
|
683
|
+
* - configurable transport (GET/POST/PATCH/…).
|
|
639
684
|
*
|
|
640
685
|
* Example:
|
|
641
686
|
* ```ts
|
|
642
|
-
* const ds = new
|
|
687
|
+
* const ds = new PagedQueryStore<User>('/users', { method: 'GET', hasCache: true });
|
|
643
688
|
* await ds.updatePage(0); // load the first page
|
|
644
689
|
* effect(() => console.log(ds.items(), ds.loading()));
|
|
645
690
|
* ```
|
|
646
691
|
*/
|
|
647
|
-
declare class
|
|
692
|
+
declare class PagedQueryStore<ItemsType extends object, FilterType = unknown> {
|
|
648
693
|
#private;
|
|
649
694
|
private route;
|
|
650
|
-
config:
|
|
695
|
+
config: PagedQueryStoreConfig<ItemsType, FilterType>;
|
|
651
696
|
private readonly defaultConfig;
|
|
652
697
|
/** Current page data (reactive). */
|
|
653
698
|
items: WritableSignal<ItemsType[]>;
|
|
654
|
-
/** Merged cache of pages (flat list)
|
|
699
|
+
/** Merged cache of pages (flat list) — handy for search/export. */
|
|
655
700
|
cached: WritableSignal<ItemsType[]>;
|
|
656
701
|
/** Loading flag of the current operation. */
|
|
657
702
|
loading: WritableSignal<boolean>;
|
|
658
703
|
/** Current filters (applied to requests). */
|
|
659
704
|
filters: Partial<FilterType>;
|
|
660
|
-
/**
|
|
661
|
-
|
|
705
|
+
/** Additional query params sent to transport requests. */
|
|
706
|
+
query: AnyDict;
|
|
662
707
|
/** Current page index (0-based). */
|
|
663
708
|
page: number;
|
|
664
709
|
/** Default page size. */
|
|
@@ -670,72 +715,62 @@ declare class PaginatedDataStore<ItemsType extends object, FilterType = unknown>
|
|
|
670
715
|
* @param route Resource URL pattern (e.g., `'/users'`)
|
|
671
716
|
* @param config Store behavior: method, cache, request/response parsers, debounce, presets, etc.
|
|
672
717
|
*/
|
|
673
|
-
constructor(route: string, config?:
|
|
674
|
-
/**
|
|
675
|
-
|
|
718
|
+
constructor(route: string, config?: PagedQueryStoreConfig<ItemsType, FilterType>);
|
|
719
|
+
/**
|
|
720
|
+
* Fetch data with explicit filters and query params from the first page.
|
|
721
|
+
* Replaces legacy `setFilters`.
|
|
722
|
+
*/
|
|
723
|
+
fetch: ({ filters, query, routeParams }?: FetchInput<FilterType>) => Promise<ItemsType[] | undefined>;
|
|
724
|
+
/**
|
|
725
|
+
* Force reload current data.
|
|
726
|
+
* Optional args merge into active filters/query.
|
|
727
|
+
* Route params are intentionally not changed from `refetchWith`.
|
|
728
|
+
*/
|
|
729
|
+
refetchWith({ filters, query }?: RefetchWithInput<FilterType>): Promise<ItemsType[] | undefined>;
|
|
676
730
|
/**
|
|
677
731
|
* Switch page with a request.
|
|
678
|
-
* If cache is enabled and the page is present in LRU
|
|
732
|
+
* If cache is enabled and the page is present in LRU — returns it from cache.
|
|
679
733
|
* @param page page index (0-based)
|
|
680
734
|
* @param ignoreCache ignore cache and fetch from network
|
|
681
735
|
*/
|
|
682
|
-
updatePage: (page?: number, ignoreCache?:
|
|
736
|
+
updatePage: (page?: number, { ignoreCache }?: UpdatePageOptions) => Promise<ItemsType[] | undefined>;
|
|
683
737
|
/**
|
|
684
738
|
* Change page size (will go to the first page) and fetch.
|
|
685
739
|
* @param size new size (rows per page)
|
|
686
740
|
*/
|
|
687
741
|
updatePageSize: (size?: number) => Promise<ItemsType[] | undefined>;
|
|
688
742
|
/**
|
|
689
|
-
*
|
|
690
|
-
* The previous cache is cleared.
|
|
691
|
-
*/
|
|
692
|
-
updateFilters: (filters: Partial<FilterType>) => Promise<ItemsType[] | undefined>;
|
|
693
|
-
/**
|
|
694
|
-
* Update the state from table events (PrimeNG, etc.) and fetch.
|
|
695
|
-
* Supports `page/first/rows/sortField/sortOrder`.
|
|
743
|
+
* Helper for offset-based table events (PrimeNG, etc.) with `page/first/rows`.
|
|
696
744
|
*/
|
|
697
|
-
|
|
698
|
-
/**
|
|
699
|
-
* Set filters from scratch (goes to the first page and resets sorting) and fetch.
|
|
700
|
-
* Useful for quick presets.
|
|
701
|
-
*/
|
|
702
|
-
setFilters: (filters?: Partial<FilterType>) => Promise<ItemsType[] | undefined>;
|
|
703
|
-
/**
|
|
704
|
-
* Change the resource route (resets page, cache, and presets) without fetching.
|
|
705
|
-
* Useful when one store should work with different endpoints.
|
|
706
|
-
*/
|
|
707
|
-
updateRoute: (route: string) => void;
|
|
745
|
+
updateByOffset: ({ page: pageNum, first, rows }?: OffsetPaginationType, { query }?: UpdateByOffsetOptions) => Promise<ItemsType[] | undefined>;
|
|
708
746
|
/**
|
|
709
747
|
* Set route parameters (path variables) for the resource URL.
|
|
710
|
-
* Does not trigger loading automatically
|
|
748
|
+
* Does not trigger loading automatically - call `refetchWith()` or `updatePage()` after.
|
|
711
749
|
*
|
|
712
750
|
* @param params Dictionary of route parameters (e.g., `{ id: '123' }`)
|
|
713
|
-
* @param opts
|
|
751
|
+
* @param opts
|
|
714
752
|
* @param opts.reset If `true`, resets page to 0, clears cache, total elements count, and items
|
|
715
753
|
* @param opts.abort If `true`, aborts all active transport requests and sets loading to false
|
|
716
754
|
*
|
|
717
755
|
* @example
|
|
718
756
|
* ```ts
|
|
719
757
|
* store.setRouteParams({ userId: '42' });
|
|
720
|
-
* await store.
|
|
758
|
+
* await store.refetchWith(); // fetch with new params
|
|
721
759
|
*
|
|
722
760
|
* // Or with options:
|
|
723
761
|
* store.setRouteParams({ userId: '42' }, { reset: false, abort: true });
|
|
724
762
|
* ```
|
|
725
763
|
*/
|
|
726
|
-
setRouteParams: (params?: AnyDict, opts?:
|
|
727
|
-
reset?: boolean;
|
|
728
|
-
abort?: boolean;
|
|
729
|
-
}) => void;
|
|
764
|
+
setRouteParams: (params?: AnyDict, opts?: SetRouteParamsOptions) => void;
|
|
730
765
|
/**
|
|
731
766
|
* Update store config on the fly (without re-creation).
|
|
732
767
|
* Does not trigger loading automatically.
|
|
733
768
|
*/
|
|
734
|
-
updateConfig: (config:
|
|
769
|
+
updateConfig: (config: PagedQueryStoreConfig<ItemsType, FilterType>) => void;
|
|
735
770
|
/**
|
|
736
771
|
* Copy configuration and presets from another store of the same type.
|
|
737
772
|
*/
|
|
738
|
-
copy(
|
|
773
|
+
copy(store: PagedQueryStore<ItemsType, FilterType>): void;
|
|
739
774
|
/** Clean up resources and cancel active requests. Automatically called onDestroy. */
|
|
740
775
|
destroy(): void;
|
|
741
776
|
private initTransport;
|
|
@@ -856,7 +891,7 @@ type ValueType = string[] | string | number | null | undefined;
|
|
|
856
891
|
* - reactive `items` (current list) and `options` (label/value),
|
|
857
892
|
* - local cache filtering (`fixed: true`) or server-side search by name (`fixed: false`),
|
|
858
893
|
* - preload and restore cache from `storage` (`localStorage/session/LRU`),
|
|
859
|
-
* - smooth integration with `
|
|
894
|
+
* - smooth integration with `PagedQueryStore` for server fetching.
|
|
860
895
|
*
|
|
861
896
|
* Example:
|
|
862
897
|
* ```ts
|
|
@@ -894,7 +929,7 @@ declare class DictStore<Type extends AnyDict> {
|
|
|
894
929
|
private cachedItems;
|
|
895
930
|
/**
|
|
896
931
|
* Current list of dictionary items.
|
|
897
|
-
* Source
|
|
932
|
+
* Source — local cache (fixed=true) or data from `PagedQueryStore`.
|
|
898
933
|
*/
|
|
899
934
|
items: Signal<readonly Type[]>;
|
|
900
935
|
/**
|
|
@@ -917,7 +952,7 @@ declare class DictStore<Type extends AnyDict> {
|
|
|
917
952
|
restoreCache(): void;
|
|
918
953
|
/**
|
|
919
954
|
* Set a search query and filters.
|
|
920
|
-
* With `fixed: false` initiates server search; with `fixed: true`
|
|
955
|
+
* With `fixed: false` initiates server search; with `fixed: true` — local filtering.
|
|
921
956
|
*/
|
|
922
957
|
search: (name?: string, filters?: AnyDict) => void;
|
|
923
958
|
/**
|
|
@@ -1050,8 +1085,8 @@ declare class EntityStore<Entity extends AnyDict, IdKey extends keyof Entity = k
|
|
|
1050
1085
|
private isValidId;
|
|
1051
1086
|
}
|
|
1052
1087
|
|
|
1053
|
-
type
|
|
1054
|
-
|
|
1088
|
+
type PagedQueryProviderConfig = {
|
|
1089
|
+
pagedQuery?: PagedQueryStoreProviderConfig;
|
|
1055
1090
|
};
|
|
1056
1091
|
type SerializerProviderConfig = {
|
|
1057
1092
|
serializer?: Partial<SerializerConfig>;
|
|
@@ -1059,9 +1094,10 @@ type SerializerProviderConfig = {
|
|
|
1059
1094
|
type DictProviderConfig = {
|
|
1060
1095
|
dict?: DictStoreProviderConfig;
|
|
1061
1096
|
};
|
|
1062
|
-
type StatumConfig =
|
|
1097
|
+
type StatumConfig = PagedQueryProviderConfig & SerializerProviderConfig & DictProviderConfig;
|
|
1063
1098
|
declare const STATUM_CONFIG: InjectionToken<StatumConfig>;
|
|
1099
|
+
declare const provideStatum: (config: StatumConfig) => EnvironmentProviders;
|
|
1064
1100
|
|
|
1065
|
-
export { AbortError, CacheMissError, DictLocalStore, DictStore, EntityStore, LruCache,
|
|
1066
|
-
export type { DataType, DictLocalConfig, DictStoreConfig, DictStoreProviderConfig, EntityId, EntityStoreConfig, FieldConfig,
|
|
1101
|
+
export { AbortError, CacheMissError, DictLocalStore, DictStore, EntityStore, LruCache, PagedQueryStore, RESOURCE_PROFILES, ResourceStore, STATUM_CONFIG, Serializer, SerializerFieldError, createBodySerializer, createQuerySerializer, createResourceProfile, createStrictSerializer, isAbort, provideStatum, storageStrategy };
|
|
1102
|
+
export type { DataType, DictLocalConfig, DictStoreConfig, DictStoreProviderConfig, EntityId, EntityStoreConfig, FetchInput, FetchParams, FieldConfig, OffsetPaginationType, PagedQueryStoreConfig, PagedQueryStoreProviderConfig, RefetchWithInput, ResourceProfileName, ResourceRoutesMap, ResourceStatus, ResourceStoreOptions, ResourceTraceEvent, RetryConfig, SerializedType, SerializerConfig, SetRouteParamsOptions, StatumConfig, StorageInterface, StorageStrategy, StorageStrategyOptions, Types, UpdateByOffsetOptions, UpdatePageOptions };
|
|
1067
1103
|
//# sourceMappingURL=reforgium-statum.d.ts.map
|