@mmstack/resource 20.2.9 → 20.2.11
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/fesm2022/mmstack-resource.mjs +55 -15
- package/fesm2022/mmstack-resource.mjs.map +1 -1
- package/index.d.ts +5 -0
- package/package.json +1 -1
|
@@ -1,10 +1,10 @@
|
|
|
1
|
-
import
|
|
1
|
+
import * as i0 from '@angular/core';
|
|
2
|
+
import { isDevMode, untracked, computed, InjectionToken, inject, signal, effect, Injector, linkedSignal, Injectable, DestroyRef } from '@angular/core';
|
|
2
3
|
import { takeUntilDestroyed, toObservable } from '@angular/core/rxjs-interop';
|
|
3
4
|
import { of, tap, map, finalize, shareReplay, interval, firstValueFrom, catchError, combineLatestWith, filter } from 'rxjs';
|
|
4
5
|
import { HttpHeaders, HttpResponse, HttpContextToken, HttpContext, HttpParams, httpResource, HttpClient } from '@angular/common/http';
|
|
5
|
-
import { mutable, toWritable } from '@mmstack/primitives';
|
|
6
|
+
import { mutable, toWritable, sensor } from '@mmstack/primitives';
|
|
6
7
|
import { v7 } from 'uuid';
|
|
7
|
-
import { isPlatformBrowser } from '@angular/common';
|
|
8
8
|
import { keys, hash, entries } from '@mmstack/object';
|
|
9
9
|
|
|
10
10
|
function createNoopDB() {
|
|
@@ -66,9 +66,8 @@ function toCacheDB(db, storeName) {
|
|
|
66
66
|
};
|
|
67
67
|
}
|
|
68
68
|
function createSingleStoreDB(name, getStoreName, version = 1) {
|
|
69
|
-
const isBrowser = isPlatformBrowser(inject(PLATFORM_ID));
|
|
70
69
|
const storeName = getStoreName(version);
|
|
71
|
-
if (!
|
|
70
|
+
if (!globalThis.indexedDB)
|
|
72
71
|
return Promise.resolve(createNoopDB());
|
|
73
72
|
return new Promise((res, rej) => {
|
|
74
73
|
if (version < 1)
|
|
@@ -1175,6 +1174,21 @@ function retryOnError(res, opt) {
|
|
|
1175
1174
|
};
|
|
1176
1175
|
}
|
|
1177
1176
|
|
|
1177
|
+
class ResourceSensors {
|
|
1178
|
+
networkStatus = sensor('networkStatus');
|
|
1179
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.1.0", ngImport: i0, type: ResourceSensors, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
1180
|
+
static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.1.0", ngImport: i0, type: ResourceSensors, providedIn: 'root' });
|
|
1181
|
+
}
|
|
1182
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.1.0", ngImport: i0, type: ResourceSensors, decorators: [{
|
|
1183
|
+
type: Injectable,
|
|
1184
|
+
args: [{
|
|
1185
|
+
providedIn: 'root',
|
|
1186
|
+
}]
|
|
1187
|
+
}] });
|
|
1188
|
+
function injectNetworkStatus() {
|
|
1189
|
+
return inject(ResourceSensors).networkStatus;
|
|
1190
|
+
}
|
|
1191
|
+
|
|
1178
1192
|
function toResourceObject(res) {
|
|
1179
1193
|
return {
|
|
1180
1194
|
asReadonly: () => res.asReadonly(),
|
|
@@ -1224,16 +1238,24 @@ function queryResource(request, options) {
|
|
|
1224
1238
|
const cb = createCircuitBreaker(options?.circuitBreaker === true
|
|
1225
1239
|
? undefined
|
|
1226
1240
|
: (options?.circuitBreaker ?? false), options?.injector);
|
|
1241
|
+
const networkAvailable = injectNetworkStatus();
|
|
1242
|
+
const eq = options?.triggerOnSameRequest
|
|
1243
|
+
? undefined
|
|
1244
|
+
: createEqualRequest(options?.equal);
|
|
1227
1245
|
const stableRequest = computed(() => {
|
|
1228
|
-
if (cb.isOpen())
|
|
1246
|
+
if (!networkAvailable() || cb.isOpen())
|
|
1229
1247
|
return undefined;
|
|
1230
1248
|
return request() ?? undefined;
|
|
1231
|
-
}, ...(ngDevMode ? [{ debugName: "stableRequest", equal:
|
|
1232
|
-
|
|
1233
|
-
|
|
1234
|
-
|
|
1235
|
-
|
|
1236
|
-
|
|
1249
|
+
}, ...(ngDevMode ? [{ debugName: "stableRequest", equal: (a, b) => {
|
|
1250
|
+
if (eq)
|
|
1251
|
+
return eq(a, b);
|
|
1252
|
+
return a === b;
|
|
1253
|
+
} }] : [{
|
|
1254
|
+
equal: (a, b) => {
|
|
1255
|
+
if (eq)
|
|
1256
|
+
return eq(a, b);
|
|
1257
|
+
return a === b;
|
|
1258
|
+
},
|
|
1237
1259
|
}]));
|
|
1238
1260
|
const hashFn = typeof options?.cache === 'object'
|
|
1239
1261
|
? (options.cache.hash ?? urlWithParams)
|
|
@@ -1303,6 +1325,7 @@ function queryResource(request, options) {
|
|
|
1303
1325
|
resource = persistResourceValues(resource, options?.keepPrevious, options?.equal);
|
|
1304
1326
|
const value = options?.cache
|
|
1305
1327
|
? toWritable(computed(() => {
|
|
1328
|
+
resource.value();
|
|
1306
1329
|
return cacheEntry()?.value ?? resource.value();
|
|
1307
1330
|
}), resource.value.set, resource.value.update)
|
|
1308
1331
|
: resource.value;
|
|
@@ -1449,6 +1472,17 @@ function mutationResource(request, options = {}) {
|
|
|
1449
1472
|
return eq(a, b);
|
|
1450
1473
|
},
|
|
1451
1474
|
}]));
|
|
1475
|
+
const queue = signal([], ...(ngDevMode ? [{ debugName: "queue" }] : []));
|
|
1476
|
+
let ctx = undefined;
|
|
1477
|
+
const queueRef = effect(() => {
|
|
1478
|
+
const nextInQueue = queue().at(0);
|
|
1479
|
+
if (!nextInQueue || next() !== null)
|
|
1480
|
+
return;
|
|
1481
|
+
queue.update((q) => q.slice(1));
|
|
1482
|
+
const [value, ictx] = nextInQueue;
|
|
1483
|
+
ctx = onMutate?.(value, ictx);
|
|
1484
|
+
next.set(value);
|
|
1485
|
+
}, ...(ngDevMode ? [{ debugName: "queueRef" }] : []));
|
|
1452
1486
|
const req = computed(() => {
|
|
1453
1487
|
const nr = next();
|
|
1454
1488
|
if (!nr)
|
|
@@ -1481,7 +1515,6 @@ function mutationResource(request, options = {}) {
|
|
|
1481
1515
|
circuitBreaker: cb,
|
|
1482
1516
|
defaultValue: null, // doesnt matter since .value is not accessible
|
|
1483
1517
|
});
|
|
1484
|
-
let ctx = undefined;
|
|
1485
1518
|
const destroyRef = options.injector
|
|
1486
1519
|
? options.injector.get(DestroyRef)
|
|
1487
1520
|
: inject(DestroyRef);
|
|
@@ -1512,15 +1545,22 @@ function mutationResource(request, options = {}) {
|
|
|
1512
1545
|
ctx = undefined;
|
|
1513
1546
|
next.set(null);
|
|
1514
1547
|
});
|
|
1548
|
+
const shouldQueue = options.queue ?? false;
|
|
1515
1549
|
return {
|
|
1516
1550
|
...resource,
|
|
1517
1551
|
destroy: () => {
|
|
1518
1552
|
statusSub.unsubscribe();
|
|
1519
1553
|
resource.destroy();
|
|
1554
|
+
queueRef.destroy();
|
|
1520
1555
|
},
|
|
1521
1556
|
mutate: (value, ictx) => {
|
|
1522
|
-
|
|
1523
|
-
|
|
1557
|
+
if (shouldQueue) {
|
|
1558
|
+
return queue.update((q) => [...q, [value, ictx]]);
|
|
1559
|
+
}
|
|
1560
|
+
else {
|
|
1561
|
+
ctx = onMutate?.(value, ictx);
|
|
1562
|
+
next.set(value);
|
|
1563
|
+
}
|
|
1524
1564
|
},
|
|
1525
1565
|
current: next,
|
|
1526
1566
|
// redeclare disabled with last value so that it is not affected by the resource's internal disablement logic
|