jazz-tools 0.16.5 → 0.16.7
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/.turbo/turbo-build.log +38 -38
- package/CHANGELOG.md +25 -0
- package/dist/{chunk-H3BIFFQG.js → chunk-R2VNCMG6.js} +3 -3
- package/dist/chunk-R2VNCMG6.js.map +1 -0
- package/dist/index.js +1 -3
- package/dist/index.js.map +1 -1
- package/dist/inspector/{custom-element-TUXKXSZU.js → custom-element-I7L56H6B.js} +3 -5
- package/dist/inspector/{custom-element-TUXKXSZU.js.map → custom-element-I7L56H6B.js.map} +1 -1
- package/dist/inspector/index.js +2 -4
- package/dist/inspector/index.js.map +1 -1
- package/dist/inspector/register-custom-element.js +1 -1
- package/dist/inspector/viewer/co-plain-text-view.d.ts +1 -1
- package/dist/inspector/viewer/co-plain-text-view.d.ts.map +1 -1
- package/dist/inspector/viewer/role-display.d.ts.map +1 -1
- package/dist/react/ssr.d.ts.map +1 -1
- package/dist/react/ssr.js.map +1 -1
- package/dist/react/tests/testUtils.d.ts.map +1 -1
- package/dist/react-core/auth/PassphraseAuth.d.ts +1 -1
- package/dist/react-core/auth/PassphraseAuth.d.ts.map +1 -1
- package/dist/react-core/index.js +1 -3
- package/dist/react-core/index.js.map +1 -1
- package/dist/react-core/tests/testUtils.d.ts.map +1 -1
- package/dist/testing.js +1 -1
- package/dist/testing.js.map +1 -1
- package/dist/tools/coValues/coFeed.d.ts.map +1 -1
- package/dist/tools/coValues/deepLoading.d.ts +10 -10
- package/dist/tools/coValues/deepLoading.d.ts.map +1 -1
- package/dist/tools/index.d.ts +1 -1
- package/dist/tools/index.d.ts.map +1 -1
- package/dist/tools/testing.d.ts.map +1 -1
- package/package.json +4 -4
- package/src/inspector/viewer/co-plain-text-view.tsx +1 -5
- package/src/inspector/viewer/co-stream-view.tsx +1 -1
- package/src/inspector/viewer/role-display.tsx +4 -1
- package/src/react/ssr.ts +1 -3
- package/src/react/tests/testUtils.tsx +2 -10
- package/src/react-core/auth/PassphraseAuth.tsx +1 -5
- package/src/react-core/tests/testUtils.tsx +2 -10
- package/src/tools/coValues/coFeed.ts +3 -2
- package/src/tools/coValues/deepLoading.ts +46 -32
- package/src/tools/index.ts +0 -1
- package/src/tools/testing.ts +3 -1
- package/src/tools/tests/coList.test.ts +1 -1
- package/src/tools/tests/coMap.record.test-d.ts +105 -0
- package/src/tools/tests/coMap.record.test.ts +45 -0
- package/src/tools/tests/coMap.test-d.ts +50 -0
- package/vitest.config.ts +1 -21
- package/dist/browser-media-images/index.test.browser.d.ts +0 -2
- package/dist/browser-media-images/index.test.browser.d.ts.map +0 -1
- package/dist/chunk-H3BIFFQG.js.map +0 -1
- package/src/browser-media-images/index.test.browser.ts +0 -73
@@ -97,6 +97,27 @@ type onErrorNullEnabled<Depth> = Depth extends { $onError: null }
|
|
97
97
|
? null
|
98
98
|
: never;
|
99
99
|
|
100
|
+
type CoMapLikeLoaded<
|
101
|
+
V extends object,
|
102
|
+
Depth,
|
103
|
+
DepthLimit extends number,
|
104
|
+
CurrentDepth extends number[],
|
105
|
+
> = {
|
106
|
+
-readonly [Key in keyof Depth]-?: Key extends CoKeys<V>
|
107
|
+
? NonNullable<V[Key]> extends CoValue
|
108
|
+
?
|
109
|
+
| DeeplyLoaded<
|
110
|
+
NonNullable<V[Key]>,
|
111
|
+
Depth[Key],
|
112
|
+
DepthLimit,
|
113
|
+
[0, ...CurrentDepth]
|
114
|
+
>
|
115
|
+
| (undefined extends V[Key] ? undefined : never)
|
116
|
+
| onErrorNullEnabled<Depth[Key]>
|
117
|
+
: never
|
118
|
+
: never;
|
119
|
+
} & V;
|
120
|
+
|
100
121
|
export type DeeplyLoaded<
|
101
122
|
V,
|
102
123
|
Depth,
|
@@ -126,38 +147,31 @@ export type DeeplyLoaded<
|
|
126
147
|
: V
|
127
148
|
: // Basically V extends CoMap | Group | Account - but if we used that we'd introduce circularity into the definition of CoMap itself
|
128
149
|
[V] extends [{ _type: "CoMap" | "Group" | "Account" }]
|
129
|
-
?
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
{
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
[0, ...CurrentDepth]
|
155
|
-
>
|
156
|
-
| (undefined extends V[Key] ? undefined : never)
|
157
|
-
| onErrorNullEnabled<Depth[Key]>
|
158
|
-
: never
|
159
|
-
: never;
|
160
|
-
} & V // same reason as in CoList
|
150
|
+
? // If Depth = {} return V in any case
|
151
|
+
keyof Depth extends never
|
152
|
+
? V
|
153
|
+
: // 1. Record-like CoMap
|
154
|
+
ItemsSym extends keyof V
|
155
|
+
? // 1.1. Deeply loaded Record-like CoMap with { $each: true | {$onError: null} }
|
156
|
+
Depth extends { $each: infer ItemDepth }
|
157
|
+
? {
|
158
|
+
[key: string]:
|
159
|
+
| DeeplyLoaded<
|
160
|
+
NonNullable<V[ItemsSym]>,
|
161
|
+
ItemDepth,
|
162
|
+
DepthLimit,
|
163
|
+
[0, ...CurrentDepth]
|
164
|
+
>
|
165
|
+
| onErrorNullEnabled<Depth["$each"]>;
|
166
|
+
} & V // same reason as in CoList
|
167
|
+
: // 1.2. Deeply loaded Record-like CoMap with { [key: string]: true }
|
168
|
+
string extends keyof Depth
|
169
|
+
? // if at least one key is `string`, then we treat the resolve as it was empty
|
170
|
+
DeeplyLoaded<V, {}, DepthLimit, [0, ...CurrentDepth]> & V
|
171
|
+
: // 1.3 Deeply loaded Record-like CoMap with single keys
|
172
|
+
CoMapLikeLoaded<V, Depth, DepthLimit, CurrentDepth>
|
173
|
+
: // 2. Deeply loaded CoMap
|
174
|
+
CoMapLikeLoaded<V, Depth, DepthLimit, CurrentDepth>
|
161
175
|
: [V] extends [
|
162
176
|
{
|
163
177
|
_type: "CoStream";
|
package/src/tools/index.ts
CHANGED
package/src/tools/testing.ts
CHANGED
@@ -305,7 +305,9 @@ export async function linkAccounts(
|
|
305
305
|
|
306
306
|
export async function setupJazzTestSync({
|
307
307
|
asyncPeers = false,
|
308
|
-
}: {
|
308
|
+
}: {
|
309
|
+
asyncPeers?: boolean;
|
310
|
+
} = {}) {
|
309
311
|
if (syncServer.current) {
|
310
312
|
syncServer.current.gracefulShutdown();
|
311
313
|
}
|
@@ -1,5 +1,5 @@
|
|
1
1
|
import { WasmCrypto } from "cojson/crypto/WasmCrypto";
|
2
|
-
import { beforeEach, describe, expect, test, vi } from "vitest";
|
2
|
+
import { assert, beforeEach, describe, expect, test, vi } from "vitest";
|
3
3
|
import { Account, Group, subscribeToCoValue, z } from "../index.js";
|
4
4
|
import {
|
5
5
|
Loaded,
|
@@ -173,6 +173,111 @@ describe("CoMap.Record", () => {
|
|
173
173
|
matches(loadedPerson);
|
174
174
|
});
|
175
175
|
|
176
|
+
test("loading a record with property resolve", async () => {
|
177
|
+
const Dog = co.map({
|
178
|
+
name: z.string(),
|
179
|
+
breed: z.string(),
|
180
|
+
});
|
181
|
+
|
182
|
+
const Person = co.record(z.string(), Dog);
|
183
|
+
|
184
|
+
const person = Person.create({
|
185
|
+
pet1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
186
|
+
pet2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
187
|
+
});
|
188
|
+
|
189
|
+
const loadedPerson = await Person.load(person.id, {
|
190
|
+
resolve: {
|
191
|
+
pet1: true,
|
192
|
+
},
|
193
|
+
});
|
194
|
+
|
195
|
+
type Expect = NonNullable<typeof loadedPerson> extends never
|
196
|
+
? "error: is never"
|
197
|
+
: "ok";
|
198
|
+
|
199
|
+
expectTypeOf("ok" as const).toEqualTypeOf<Expect>();
|
200
|
+
|
201
|
+
expectTypeOf(loadedPerson?.pet1).toEqualTypeOf<
|
202
|
+
Loaded<typeof Dog> | undefined
|
203
|
+
>();
|
204
|
+
expectTypeOf(loadedPerson?.pet3).toEqualTypeOf<
|
205
|
+
Loaded<typeof Dog> | undefined | null
|
206
|
+
>();
|
207
|
+
});
|
208
|
+
|
209
|
+
test("loading a record with generic string resolve", async () => {
|
210
|
+
const Dog = co.map({
|
211
|
+
name: z.string(),
|
212
|
+
breed: z.string(),
|
213
|
+
});
|
214
|
+
|
215
|
+
const Person = co.record(z.string(), Dog);
|
216
|
+
|
217
|
+
const person = Person.create({
|
218
|
+
pet1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
219
|
+
pet2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
220
|
+
});
|
221
|
+
|
222
|
+
const userId: string = "pet1";
|
223
|
+
const userId2: string = "pet3";
|
224
|
+
|
225
|
+
const loadedPerson = await Person.load(person.id, {
|
226
|
+
resolve: {
|
227
|
+
[userId]: true,
|
228
|
+
pet2: true,
|
229
|
+
[userId2]: {
|
230
|
+
$onError: null,
|
231
|
+
},
|
232
|
+
},
|
233
|
+
});
|
234
|
+
|
235
|
+
type Expect = NonNullable<typeof loadedPerson> extends never
|
236
|
+
? "error: is never"
|
237
|
+
: "ok";
|
238
|
+
|
239
|
+
expectTypeOf("ok" as const).toEqualTypeOf<Expect>();
|
240
|
+
|
241
|
+
expectTypeOf(loadedPerson?.pet1).toEqualTypeOf<
|
242
|
+
Loaded<typeof Dog> | undefined | null
|
243
|
+
>();
|
244
|
+
expectTypeOf(loadedPerson?.pet2).toEqualTypeOf<
|
245
|
+
Loaded<typeof Dog> | undefined | null
|
246
|
+
>();
|
247
|
+
expectTypeOf(loadedPerson?.pet3).toEqualTypeOf<
|
248
|
+
Loaded<typeof Dog> | undefined | null
|
249
|
+
>();
|
250
|
+
});
|
251
|
+
|
252
|
+
test("loading a record with empty resolve", async () => {
|
253
|
+
const Dog = co.map({
|
254
|
+
name: z.string(),
|
255
|
+
breed: z.string(),
|
256
|
+
});
|
257
|
+
|
258
|
+
const Person = co.record(z.string(), Dog);
|
259
|
+
|
260
|
+
const person = Person.create({
|
261
|
+
pet1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
262
|
+
pet2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
263
|
+
});
|
264
|
+
|
265
|
+
const loadedPerson = await Person.load(person.id);
|
266
|
+
|
267
|
+
type Expect = NonNullable<typeof loadedPerson> extends never
|
268
|
+
? "error: is never"
|
269
|
+
: "ok";
|
270
|
+
|
271
|
+
expectTypeOf("ok" as const).toEqualTypeOf<Expect>();
|
272
|
+
|
273
|
+
expectTypeOf(loadedPerson?.pet1).toEqualTypeOf<
|
274
|
+
Loaded<typeof Dog> | undefined | null
|
275
|
+
>();
|
276
|
+
expectTypeOf(loadedPerson?.pet3).toEqualTypeOf<
|
277
|
+
Loaded<typeof Dog> | undefined | null
|
278
|
+
>();
|
279
|
+
});
|
280
|
+
|
176
281
|
test("loading a record with $onError", async () => {
|
177
282
|
const Dog = co.map({
|
178
283
|
name: z.string(),
|
@@ -213,6 +213,51 @@ describe("CoMap.Record", async () => {
|
|
213
213
|
expect(loadedPerson.pet2?.name).toEqual("Fido");
|
214
214
|
});
|
215
215
|
|
216
|
+
test("loading a locally available record with single resolve", async () => {
|
217
|
+
const Dog = co.map({
|
218
|
+
name: z.string(),
|
219
|
+
breed: z.string(),
|
220
|
+
});
|
221
|
+
|
222
|
+
const Person = co.record(z.string(), Dog);
|
223
|
+
|
224
|
+
const person = Person.create({
|
225
|
+
pet1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
226
|
+
pet2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
227
|
+
});
|
228
|
+
|
229
|
+
const loadedPerson = await Person.load(person.id, {
|
230
|
+
resolve: {
|
231
|
+
pet1: true,
|
232
|
+
},
|
233
|
+
});
|
234
|
+
|
235
|
+
assert(loadedPerson);
|
236
|
+
expect(loadedPerson.pet1?.name).toEqual("Rex");
|
237
|
+
});
|
238
|
+
|
239
|
+
test("loading a locally available record with unavailable single resolve", async () => {
|
240
|
+
const Dog = co.map({
|
241
|
+
name: z.string(),
|
242
|
+
breed: z.string(),
|
243
|
+
});
|
244
|
+
|
245
|
+
const Person = co.record(z.string(), Dog);
|
246
|
+
|
247
|
+
const person = Person.create({
|
248
|
+
pet1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
249
|
+
pet2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
250
|
+
});
|
251
|
+
|
252
|
+
const loadedPerson = await Person.load(person.id, {
|
253
|
+
resolve: {
|
254
|
+
pet3: true,
|
255
|
+
},
|
256
|
+
});
|
257
|
+
|
258
|
+
expect(loadedPerson).toEqual(null);
|
259
|
+
});
|
260
|
+
|
216
261
|
test("loading a locally available record using autoload for the refs", async () => {
|
217
262
|
const Dog = co.map({
|
218
263
|
name: z.string(),
|
@@ -542,6 +542,56 @@ describe("CoMap resolution", async () => {
|
|
542
542
|
> | null>();
|
543
543
|
});
|
544
544
|
|
545
|
+
test("partial loading a map with string resolve", async () => {
|
546
|
+
const Dog = co.map({
|
547
|
+
name: z.string(),
|
548
|
+
breed: z.string(),
|
549
|
+
});
|
550
|
+
|
551
|
+
const Person = co.map({
|
552
|
+
name: z.string(),
|
553
|
+
age: z.number(),
|
554
|
+
dog1: Dog,
|
555
|
+
dog2: Dog,
|
556
|
+
});
|
557
|
+
|
558
|
+
const person = Person.create({
|
559
|
+
name: "John",
|
560
|
+
age: 20,
|
561
|
+
dog1: Dog.create({ name: "Rex", breed: "Labrador" }),
|
562
|
+
dog2: Dog.create({ name: "Fido", breed: "Poodle" }),
|
563
|
+
});
|
564
|
+
|
565
|
+
const userId: string = "dog1";
|
566
|
+
|
567
|
+
const loadedPerson = await Person.load(person.id, {
|
568
|
+
resolve: {
|
569
|
+
[userId]: true,
|
570
|
+
},
|
571
|
+
});
|
572
|
+
|
573
|
+
type ExpectedType = {
|
574
|
+
name: string;
|
575
|
+
age: number;
|
576
|
+
dog1: Loaded<typeof Dog> | null;
|
577
|
+
dog2: Loaded<typeof Dog> | null;
|
578
|
+
} | null;
|
579
|
+
|
580
|
+
function matches(value: ExpectedType) {
|
581
|
+
return value;
|
582
|
+
}
|
583
|
+
|
584
|
+
matches(loadedPerson);
|
585
|
+
|
586
|
+
assert(loadedPerson);
|
587
|
+
expectTypeOf<typeof loadedPerson.dog1>().toEqualTypeOf<Loaded<
|
588
|
+
typeof Dog
|
589
|
+
> | null>();
|
590
|
+
expectTypeOf<typeof loadedPerson.dog2>().toEqualTypeOf<Loaded<
|
591
|
+
typeof Dog
|
592
|
+
> | null>();
|
593
|
+
});
|
594
|
+
|
545
595
|
test("loading a map with deep resolve and $onError", async () => {
|
546
596
|
const Dog = co.map({
|
547
597
|
name: z.string(),
|
package/vitest.config.ts
CHANGED
@@ -3,30 +3,10 @@ import { defineProject } from "vitest/config";
|
|
3
3
|
export default defineProject({
|
4
4
|
test: {
|
5
5
|
name: "jazz-tools",
|
6
|
+
include: ["src/**/*.test.{js,ts,svelte}"],
|
6
7
|
typecheck: {
|
7
8
|
enabled: true,
|
8
9
|
checker: "tsc",
|
9
10
|
},
|
10
|
-
projects: [
|
11
|
-
{
|
12
|
-
test: {
|
13
|
-
include: ["src/**/*.test.browser.ts"],
|
14
|
-
browser: {
|
15
|
-
enabled: true,
|
16
|
-
provider: "playwright",
|
17
|
-
headless: true,
|
18
|
-
screenshotFailures: false,
|
19
|
-
instances: [{ browser: "chromium" }],
|
20
|
-
},
|
21
|
-
name: "browser",
|
22
|
-
},
|
23
|
-
},
|
24
|
-
{
|
25
|
-
test: {
|
26
|
-
include: ["src/**/*.test.{js,ts,svelte}"],
|
27
|
-
name: "unit",
|
28
|
-
},
|
29
|
-
},
|
30
|
-
],
|
31
11
|
},
|
32
12
|
});
|
@@ -1 +0,0 @@
|
|
1
|
-
{"version":3,"file":"index.test.browser.d.ts","sourceRoot":"","sources":["../../src/browser-media-images/index.test.browser.ts"],"names":[],"mappings":""}
|