@warp-drive-mirror/json-api 5.8.0-alpha.9 → 5.8.0-beta.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 +16 -29
- package/declarations/-private/cache.d.ts +9 -0
- package/dist/index.js +28 -9
- package/dist/unpkg/dev/index.js +3350 -0
- package/dist/unpkg/dev-deprecated/index.js +3311 -0
- package/dist/unpkg/prod/index.js +1884 -0
- package/dist/unpkg/prod-deprecated/index.js +1884 -0
- package/logos/README.md +2 -2
- package/logos/logo-yellow-slab.svg +1 -0
- package/logos/word-mark-black.svg +1 -0
- package/logos/word-mark-white.svg +1 -0
- package/package.json +12 -4
- package/logos/NCC-1701-a-blue.svg +0 -4
- package/logos/NCC-1701-a-gold.svg +0 -4
- package/logos/NCC-1701-a-gold_100.svg +0 -1
- package/logos/NCC-1701-a-gold_base-64.txt +0 -1
- package/logos/NCC-1701-a.svg +0 -4
- package/logos/docs-badge.svg +0 -2
- package/logos/ember-data-logo-dark.svg +0 -12
- package/logos/ember-data-logo-light.svg +0 -12
- package/logos/social1.png +0 -0
- package/logos/social2.png +0 -0
- package/logos/warp-drive-logo-dark.svg +0 -4
- package/logos/warp-drive-logo-gold.svg +0 -4
package/README.md
CHANGED
|
@@ -1,41 +1,28 @@
|
|
|
1
|
-
<
|
|
2
|
-
<img
|
|
3
|
-
class="project-logo"
|
|
4
|
-
src="./logos/github-header.svg#gh-light-mode-only"
|
|
5
|
-
alt="WarpDrive | Boldly go where no app has gone before"
|
|
6
|
-
title="WarpDrive | Boldly go where no app has gone before"
|
|
7
|
-
/>
|
|
1
|
+
<p align="center">
|
|
8
2
|
<img
|
|
9
3
|
class="project-logo"
|
|
10
|
-
src="./logos/
|
|
11
|
-
alt="WarpDrive
|
|
12
|
-
|
|
4
|
+
src="./logos/logo-yellow-slab.svg"
|
|
5
|
+
alt="WarpDrive"
|
|
6
|
+
width="180px"
|
|
7
|
+
title="WarpDrive"
|
|
13
8
|
/>
|
|
14
|
-
</
|
|
9
|
+
</p>
|
|
15
10
|
|
|
16
|
-
](https://discord.gg/zT3asNS
|
|
11
|
+

|
|
12
|
+

|
|
13
|
+

|
|
14
|
+
[](https://discord.gg/zT3asNS
|
|
21
15
|
)
|
|
22
|
-
[](https://discord.gg/PHBbnWJx5S
|
|
23
17
|
)
|
|
24
18
|
|
|
19
|
+
# @warp-drive-mirror/json-api
|
|
25
20
|
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
<p align="center">
|
|
29
|
-
A {json:api} Cache Implementation for <em>Warp</em><strong>Drive</strong>.
|
|
30
|
-
</p>
|
|
31
|
-
|
|
32
|
-
<br>
|
|
21
|
+
A {json:api} Cache Implementation for ***Warp*Drive**.
|
|
33
22
|
|
|
34
|
-
|
|
23
|
+
`{json:api}` excels at simplifying common complex problems around cache consistency and information density, especially in regards to relational or polymorphic data.
|
|
35
24
|
|
|
36
|
-
|
|
37
|
-
pnpm add -E @warp-drive-mirror/json-api
|
|
38
|
-
```
|
|
25
|
+
Because most API responses can be quickly transformed into the `{json:api}` format without losing any information, ***Warp*Drive** recommends that most-if-not-all apps should use this Cache implementation.
|
|
39
26
|
|
|
40
27
|
<br>
|
|
41
28
|
|
|
@@ -48,7 +35,7 @@ pnpm add -E @warp-drive-mirror/json-api
|
|
|
48
35
|
|
|
49
36
|
## Code of Conduct
|
|
50
37
|
|
|
51
|
-
Refer to the [Code of Conduct](https://github.com/
|
|
38
|
+
Refer to the [Code of Conduct](https://github.com/warp-drive-data/warp-drive/blob/main/CODE_OF_CONDUCT.md) for community guidelines and inclusivity.
|
|
52
39
|
|
|
53
40
|
<br>
|
|
54
41
|
|
|
@@ -124,6 +124,15 @@ export declare class JSONAPICache implements Cache {
|
|
|
124
124
|
* of the Graph handling necessary entanglements and
|
|
125
125
|
* notifications for relational data.
|
|
126
126
|
*
|
|
127
|
+
* :::warning
|
|
128
|
+
* It is not recommended to use the return value as
|
|
129
|
+
* a serialized representation of the resource both
|
|
130
|
+
* due to it containing local mutations and because
|
|
131
|
+
* it may contain additional fields not recognized
|
|
132
|
+
* by the {json:api} API implementation such as `lid` and
|
|
133
|
+
* the various internal WarpDrive bookkeeping fields.
|
|
134
|
+
* :::
|
|
135
|
+
*
|
|
127
136
|
* @category Cache Management
|
|
128
137
|
* @public
|
|
129
138
|
*/
|
package/dist/index.js
CHANGED
|
@@ -196,7 +196,10 @@ class Reporter {
|
|
|
196
196
|
const allFields = this.schema.fields({
|
|
197
197
|
type
|
|
198
198
|
});
|
|
199
|
-
const
|
|
199
|
+
const allCacheFields = this.schema.cacheFields?.({
|
|
200
|
+
type
|
|
201
|
+
}) ?? allFields;
|
|
202
|
+
const attrs = Array.from(allCacheFields.values()).filter(isRemoteField).map(v => v.name);
|
|
200
203
|
this._fieldFilters.set(type, new Fuse(attrs));
|
|
201
204
|
}
|
|
202
205
|
const result = this._fieldFilters.get(type).search(field);
|
|
@@ -786,12 +789,15 @@ function validateTopLevelResourceShape(reporter, resource, path) {
|
|
|
786
789
|
}
|
|
787
790
|
}
|
|
788
791
|
function validateResourceAttributes(reporter, type, resource, path) {
|
|
789
|
-
const
|
|
792
|
+
const fields = reporter.schema.fields({
|
|
790
793
|
type
|
|
791
794
|
});
|
|
795
|
+
const cacheFields = reporter.schema.cacheFields?.({
|
|
796
|
+
type
|
|
797
|
+
}) ?? fields;
|
|
792
798
|
for (const [key] of Object.entries(resource)) {
|
|
793
|
-
const field = getRemoteField(
|
|
794
|
-
const actualField =
|
|
799
|
+
const field = getRemoteField(cacheFields, key);
|
|
800
|
+
const actualField = cacheFields.get(key);
|
|
795
801
|
if (!field && actualField) {
|
|
796
802
|
reporter.warn([...path, key], `Expected the ${actualField.kind} field "${key}" to not have its own data in the ResourceObject's attributes. Likely this field should either not be returned in this payload or the field definition should be updated in the schema.`);
|
|
797
803
|
} else if (!field) {
|
|
@@ -1279,6 +1285,15 @@ class JSONAPICache {
|
|
|
1279
1285
|
* of the Graph handling necessary entanglements and
|
|
1280
1286
|
* notifications for relational data.
|
|
1281
1287
|
*
|
|
1288
|
+
* :::warning
|
|
1289
|
+
* It is not recommended to use the return value as
|
|
1290
|
+
* a serialized representation of the resource both
|
|
1291
|
+
* due to it containing local mutations and because
|
|
1292
|
+
* it may contain additional fields not recognized
|
|
1293
|
+
* by the {json:api} API implementation such as `lid` and
|
|
1294
|
+
* the various internal WarpDrive bookkeeping fields.
|
|
1295
|
+
* :::
|
|
1296
|
+
*
|
|
1282
1297
|
* @category Cache Management
|
|
1283
1298
|
* @public
|
|
1284
1299
|
*/
|
|
@@ -1294,7 +1309,7 @@ class JSONAPICache {
|
|
|
1294
1309
|
id,
|
|
1295
1310
|
lid
|
|
1296
1311
|
} = identifier;
|
|
1297
|
-
const attributes = Object.assign({}, peeked.remoteAttrs, peeked.inflightAttrs, peeked.localAttrs);
|
|
1312
|
+
const attributes = structuredClone(Object.assign({}, peeked.remoteAttrs, peeked.inflightAttrs, peeked.localAttrs));
|
|
1298
1313
|
const relationships = {};
|
|
1299
1314
|
const rels = this.__graph.identifiers.get(identifier);
|
|
1300
1315
|
if (rels) {
|
|
@@ -1352,7 +1367,7 @@ class JSONAPICache {
|
|
|
1352
1367
|
id,
|
|
1353
1368
|
lid
|
|
1354
1369
|
} = identifier;
|
|
1355
|
-
const attributes =
|
|
1370
|
+
const attributes = structuredClone(peeked.remoteAttrs);
|
|
1356
1371
|
const relationships = {};
|
|
1357
1372
|
const rels = this.__graph.identifiers.get(identifier);
|
|
1358
1373
|
if (rels) {
|
|
@@ -1361,7 +1376,7 @@ class JSONAPICache {
|
|
|
1361
1376
|
if (rel.definition.isImplicit) {
|
|
1362
1377
|
return;
|
|
1363
1378
|
} else {
|
|
1364
|
-
relationships[key] = this.__graph.getData(identifier, key);
|
|
1379
|
+
relationships[key] = structuredClone(this.__graph.getData(identifier, key));
|
|
1365
1380
|
}
|
|
1366
1381
|
});
|
|
1367
1382
|
}
|
|
@@ -3053,7 +3068,10 @@ function patchCache(Cache, op) {
|
|
|
3053
3068
|
}
|
|
3054
3069
|
function getCacheFields(cache, identifier) {
|
|
3055
3070
|
if (cache._capabilities.schema.cacheFields) {
|
|
3056
|
-
|
|
3071
|
+
const result = cache._capabilities.schema.cacheFields(identifier);
|
|
3072
|
+
if (result) {
|
|
3073
|
+
return result;
|
|
3074
|
+
}
|
|
3057
3075
|
}
|
|
3058
3076
|
|
|
3059
3077
|
// the model schema service cannot process fields that are not cache fields
|
|
@@ -3092,12 +3110,13 @@ function didCommit(cache, committedIdentifier, data, op) {
|
|
|
3092
3110
|
const existingId = committedIdentifier.id;
|
|
3093
3111
|
const identifier = op !== 'deleteRecord' && data ? cacheKeyManager.updateRecordIdentifier(committedIdentifier, data) : committedIdentifier;
|
|
3094
3112
|
const cached = cache.__peek(identifier, false);
|
|
3095
|
-
if (cached.isDeleted) {
|
|
3113
|
+
if (cached.isDeleted || op === 'deleteRecord') {
|
|
3096
3114
|
cache.__graph.push({
|
|
3097
3115
|
op: 'deleteRecord',
|
|
3098
3116
|
record: identifier,
|
|
3099
3117
|
isNew: false
|
|
3100
3118
|
});
|
|
3119
|
+
cached.isDeleted = true;
|
|
3101
3120
|
cached.isDeletionCommitted = true;
|
|
3102
3121
|
cache._capabilities.notifyChange(identifier, 'removed', null);
|
|
3103
3122
|
// TODO @runspired should we early exit here?
|