jazz-tools 0.18.26 → 0.18.28
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 +61 -61
- package/CHANGELOG.md +24 -0
- package/dist/{chunk-ZIAN4UY5.js → chunk-YOL3XDDW.js} +158 -120
- package/dist/chunk-YOL3XDDW.js.map +1 -0
- package/dist/index.js +97 -5
- package/dist/index.js.map +1 -1
- package/dist/media/{chunk-W3S526L3.js → chunk-K6GCHLQU.js} +1 -1
- package/dist/media/chunk-K6GCHLQU.js.map +1 -0
- package/dist/media/create-image/browser.d.ts +1 -1
- package/dist/media/create-image/react-native.d.ts +1 -1
- package/dist/media/create-image/react-native.d.ts.map +1 -1
- package/dist/media/create-image/server.d.ts +1 -1
- package/dist/media/create-image-factory.d.ts +5 -2
- package/dist/media/create-image-factory.d.ts.map +1 -1
- package/dist/media/index.browser.js +1 -1
- package/dist/media/index.d.ts +3 -4
- package/dist/media/index.d.ts.map +1 -1
- package/dist/media/index.js +1 -1
- package/dist/media/index.native.js +63 -28
- package/dist/media/index.native.js.map +1 -1
- package/dist/media/index.server.js +1 -1
- package/dist/react/index.js.map +1 -1
- package/dist/react-core/hooks.d.ts +4 -0
- package/dist/react-core/hooks.d.ts.map +1 -1
- package/dist/react-core/index.js +5 -0
- package/dist/react-core/index.js.map +1 -1
- package/dist/testing.js +1 -1
- package/dist/tools/coValues/coList.d.ts +11 -3
- package/dist/tools/coValues/coList.d.ts.map +1 -1
- package/dist/tools/coValues/coMap.d.ts +21 -5
- package/dist/tools/coValues/coMap.d.ts.map +1 -1
- package/dist/tools/coValues/group.d.ts +2 -2
- package/dist/tools/coValues/group.d.ts.map +1 -1
- package/dist/tools/coValues/inbox.d.ts.map +1 -1
- package/dist/tools/coValues/interfaces.d.ts +9 -0
- package/dist/tools/coValues/interfaces.d.ts.map +1 -1
- package/dist/tools/coValues/request.d.ts +70 -0
- package/dist/tools/coValues/request.d.ts.map +1 -1
- package/dist/tools/exports.d.ts +2 -2
- package/dist/tools/exports.d.ts.map +1 -1
- package/dist/tools/tests/authenticate-request.test.d.ts +2 -0
- package/dist/tools/tests/authenticate-request.test.d.ts.map +1 -0
- package/dist/tools/tests/coList.unique.test.d.ts +2 -0
- package/dist/tools/tests/coList.unique.test.d.ts.map +1 -0
- package/dist/tools/tests/coMap.unique.test.d.ts +2 -0
- package/dist/tools/tests/coMap.unique.test.d.ts.map +1 -0
- package/package.json +8 -4
- package/src/media/create-image/react-native.ts +75 -30
- package/src/media/create-image-factory.test.ts +18 -0
- package/src/media/create-image-factory.ts +6 -1
- package/src/media/index.ts +7 -4
- package/src/react-core/hooks.ts +8 -0
- package/src/react-core/tests/useAccount.test.ts +61 -1
- package/src/react-core/tests/usePassPhraseAuth.test.ts +74 -2
- package/src/tools/coValues/coList.ts +38 -35
- package/src/tools/coValues/coMap.ts +38 -38
- package/src/tools/coValues/group.ts +5 -1
- package/src/tools/coValues/inbox.ts +4 -3
- package/src/tools/coValues/interfaces.ts +88 -0
- package/src/tools/coValues/request.ts +188 -4
- package/src/tools/exports.ts +4 -0
- package/src/tools/tests/authenticate-request.test.ts +194 -0
- package/src/tools/tests/coList.test.ts +0 -190
- package/src/tools/tests/coList.unique.test.ts +244 -0
- package/src/tools/tests/coMap.test.ts +0 -433
- package/src/tools/tests/coMap.unique.test.ts +474 -0
- package/dist/chunk-ZIAN4UY5.js.map +0 -1
- package/dist/media/chunk-W3S526L3.js.map +0 -1
package/dist/tools/exports.d.ts
CHANGED
|
@@ -8,7 +8,7 @@ export { CoValueBase } from "./internal.js";
|
|
|
8
8
|
export { Profile } from "./internal.js";
|
|
9
9
|
export { SchemaUnion } from "./internal.js";
|
|
10
10
|
export { co } from "./internal.js";
|
|
11
|
-
export type { CoValueClass, CoValueFromRaw, DeeplyLoaded, Resolved, RefsToResolve, RefsToResolveStrict, CoMapInit_DEPRECATED as CoMapInit, CoFeedEntry, TextPos, AccountClass, AccountCreationProps, BaseProfileShape, } from "./internal.js";
|
|
11
|
+
export type { CoValueClass, CoValueFromRaw, DeeplyLoaded, Resolved, RefsToResolve, RefsToResolveStrict, CoMapInit_DEPRECATED as CoMapInit, CoFeedEntry, TextPos, AccountClass, AccountCreationProps, BaseProfileShape, unstable_loadUnique, } from "./internal.js";
|
|
12
12
|
export { CoMap, CoList, BinaryCoStream, CoFeed, CoStream, FileStream, CoPlainText, CoRichText, Account, isControlledAccount, loadCoValue, subscribeToCoValue, ImageDefinition, SubscriptionScope, exportCoValue, importContentPieces, Ref, } from "./internal.js";
|
|
13
13
|
export { JazzContextManager, type JazzContextManagerAuthProps, } from "./internal.js";
|
|
14
14
|
export { AuthSecretStorage, type AuthSetPayload, } from "./auth/AuthSecretStorage.js";
|
|
@@ -21,6 +21,6 @@ export { createInviteLink, parseInviteLink, consumeInviteLink, } from "./impleme
|
|
|
21
21
|
export { AnonymousJazzAgent, createAnonymousJazzContext, createJazzContextFromExistingCredentials, createJazzContextForNewAccount, createJazzContext, randomSessionProvider, type AuthResult, type Credentials, type JazzContextWithAccount, type BranchDefinition, } from "./internal.js";
|
|
22
22
|
export type * from "./types.js";
|
|
23
23
|
export { coValueClassFromCoValueClassOrSchema, type InstanceOfSchema, type InstanceOfSchemaCoValuesNullable, type CoValueClassOrSchema, type Loaded, type BaseAccountShape, type DefaultAccountShape, type CoreAccountSchema as AnyAccountSchema, type ResolveQuery, type ResolveQueryStrict, } from "./internal.js";
|
|
24
|
-
export { experimental_defineRequest, JazzRequestError, isJazzRequestError, type HttpRoute, } from "./coValues/request.js";
|
|
24
|
+
export { experimental_defineRequest, JazzRequestError, isJazzRequestError, authenticateRequest, generateAuthToken, parseAuthToken, type HttpRoute, } from "./coValues/request.js";
|
|
25
25
|
export * from "./ssr/index.js";
|
|
26
26
|
//# sourceMappingURL=exports.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"exports.d.ts","sourceRoot":"","sources":["../../src/tools/exports.ts"],"names":[],"mappings":"AAAA,YAAY,EACV,OAAO,EACP,iBAAiB,EACjB,cAAc,EACd,YAAY,EACZ,IAAI,EACJ,SAAS,EACT,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,KAAK,CAAC,MAAM,2CAA2C,CAAC;AAE/D,YAAY,EAAE,OAAO,EAAE,EAAE,EAAE,MAAM,eAAe,CAAC;AAEjD,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AAElD,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEnD,OAAO,EAAE,KAAK,EAAE,MAAM,eAAe,CAAC;AACtC,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AACxC,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EAAE,EAAE,EAAE,MAAM,eAAe,CAAC;AAEnC,YAAY,EACV,YAAY,EACZ,cAAc,EACd,YAAY,EACZ,QAAQ,EACR,aAAa,EACb,mBAAmB,EACnB,oBAAoB,IAAI,SAAS,EACjC,WAAW,EACX,OAAO,EACP,YAAY,EACZ,oBAAoB,EACpB,gBAAgB,
|
|
1
|
+
{"version":3,"file":"exports.d.ts","sourceRoot":"","sources":["../../src/tools/exports.ts"],"names":[],"mappings":"AAAA,YAAY,EACV,OAAO,EACP,iBAAiB,EACjB,cAAc,EACd,YAAY,EACZ,IAAI,EACJ,SAAS,EACT,WAAW,GACZ,MAAM,QAAQ,CAAC;AAEhB,OAAO,KAAK,CAAC,MAAM,2CAA2C,CAAC;AAE/D,YAAY,EAAE,OAAO,EAAE,EAAE,EAAE,MAAM,eAAe,CAAC;AAEjD,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AAElD,OAAO,EAAE,KAAK,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAEnD,OAAO,EAAE,KAAK,EAAE,MAAM,eAAe,CAAC;AACtC,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AACxC,OAAO,EAAE,WAAW,EAAE,MAAM,eAAe,CAAC;AAE5C,OAAO,EAAE,EAAE,EAAE,MAAM,eAAe,CAAC;AAEnC,YAAY,EACV,YAAY,EACZ,cAAc,EACd,YAAY,EACZ,QAAQ,EACR,aAAa,EACb,mBAAmB,EACnB,oBAAoB,IAAI,SAAS,EACjC,WAAW,EACX,OAAO,EACP,YAAY,EACZ,oBAAoB,EACpB,gBAAgB,EAChB,mBAAmB,GACpB,MAAM,eAAe,CAAC;AAEvB,OAAO,EACL,KAAK,EACL,MAAM,EACN,cAAc,EACd,MAAM,EACN,QAAQ,EACR,UAAU,EACV,WAAW,EACX,UAAU,EACV,OAAO,EACP,mBAAmB,EACnB,WAAW,EACX,kBAAkB,EAClB,eAAe,EACf,iBAAiB,EACjB,aAAa,EACb,mBAAmB,EACnB,GAAG,GACJ,MAAM,eAAe,CAAC;AAEvB,OAAO,EACL,kBAAkB,EAClB,KAAK,2BAA2B,GACjC,MAAM,eAAe,CAAC;AAEvB,OAAO,EACL,iBAAiB,EACjB,KAAK,cAAc,GACpB,MAAM,6BAA6B,CAAC;AACrC,OAAO,EACL,aAAa,EACb,kBAAkB,EAClB,kBAAkB,EAClB,gBAAgB,GACjB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAAE,cAAc,EAAE,KAAK,OAAO,EAAE,MAAM,0BAA0B,CAAC;AACxE,OAAO,EAAE,eAAe,EAAE,MAAM,2BAA2B,CAAC;AAC5D,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,cAAc,EAAE,MAAM,0BAA0B,CAAC;AAE1D,OAAO,EACL,gBAAgB,EAChB,eAAe,EACf,iBAAiB,GAClB,MAAM,6BAA6B,CAAC;AAErC,OAAO,EACL,kBAAkB,EAClB,0BAA0B,EAC1B,wCAAwC,EACxC,8BAA8B,EAC9B,iBAAiB,EACjB,qBAAqB,EACrB,KAAK,UAAU,EACf,KAAK,WAAW,EAChB,KAAK,sBAAsB,EAC3B,KAAK,gBAAgB,GACtB,MAAM,eAAe,CAAC;AAEvB,mBAAmB,YAAY,CAAC;AAEhC,OAAO,EACL,oCAAoC,EACpC,KAAK,gBAAgB,EACrB,KAAK,gCAAgC,EACrC,KAAK,oBAAoB,EACzB,KAAK,MAAM,EACX,KAAK,gBAAgB,EACrB,KAAK,mBAAmB,EACxB,KAAK,iBAAiB,IAAI,gBAAgB,EAC1C,KAAK,YAAY,EACjB,KAAK,kBAAkB,GACxB,MAAM,eAAe,CAAC;AAEvB,OAAO,EACL,0BAA0B,EAC1B,gBAAgB,EAChB,kBAAkB,EAClB,mBAAmB,EACnB,iBAAiB,EACjB,cAAc,EACd,KAAK,SAAS,GACf,MAAM,uBAAuB,CAAC;AAE/B,cAAc,gBAAgB,CAAC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"authenticate-request.test.d.ts","sourceRoot":"","sources":["../../../src/tools/tests/authenticate-request.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"coList.unique.test.d.ts","sourceRoot":"","sources":["../../../src/tools/tests/coList.unique.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"coMap.unique.test.d.ts","sourceRoot":"","sources":["../../../src/tools/tests/coMap.unique.test.ts"],"names":[],"mappings":""}
|
package/package.json
CHANGED
|
@@ -187,7 +187,7 @@
|
|
|
187
187
|
},
|
|
188
188
|
"type": "module",
|
|
189
189
|
"license": "MIT",
|
|
190
|
-
"version": "0.18.
|
|
190
|
+
"version": "0.18.28",
|
|
191
191
|
"dependencies": {
|
|
192
192
|
"@manuscripts/prosemirror-recreate-steps": "^0.1.4",
|
|
193
193
|
"@scure/base": "1.2.1",
|
|
@@ -204,9 +204,9 @@
|
|
|
204
204
|
"prosemirror-transform": "^1.9.0",
|
|
205
205
|
"use-sync-external-store": "^1.5.0",
|
|
206
206
|
"zod": "4.1.11",
|
|
207
|
-
"cojson": "0.18.
|
|
208
|
-
"cojson-storage-indexeddb": "0.18.
|
|
209
|
-
"cojson-transport-ws": "0.18.
|
|
207
|
+
"cojson": "0.18.28",
|
|
208
|
+
"cojson-storage-indexeddb": "0.18.28",
|
|
209
|
+
"cojson-transport-ws": "0.18.28"
|
|
210
210
|
},
|
|
211
211
|
"devDependencies": {
|
|
212
212
|
"@scure/bip39": "^1.3.0",
|
|
@@ -234,6 +234,7 @@
|
|
|
234
234
|
"@op-engineering/op-sqlite": "*",
|
|
235
235
|
"@react-native-community/netinfo": "*",
|
|
236
236
|
"better-auth": "^1.3.2",
|
|
237
|
+
"expo-image-manipulator": "*",
|
|
237
238
|
"expo-file-system": "*",
|
|
238
239
|
"expo-secure-store": "*",
|
|
239
240
|
"expo-sqlite": "*",
|
|
@@ -260,6 +261,9 @@
|
|
|
260
261
|
"better-auth": {
|
|
261
262
|
"optional": true
|
|
262
263
|
},
|
|
264
|
+
"expo-image-manipulator": {
|
|
265
|
+
"optional": true
|
|
266
|
+
},
|
|
263
267
|
"expo-file-system": {
|
|
264
268
|
"optional": true
|
|
265
269
|
},
|
|
@@ -1,11 +1,11 @@
|
|
|
1
|
+
import { NativeModules } from "react-native";
|
|
1
2
|
import type ImageResizerType from "@bam.tech/react-native-image-resizer";
|
|
3
|
+
import type ImageManipulatorType from "expo-image-manipulator";
|
|
2
4
|
import type { Account, Group } from "jazz-tools";
|
|
3
5
|
import { FileStream } from "jazz-tools";
|
|
4
6
|
import { Image } from "react-native";
|
|
5
7
|
import { createImageFactory } from "../create-image-factory";
|
|
6
8
|
|
|
7
|
-
let ImageResizer: typeof ImageResizerType | undefined;
|
|
8
|
-
|
|
9
9
|
/**
|
|
10
10
|
* Creates an ImageDefinition from an image file path with built-in UX features.
|
|
11
11
|
*
|
|
@@ -45,19 +45,27 @@ export const createImage = createImageFactory(
|
|
|
45
45
|
},
|
|
46
46
|
);
|
|
47
47
|
|
|
48
|
-
async function getResizer(): Promise<
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
);
|
|
48
|
+
async function getResizer(): Promise<
|
|
49
|
+
typeof ImageResizerType | typeof ImageManipulatorType
|
|
50
|
+
> {
|
|
51
|
+
try {
|
|
52
|
+
const rnImageResizer = await import("@bam.tech/react-native-image-resizer");
|
|
53
|
+
|
|
54
|
+
if (rnImageResizer.default !== undefined) {
|
|
55
|
+
return rnImageResizer.default;
|
|
57
56
|
}
|
|
58
|
-
}
|
|
57
|
+
} catch (e) {}
|
|
58
|
+
|
|
59
|
+
try {
|
|
60
|
+
const expoImageManipulator = await import("expo-image-manipulator");
|
|
61
|
+
if (expoImageManipulator.ImageManipulator !== undefined) {
|
|
62
|
+
return expoImageManipulator;
|
|
63
|
+
}
|
|
64
|
+
} catch (e) {}
|
|
59
65
|
|
|
60
|
-
|
|
66
|
+
throw new Error(
|
|
67
|
+
"No resizer lib found. Please install `@bam.tech/react-native-image-resizer` or `expo-image-manipulator`",
|
|
68
|
+
);
|
|
61
69
|
}
|
|
62
70
|
|
|
63
71
|
async function getImageSize(
|
|
@@ -71,15 +79,37 @@ async function getImageSize(
|
|
|
71
79
|
async function getPlaceholderBase64(filePath: string): Promise<string> {
|
|
72
80
|
const ImageResizer = await getResizer();
|
|
73
81
|
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
82
|
+
if ("createResizedImage" in ImageResizer) {
|
|
83
|
+
const { uri } = await ImageResizer.createResizedImage(
|
|
84
|
+
filePath,
|
|
85
|
+
8,
|
|
86
|
+
8,
|
|
87
|
+
"PNG",
|
|
88
|
+
100,
|
|
89
|
+
);
|
|
90
|
+
|
|
91
|
+
return imageUrlToBase64(uri);
|
|
92
|
+
} else {
|
|
93
|
+
const ctx = ImageResizer.ImageManipulator.manipulate(filePath);
|
|
81
94
|
|
|
82
|
-
|
|
95
|
+
ctx.resize({ width: 8, height: 8 });
|
|
96
|
+
|
|
97
|
+
const im = await ctx.renderAsync();
|
|
98
|
+
const result = await im.saveAsync({
|
|
99
|
+
base64: true,
|
|
100
|
+
format: ImageResizer.SaveFormat.PNG,
|
|
101
|
+
});
|
|
102
|
+
|
|
103
|
+
const base64 = result.base64;
|
|
104
|
+
|
|
105
|
+
if (!base64) {
|
|
106
|
+
throw new Error(
|
|
107
|
+
"Failed to get generate placeholder using expo-image-manipulator",
|
|
108
|
+
);
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
return base64;
|
|
112
|
+
}
|
|
83
113
|
}
|
|
84
114
|
|
|
85
115
|
async function resize(
|
|
@@ -91,15 +121,30 @@ async function resize(
|
|
|
91
121
|
|
|
92
122
|
const mimeType = await getMimeType(filePath);
|
|
93
123
|
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
124
|
+
if ("createResizedImage" in ImageResizer) {
|
|
125
|
+
const { uri } = await ImageResizer.createResizedImage(
|
|
126
|
+
filePath,
|
|
127
|
+
width,
|
|
128
|
+
height,
|
|
129
|
+
contentTypeToFormat(mimeType),
|
|
130
|
+
80,
|
|
131
|
+
);
|
|
132
|
+
|
|
133
|
+
return uri;
|
|
134
|
+
} else {
|
|
135
|
+
const ctx = ImageResizer.ImageManipulator.manipulate(filePath);
|
|
136
|
+
ctx.resize({ width: width, height: height });
|
|
137
|
+
|
|
138
|
+
const mime = contentTypeToFormat(mimeType);
|
|
139
|
+
|
|
140
|
+
const im = await ctx.renderAsync();
|
|
141
|
+
const result = await im.saveAsync({
|
|
142
|
+
format: ImageResizer.SaveFormat[mime],
|
|
143
|
+
compress: 0.8,
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
return result.uri;
|
|
147
|
+
}
|
|
103
148
|
}
|
|
104
149
|
|
|
105
150
|
function getMimeType(filePath: string): Promise<string> {
|
|
@@ -24,6 +24,24 @@ describe("createImage", async () => {
|
|
|
24
24
|
vi.clearAllMocks();
|
|
25
25
|
});
|
|
26
26
|
|
|
27
|
+
it("should return a loaded image definition", async () => {
|
|
28
|
+
const imageBlob = new Blob(
|
|
29
|
+
[Uint8Array.from(OnePixel, (c) => c.charCodeAt(0))],
|
|
30
|
+
{ type: "image/png" },
|
|
31
|
+
);
|
|
32
|
+
|
|
33
|
+
getImageSize.mockResolvedValue({ width: 1, height: 1 });
|
|
34
|
+
|
|
35
|
+
const image = await createImage(imageBlob, { owner: account });
|
|
36
|
+
|
|
37
|
+
// ensure `original` is loaded
|
|
38
|
+
function typeMatch(value: { original: FileStream }) {
|
|
39
|
+
return value;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
typeMatch(image);
|
|
43
|
+
});
|
|
44
|
+
|
|
27
45
|
it("should create a single original image if all settings are off", async () => {
|
|
28
46
|
const imageBlob = new Blob(
|
|
29
47
|
[Uint8Array.from(OnePixel, (c) => c.charCodeAt(0))],
|
|
@@ -37,6 +37,11 @@ export type CreateImageOptions = {
|
|
|
37
37
|
progressive?: boolean;
|
|
38
38
|
};
|
|
39
39
|
|
|
40
|
+
export type CreateImageReturnType = Loaded<
|
|
41
|
+
typeof ImageDefinition,
|
|
42
|
+
{ original: true }
|
|
43
|
+
>;
|
|
44
|
+
|
|
40
45
|
export type CreateImageImpl<
|
|
41
46
|
TSourceType = SourceType,
|
|
42
47
|
TResizeOutput = ResizeOutput,
|
|
@@ -70,7 +75,7 @@ async function createImage<TSourceType, TResizeOutput>(
|
|
|
70
75
|
imageBlobOrFile: TSourceType,
|
|
71
76
|
options: CreateImageOptions,
|
|
72
77
|
impl: CreateImageImpl<TSourceType, TResizeOutput>,
|
|
73
|
-
): Promise<
|
|
78
|
+
): Promise<CreateImageReturnType> {
|
|
74
79
|
// Get the original size of the image
|
|
75
80
|
const { width: originalWidth, height: originalHeight } =
|
|
76
81
|
await impl.getImageSize(imageBlobOrFile);
|
package/src/media/index.ts
CHANGED
|
@@ -1,5 +1,8 @@
|
|
|
1
|
-
import type { ImageDefinition } from "jazz-tools";
|
|
2
|
-
import {
|
|
1
|
+
import type { ImageDefinition, Loaded } from "jazz-tools";
|
|
2
|
+
import type {
|
|
3
|
+
CreateImageOptions,
|
|
4
|
+
CreateImageReturnType,
|
|
5
|
+
} from "./create-image-factory";
|
|
3
6
|
|
|
4
7
|
export * from "./exports";
|
|
5
8
|
|
|
@@ -38,7 +41,7 @@ export * from "./exports";
|
|
|
38
41
|
export declare function createImage(
|
|
39
42
|
imageBlobOrFile: Blob | File,
|
|
40
43
|
options?: CreateImageOptions,
|
|
41
|
-
): Promise<
|
|
44
|
+
): Promise<CreateImageReturnType>;
|
|
42
45
|
|
|
43
46
|
/**
|
|
44
47
|
* Creates an ImageDefinition from an image file path with built-in UX features.
|
|
@@ -66,4 +69,4 @@ export declare function createImage(
|
|
|
66
69
|
export declare function createImage(
|
|
67
70
|
filePath: string,
|
|
68
71
|
options?: CreateImageOptions,
|
|
69
|
-
): Promise<
|
|
72
|
+
): Promise<CreateImageReturnType>;
|
package/src/react-core/hooks.ts
CHANGED
|
@@ -792,6 +792,14 @@ export function useAccountWithSelector<
|
|
|
792
792
|
);
|
|
793
793
|
}
|
|
794
794
|
|
|
795
|
+
/**
|
|
796
|
+
* Returns a function for logging out of the current account.
|
|
797
|
+
*/
|
|
798
|
+
export function useLogOut(): () => void {
|
|
799
|
+
const contextManager = useJazzContextManager();
|
|
800
|
+
return contextManager.logOut;
|
|
801
|
+
}
|
|
802
|
+
|
|
795
803
|
export function experimental_useInboxSender<
|
|
796
804
|
I extends CoValue,
|
|
797
805
|
O extends CoValue | undefined,
|
|
@@ -64,7 +64,67 @@ describe("useAccount", () => {
|
|
|
64
64
|
expect(result.current?.me?.root?.value).toBe("123");
|
|
65
65
|
});
|
|
66
66
|
|
|
67
|
-
it("should be in sync with useIsAuthenticated when logOut is called", async () => {
|
|
67
|
+
it("should be in sync with useIsAuthenticated when logOut (from useAccount.logOut) is called", async () => {
|
|
68
|
+
const account = await createJazzTestAccount({});
|
|
69
|
+
|
|
70
|
+
const accounts: string[] = [];
|
|
71
|
+
const updates: { isAuthenticated: boolean; accountIndex: number }[] = [];
|
|
72
|
+
|
|
73
|
+
const { result } = renderHook(
|
|
74
|
+
() => {
|
|
75
|
+
const isAuthenticated = useIsAuthenticated();
|
|
76
|
+
const account = useAccount();
|
|
77
|
+
|
|
78
|
+
if (account.me) {
|
|
79
|
+
if (!accounts.includes(account.me.$jazz.id)) {
|
|
80
|
+
accounts.push(account.me.$jazz.id);
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
updates.push({
|
|
84
|
+
isAuthenticated,
|
|
85
|
+
accountIndex: accounts.indexOf(account.me.$jazz.id),
|
|
86
|
+
});
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
return { isAuthenticated, account };
|
|
90
|
+
},
|
|
91
|
+
{
|
|
92
|
+
account,
|
|
93
|
+
isAuthenticated: true,
|
|
94
|
+
},
|
|
95
|
+
);
|
|
96
|
+
|
|
97
|
+
expect(result.current?.isAuthenticated).toBe(true);
|
|
98
|
+
expect(result.current?.account?.me).toBeDefined();
|
|
99
|
+
|
|
100
|
+
const id = result.current?.account?.me?.$jazz.id;
|
|
101
|
+
|
|
102
|
+
await act(async () => {
|
|
103
|
+
await result.current?.account?.logOut();
|
|
104
|
+
});
|
|
105
|
+
|
|
106
|
+
expect(result.current?.isAuthenticated).toBe(false);
|
|
107
|
+
expect(result.current?.account?.me?.$jazz.id).not.toBe(id);
|
|
108
|
+
|
|
109
|
+
expect(updates).toMatchInlineSnapshot(`
|
|
110
|
+
[
|
|
111
|
+
{
|
|
112
|
+
"accountIndex": 0,
|
|
113
|
+
"isAuthenticated": true,
|
|
114
|
+
},
|
|
115
|
+
{
|
|
116
|
+
"accountIndex": 0,
|
|
117
|
+
"isAuthenticated": false,
|
|
118
|
+
},
|
|
119
|
+
{
|
|
120
|
+
"accountIndex": 1,
|
|
121
|
+
"isAuthenticated": false,
|
|
122
|
+
},
|
|
123
|
+
]
|
|
124
|
+
`);
|
|
125
|
+
});
|
|
126
|
+
|
|
127
|
+
it("should be in sync with useIsAuthenticated when logOut (from useLogOut) is called", async () => {
|
|
68
128
|
const account = await createJazzTestAccount({});
|
|
69
129
|
|
|
70
130
|
const accounts: string[] = [];
|
|
@@ -4,7 +4,7 @@ import { mnemonicToEntropy } from "@scure/bip39";
|
|
|
4
4
|
import { AuthSecretStorage, KvStoreContext } from "jazz-tools";
|
|
5
5
|
import { afterEach, beforeEach, describe, expect, it } from "vitest";
|
|
6
6
|
import { usePassphraseAuth } from "../auth/PassphraseAuth";
|
|
7
|
-
import { useAccount } from "../hooks";
|
|
7
|
+
import { useAccount, useLogOut } from "../hooks";
|
|
8
8
|
import {
|
|
9
9
|
createJazzTestAccount,
|
|
10
10
|
createJazzTestGuest,
|
|
@@ -107,7 +107,7 @@ describe("usePassphraseAuth", () => {
|
|
|
107
107
|
expect(await result.current.signUp()).toBe(passphrase);
|
|
108
108
|
});
|
|
109
109
|
|
|
110
|
-
it("should be able to logout after sign up", async () => {
|
|
110
|
+
it("should be able to logout after sign up using useAccount.logOut", async () => {
|
|
111
111
|
const account = await createJazzTestAccount({});
|
|
112
112
|
|
|
113
113
|
const accounts: string[] = [];
|
|
@@ -177,4 +177,76 @@ describe("usePassphraseAuth", () => {
|
|
|
177
177
|
]
|
|
178
178
|
`);
|
|
179
179
|
});
|
|
180
|
+
|
|
181
|
+
it("should be able to logout after sign up using useLogout", async () => {
|
|
182
|
+
const account = await createJazzTestAccount({});
|
|
183
|
+
|
|
184
|
+
const accounts: string[] = [];
|
|
185
|
+
const updates: { state: string; accountIndex: number }[] = [];
|
|
186
|
+
|
|
187
|
+
const { result } = renderHook(
|
|
188
|
+
() => {
|
|
189
|
+
const passphraseAuth = usePassphraseAuth({ wordlist: testWordlist });
|
|
190
|
+
const account = useAccount();
|
|
191
|
+
const logOut = useLogOut();
|
|
192
|
+
|
|
193
|
+
if (account.me) {
|
|
194
|
+
if (!accounts.includes(account.me.$jazz.id)) {
|
|
195
|
+
accounts.push(account.me.$jazz.id);
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
updates.push({
|
|
199
|
+
state: passphraseAuth.state,
|
|
200
|
+
accountIndex: accounts.indexOf(account.me.$jazz.id),
|
|
201
|
+
});
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
return { passphraseAuth, account, logOut };
|
|
205
|
+
},
|
|
206
|
+
{
|
|
207
|
+
account,
|
|
208
|
+
isAuthenticated: false,
|
|
209
|
+
},
|
|
210
|
+
);
|
|
211
|
+
|
|
212
|
+
expect(result.current?.passphraseAuth.state).toBe("anonymous");
|
|
213
|
+
expect(result.current?.account?.me).toBeDefined();
|
|
214
|
+
|
|
215
|
+
const id = result.current?.account?.me?.$jazz.id;
|
|
216
|
+
|
|
217
|
+
await act(async () => {
|
|
218
|
+
await result.current?.passphraseAuth.signUp();
|
|
219
|
+
});
|
|
220
|
+
|
|
221
|
+
expect(result.current?.passphraseAuth.state).toBe("signedIn");
|
|
222
|
+
expect(result.current?.account?.me?.$jazz.id).toBe(id);
|
|
223
|
+
|
|
224
|
+
await act(async () => {
|
|
225
|
+
await result.current?.logOut();
|
|
226
|
+
});
|
|
227
|
+
|
|
228
|
+
expect(result.current?.passphraseAuth.state).toBe("anonymous");
|
|
229
|
+
expect(result.current?.account?.me?.$jazz.id).not.toBe(id);
|
|
230
|
+
|
|
231
|
+
expect(updates).toMatchInlineSnapshot(`
|
|
232
|
+
[
|
|
233
|
+
{
|
|
234
|
+
"accountIndex": 0,
|
|
235
|
+
"state": "anonymous",
|
|
236
|
+
},
|
|
237
|
+
{
|
|
238
|
+
"accountIndex": 0,
|
|
239
|
+
"state": "signedIn",
|
|
240
|
+
},
|
|
241
|
+
{
|
|
242
|
+
"accountIndex": 0,
|
|
243
|
+
"state": "anonymous",
|
|
244
|
+
},
|
|
245
|
+
{
|
|
246
|
+
"accountIndex": 1,
|
|
247
|
+
"state": "anonymous",
|
|
248
|
+
},
|
|
249
|
+
]
|
|
250
|
+
`);
|
|
251
|
+
});
|
|
180
252
|
});
|
|
@@ -21,6 +21,8 @@ import {
|
|
|
21
21
|
SubscribeRestArgs,
|
|
22
22
|
TypeSym,
|
|
23
23
|
BranchDefinition,
|
|
24
|
+
getIdFromHeader,
|
|
25
|
+
unstable_loadUnique,
|
|
24
26
|
} from "../internal.js";
|
|
25
27
|
import {
|
|
26
28
|
AnonymousJazzAgent,
|
|
@@ -320,19 +322,17 @@ export class CoList<out Item = any>
|
|
|
320
322
|
ownerID: ID<Account> | ID<Group>,
|
|
321
323
|
as?: Account | Group | AnonymousJazzAgent,
|
|
322
324
|
) {
|
|
323
|
-
|
|
325
|
+
const header = CoList._getUniqueHeader(unique, ownerID);
|
|
326
|
+
|
|
327
|
+
return getIdFromHeader(header, as);
|
|
324
328
|
}
|
|
325
329
|
|
|
326
330
|
/** @internal */
|
|
327
|
-
static
|
|
328
|
-
this: CoValueClass<L>,
|
|
331
|
+
static _getUniqueHeader(
|
|
329
332
|
unique: CoValueUniqueness["uniqueness"],
|
|
330
333
|
ownerID: ID<Account> | ID<Group>,
|
|
331
|
-
as?: Account | Group | AnonymousJazzAgent,
|
|
332
334
|
) {
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
const header = {
|
|
335
|
+
return {
|
|
336
336
|
type: "colist" as const,
|
|
337
337
|
ruleset: {
|
|
338
338
|
type: "ownedByGroup" as const,
|
|
@@ -341,9 +341,6 @@ export class CoList<out Item = any>
|
|
|
341
341
|
meta: null,
|
|
342
342
|
uniqueness: unique,
|
|
343
343
|
};
|
|
344
|
-
const crypto =
|
|
345
|
-
as[TypeSym] === "Anonymous" ? as.node.crypto : as.$jazz.localNode.crypto;
|
|
346
|
-
return cojsonInternals.idforHeader(header, crypto) as ID<L>;
|
|
347
344
|
}
|
|
348
345
|
|
|
349
346
|
/**
|
|
@@ -378,29 +375,24 @@ export class CoList<out Item = any>
|
|
|
378
375
|
resolve?: RefsToResolveStrict<L, R>;
|
|
379
376
|
},
|
|
380
377
|
): Promise<Resolved<L, R> | null> {
|
|
381
|
-
const
|
|
378
|
+
const header = CoList._getUniqueHeader(
|
|
382
379
|
options.unique,
|
|
383
380
|
options.owner.$jazz.id,
|
|
384
|
-
options.owner.$jazz.loadedAs,
|
|
385
381
|
);
|
|
386
|
-
let list: Resolved<L, R> | null = await loadCoValueWithoutMe(this, listId, {
|
|
387
|
-
...options,
|
|
388
|
-
loadAs: options.owner.$jazz.loadedAs,
|
|
389
|
-
skipRetry: true,
|
|
390
|
-
});
|
|
391
|
-
if (!list) {
|
|
392
|
-
list = (this as any).create(options.value, {
|
|
393
|
-
owner: options.owner,
|
|
394
|
-
unique: options.unique,
|
|
395
|
-
}) as Resolved<L, R>;
|
|
396
|
-
} else {
|
|
397
|
-
(list as L).$jazz.applyDiff(options.value);
|
|
398
|
-
}
|
|
399
382
|
|
|
400
|
-
return
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
383
|
+
return unstable_loadUnique(this, {
|
|
384
|
+
header,
|
|
385
|
+
owner: options.owner,
|
|
386
|
+
resolve: options.resolve,
|
|
387
|
+
onCreateWhenMissing: () => {
|
|
388
|
+
(this as any).create(options.value, {
|
|
389
|
+
owner: options.owner,
|
|
390
|
+
unique: options.unique,
|
|
391
|
+
});
|
|
392
|
+
},
|
|
393
|
+
onUpdateWhenFound(value) {
|
|
394
|
+
value.$jazz.applyDiff(options.value);
|
|
395
|
+
},
|
|
404
396
|
});
|
|
405
397
|
}
|
|
406
398
|
|
|
@@ -411,7 +403,10 @@ export class CoList<out Item = any>
|
|
|
411
403
|
* @param options Additional options for loading the CoList.
|
|
412
404
|
* @returns The loaded CoList, or null if unavailable.
|
|
413
405
|
*/
|
|
414
|
-
static loadUnique<
|
|
406
|
+
static async loadUnique<
|
|
407
|
+
L extends CoList,
|
|
408
|
+
const R extends RefsToResolve<L> = true,
|
|
409
|
+
>(
|
|
415
410
|
this: CoValueClass<L>,
|
|
416
411
|
unique: CoValueUniqueness["uniqueness"],
|
|
417
412
|
ownerID: ID<Account> | ID<Group>,
|
|
@@ -420,11 +415,19 @@ export class CoList<out Item = any>
|
|
|
420
415
|
loadAs?: Account | AnonymousJazzAgent;
|
|
421
416
|
},
|
|
422
417
|
): Promise<Resolved<L, R> | null> {
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
);
|
|
418
|
+
const header = CoList._getUniqueHeader(unique, ownerID);
|
|
419
|
+
|
|
420
|
+
const owner = await Group.load(ownerID, {
|
|
421
|
+
loadAs: options?.loadAs,
|
|
422
|
+
});
|
|
423
|
+
|
|
424
|
+
if (!owner) return owner;
|
|
425
|
+
|
|
426
|
+
return unstable_loadUnique(this, {
|
|
427
|
+
header,
|
|
428
|
+
owner,
|
|
429
|
+
resolve: options?.resolve,
|
|
430
|
+
});
|
|
428
431
|
}
|
|
429
432
|
|
|
430
433
|
// Override mutation methods defined on Array, as CoLists aren't meant to be mutated directly
|