@solarpunkltd/swarm-id 0.8.1 → 0.9.0
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 +17 -7
- package/dist/bus/messages.d.ts +2 -2
- package/dist/chunks/{chat-binding-DO5aGhPl.js → chat-binding-BirKsDU3.js} +9 -9
- package/dist/chunks/{chat-binding-DO5aGhPl.js.map → chat-binding-BirKsDU3.js.map} +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/internal.d.ts +3 -2
- package/dist/internal.esm.js +1 -1
- package/dist/internal.esm.js.map +1 -1
- package/dist/schemas.d.ts +12 -5
- package/dist/swarm-id-button-frame.d.ts +77 -0
- package/dist/swarm-id-client.d.ts +64 -69
- package/dist/swarm-id-proxy.d.ts +36 -47
- package/dist/swarm-id.esm.js +1 -1
- package/dist/swarm-id.esm.js.map +1 -1
- package/dist/sync/device-state.d.ts +2 -1
- package/dist/types.d.ts +346 -64
- package/dist/utils/button-view.d.ts +16 -0
- package/dist/utils/postage-stamp-association.d.ts +4 -3
- package/dist/utils/storage-probe.d.ts +20 -10
- package/package.json +24 -23
package/dist/schemas.d.ts
CHANGED
|
@@ -59,6 +59,8 @@ export declare const ChatBindingSchema: z.ZodObject<{
|
|
|
59
59
|
message: z.ZodString;
|
|
60
60
|
signature: z.ZodString;
|
|
61
61
|
}, z.core.$strip>;
|
|
62
|
+
/** The stamp choice of an app the person set to use no stamp at all */
|
|
63
|
+
export declare const NO_POSTAGE_STAMP = "none";
|
|
62
64
|
/**
|
|
63
65
|
* Connected App Schema V1.
|
|
64
66
|
*
|
|
@@ -73,8 +75,9 @@ export declare const ConnectedAppSchemaV1: z.ZodObject<{
|
|
|
73
75
|
appDescription: z.ZodOptional<z.ZodString>;
|
|
74
76
|
connectedUntil: z.ZodOptional<z.ZodNumber>;
|
|
75
77
|
appSecret: z.ZodOptional<z.ZodString>;
|
|
76
|
-
postageStampBatchID: z.ZodOptional<z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string
|
|
78
|
+
postageStampBatchID: z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"none">, z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string>>]>>;
|
|
77
79
|
postageStampBatchIDAt: z.ZodOptional<z.ZodNumber>;
|
|
80
|
+
stampPending: z.ZodOptional<z.ZodLiteral<true>>;
|
|
78
81
|
revokedAt: z.ZodOptional<z.ZodNumber>;
|
|
79
82
|
disconnectedAt: z.ZodOptional<z.ZodNumber>;
|
|
80
83
|
chatBinding: z.ZodOptional<z.ZodObject<{
|
|
@@ -202,8 +205,9 @@ export declare const SyncedAccountSchemaV1: z.ZodObject<{
|
|
|
202
205
|
appDescription: z.ZodOptional<z.ZodString>;
|
|
203
206
|
connectedUntil: z.ZodOptional<z.ZodNumber>;
|
|
204
207
|
appSecret: z.ZodOptional<z.ZodString>;
|
|
205
|
-
postageStampBatchID: z.ZodOptional<z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string
|
|
208
|
+
postageStampBatchID: z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"none">, z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string>>]>>;
|
|
206
209
|
postageStampBatchIDAt: z.ZodOptional<z.ZodNumber>;
|
|
210
|
+
stampPending: z.ZodOptional<z.ZodLiteral<true>>;
|
|
207
211
|
revokedAt: z.ZodOptional<z.ZodNumber>;
|
|
208
212
|
disconnectedAt: z.ZodOptional<z.ZodNumber>;
|
|
209
213
|
chatBinding: z.ZodOptional<z.ZodObject<{
|
|
@@ -268,8 +272,9 @@ declare const SignedInAccountSchemaV1: z.ZodObject<{
|
|
|
268
272
|
appDescription: z.ZodOptional<z.ZodString>;
|
|
269
273
|
connectedUntil: z.ZodOptional<z.ZodNumber>;
|
|
270
274
|
appSecret: z.ZodOptional<z.ZodString>;
|
|
271
|
-
postageStampBatchID: z.ZodOptional<z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string
|
|
275
|
+
postageStampBatchID: z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"none">, z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string>>]>>;
|
|
272
276
|
postageStampBatchIDAt: z.ZodOptional<z.ZodNumber>;
|
|
277
|
+
stampPending: z.ZodOptional<z.ZodLiteral<true>>;
|
|
273
278
|
revokedAt: z.ZodOptional<z.ZodNumber>;
|
|
274
279
|
disconnectedAt: z.ZodOptional<z.ZodNumber>;
|
|
275
280
|
chatBinding: z.ZodOptional<z.ZodObject<{
|
|
@@ -392,8 +397,9 @@ export declare const LocalAccountSchemaV1: z.ZodUnion<readonly [z.ZodObject<{
|
|
|
392
397
|
appDescription: z.ZodOptional<z.ZodString>;
|
|
393
398
|
connectedUntil: z.ZodOptional<z.ZodNumber>;
|
|
394
399
|
appSecret: z.ZodOptional<z.ZodString>;
|
|
395
|
-
postageStampBatchID: z.ZodOptional<z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string
|
|
400
|
+
postageStampBatchID: z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"none">, z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string>>]>>;
|
|
396
401
|
postageStampBatchIDAt: z.ZodOptional<z.ZodNumber>;
|
|
402
|
+
stampPending: z.ZodOptional<z.ZodLiteral<true>>;
|
|
397
403
|
revokedAt: z.ZodOptional<z.ZodNumber>;
|
|
398
404
|
disconnectedAt: z.ZodOptional<z.ZodNumber>;
|
|
399
405
|
chatBinding: z.ZodOptional<z.ZodObject<{
|
|
@@ -528,8 +534,9 @@ export declare const AccountStateSnapshotSchemaV1: z.ZodObject<{
|
|
|
528
534
|
appDescription: z.ZodOptional<z.ZodString>;
|
|
529
535
|
connectedUntil: z.ZodOptional<z.ZodNumber>;
|
|
530
536
|
appSecret: z.ZodOptional<z.ZodString>;
|
|
531
|
-
postageStampBatchID: z.ZodOptional<z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string
|
|
537
|
+
postageStampBatchID: z.ZodOptional<z.ZodUnion<readonly [z.ZodLiteral<"none">, z.ZodPipe<z.ZodString, z.ZodTransform<BeeBatchId, string>>]>>;
|
|
532
538
|
postageStampBatchIDAt: z.ZodOptional<z.ZodNumber>;
|
|
539
|
+
stampPending: z.ZodOptional<z.ZodLiteral<true>>;
|
|
533
540
|
revokedAt: z.ZodOptional<z.ZodNumber>;
|
|
534
541
|
disconnectedAt: z.ZodOptional<z.ZodNumber>;
|
|
535
542
|
chatBinding: z.ZodOptional<z.ZodObject<{
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
import type { SiteAllowList } from "./utils/site-allow-list";
|
|
2
|
+
export interface ButtonFrameConfig {
|
|
3
|
+
/**
|
|
4
|
+
* The sites this frame serves (docs/Site-Allow-List.md), the same list the
|
|
5
|
+
* session frame asks. A site it refuses gets no button.
|
|
6
|
+
*/
|
|
7
|
+
siteAllowList: SiteAllowList;
|
|
8
|
+
/** Take font files over http on localhost, which only a development build does */
|
|
9
|
+
allowLocalHttp?: boolean;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* The visible Swarm ID button a site mounts with `SwarmIdClient.mountButton`.
|
|
13
|
+
*
|
|
14
|
+
* It exists because a frame may open a window only from a click inside it.
|
|
15
|
+
* A site on another site than Swarm ID gets a session frame whose storage is
|
|
16
|
+
* partitioned from the connect window's, so the only way in is a handover the
|
|
17
|
+
* window posts to Swarm ID's frames on the page that opened it, and a window
|
|
18
|
+
* the site's page opens has no such page to post to. The click therefore
|
|
19
|
+
* happens here: this frame opens the window and is its opener, and tells the
|
|
20
|
+
* session frame beside it the window's challenge, so it takes the handover
|
|
21
|
+
* that comes back under it (the window side is `ui/src/lib/handover-targets.ts`).
|
|
22
|
+
* Both frames are Swarm ID's origin under the same top-level site, so they
|
|
23
|
+
* share the partition, and nothing passes the site's page. Every check on the
|
|
24
|
+
* handover stays in the session frame (`SwarmIdProxy.handlePopupMessage`).
|
|
25
|
+
*/
|
|
26
|
+
export declare class SwarmIdButtonFrame {
|
|
27
|
+
private readonly options;
|
|
28
|
+
private readonly container;
|
|
29
|
+
private parentOrigin;
|
|
30
|
+
private identifyReceived;
|
|
31
|
+
private action;
|
|
32
|
+
private config;
|
|
33
|
+
private metadata;
|
|
34
|
+
private popupMode;
|
|
35
|
+
private storageShared;
|
|
36
|
+
private connectWindow;
|
|
37
|
+
private watchStart;
|
|
38
|
+
private watchInterval;
|
|
39
|
+
private button;
|
|
40
|
+
/** Font files asked for, so each is fetched, and reported, once */
|
|
41
|
+
private readonly requestedFonts;
|
|
42
|
+
private readonly onMessage;
|
|
43
|
+
constructor(options: ButtonFrameConfig, container: HTMLElement);
|
|
44
|
+
destroy(): void;
|
|
45
|
+
private handleMessage;
|
|
46
|
+
private handleIdentify;
|
|
47
|
+
private handleUpdate;
|
|
48
|
+
/**
|
|
49
|
+
* Loads the site's font files into this frame. The label already names the
|
|
50
|
+
* family, so it changes once a file arrives, and keeps the fallback family
|
|
51
|
+
* when one does not. The fetch is cross-origin, so the site serves the file
|
|
52
|
+
* with an `Access-Control-Allow-Origin` naming Swarm ID's origin.
|
|
53
|
+
*/
|
|
54
|
+
private loadFontFaces;
|
|
55
|
+
private render;
|
|
56
|
+
/**
|
|
57
|
+
* Opens the connect window from the person's click, which is what lets the
|
|
58
|
+
* browser open it at all. The window looks for the challenge in its own
|
|
59
|
+
* storage to learn whether the session frame reads that storage, so it goes
|
|
60
|
+
* there first only when this frame can open what the first-party pages
|
|
61
|
+
* sealed (`isStorageShared`). Otherwise the window hands the session over,
|
|
62
|
+
* and the session frames are told the challenge once the window is open, so
|
|
63
|
+
* they take the handover that comes back under it.
|
|
64
|
+
*/
|
|
65
|
+
private openConnectWindow;
|
|
66
|
+
private watchWindow;
|
|
67
|
+
private stopWatchingWindow;
|
|
68
|
+
/**
|
|
69
|
+
* Every other frame of the parent page, on Swarm ID's own origin only, so
|
|
70
|
+
* the browser delivers it to Swarm ID's frames and drops it for the site's.
|
|
71
|
+
*/
|
|
72
|
+
private tellSessionFrames;
|
|
73
|
+
private tellWindowState;
|
|
74
|
+
private tellParent;
|
|
75
|
+
}
|
|
76
|
+
/** Starts the button frame, as `initProxy` starts the session frame */
|
|
77
|
+
export declare function initButtonFrame(config: ButtonFrameConfig, container: HTMLElement): SwarmIdButtonFrame;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { ClientOptions, ConnectOptions, AuthStatus, Avatar, ConnectionInfo, UploadResult, FileData, UploadOptions, UploadFilesOptions, CollectionFileInput, CollectionEntry, ActUploadOptions, DownloadOptions, RequestOptions, Reference, SOCReader, SOCWriter, FeedReaderOptions, FeedWriterOptions, FeedReader, FeedWriter, SequentialFeedReaderOptions, SequentialFeedWriterOptions, SequentialFeedReader, SequentialFeedWriter, StampChunkInput, StampedChunk, PostageBatch } from "./types";
|
|
1
|
+
import type { ClientOptions, ConnectOptions, AuthStatus, Avatar, ConnectionInfo, UploadResult, FileData, UploadOptions, UploadFilesOptions, CollectionFileInput, CollectionEntry, ActUploadOptions, DownloadOptions, RequestOptions, Reference, SOCReader, SOCWriter, FeedReaderOptions, FeedWriterOptions, FeedReader, FeedWriter, SequentialFeedReaderOptions, SequentialFeedWriterOptions, SequentialFeedReader, SequentialFeedWriter, StampChunkInput, StampedChunk, MountButtonOptions, MountedButton, PostageBatch } from "./types";
|
|
2
2
|
import { EthAddress, PrivateKey } from "@ethersphere/bee-js";
|
|
3
3
|
/**
|
|
4
4
|
* Main client library for integrating Swarm ID authentication and storage capabilities
|
|
@@ -45,8 +45,8 @@ export declare class SwarmIdClient {
|
|
|
45
45
|
private iframeLoadReject?;
|
|
46
46
|
private popupMode;
|
|
47
47
|
private metadata;
|
|
48
|
-
|
|
49
|
-
private
|
|
48
|
+
/** Each mounted button, with what removes its frame at once */
|
|
49
|
+
private mountedButtons;
|
|
50
50
|
private subsidisedGatewayUrl?;
|
|
51
51
|
private beeApiUrl?;
|
|
52
52
|
private ready;
|
|
@@ -80,22 +80,11 @@ export declare class SwarmIdClient {
|
|
|
80
80
|
* @param options.iframePath - The path to the proxy iframe (defaults to "/proxy")
|
|
81
81
|
* @param options.timeout - Request timeout in milliseconds (defaults to 30000). Bounds each call's whole round trip through the iframe; a call's own `requestOptions.timeout` replaces it for that call
|
|
82
82
|
* @param options.onConnectionChange - Callback invoked when the dApp-visible ConnectionInfo changes (identity, stamp, account type, auth)
|
|
83
|
-
* @param options.popupMode - How
|
|
83
|
+
* @param options.popupMode - How the connect window opens, from {@link connect} or a mounted button: "popup" or "window" (defaults to "window")
|
|
84
84
|
* @param options.metadata - Application metadata shown to users during authentication
|
|
85
85
|
* @param options.metadata.name - Application name (1-100 characters)
|
|
86
86
|
* @param options.metadata.description - Optional application description (max 500 characters)
|
|
87
87
|
* @param options.metadata.icon - Optional application icon as a data URL (SVG or PNG, max 4KB)
|
|
88
|
-
* @param options.buttonConfig - Button configuration for the authentication UI (optional)
|
|
89
|
-
* @param options.buttonConfig.connectText - Text for the connect button (optional)
|
|
90
|
-
* @param options.buttonConfig.disconnectText - Text for the disconnect button (optional)
|
|
91
|
-
* @param options.buttonConfig.loadingText - Text shown during loading (optional)
|
|
92
|
-
* @param options.buttonConfig.backgroundColor - Background color for buttons (optional)
|
|
93
|
-
* @param options.buttonConfig.color - Text color for buttons (optional)
|
|
94
|
-
* @param options.buttonConfig.borderRadius - Border radius for buttons and iframe (optional)
|
|
95
|
-
* @param options.buttonConfig.fontFamily - CSS font-family for the button, so it can match the embedding page; a font stack falls back as usual (optional)
|
|
96
|
-
* @param options.buttonConfig.fontSize - CSS font-size for the button; the default floating iframe is a fixed 300x50 px and hides its overflow, so a size that does not fit is clipped — pass `containerId` to own the box (optional)
|
|
97
|
-
* @param options.buttonConfig.fontWeight - CSS font-weight for the button, as a keyword or a number (optional)
|
|
98
|
-
* @param options.containerId - ID of container element to place iframe in (optional)
|
|
99
88
|
* @param options.subsidisedGatewayUrl - A gateway that stamps uploads for a person with no drive of their own (optional)
|
|
100
89
|
* @param options.beeApiUrl - The Bee node this site's content reads and stamped uploads go through, in place of the person's own setting. Their account and device coordination stay on their own node. Change it later with {@link setBeeApiUrl} (optional)
|
|
101
90
|
* @throws {Error} If constructed where there is no `window` (a server render)
|
|
@@ -112,7 +101,6 @@ export declare class SwarmIdClient {
|
|
|
112
101
|
*
|
|
113
102
|
* @returns A promise that resolves when the client is fully initialized
|
|
114
103
|
* @throws {SwarmIdError} `invalid-state` if the client is already initialized, or `destroy()` runs before it resolves
|
|
115
|
-
* @throws {SwarmIdError} `invalid-request` if `containerId` names no element
|
|
116
104
|
* @throws {SwarmIdError} `init-failed` if the iframe fails to load, origin validation fails on the proxy side, or the proxy does not respond within `initializationTimeout` (30 seconds by default)
|
|
117
105
|
*
|
|
118
106
|
* @example
|
|
@@ -172,25 +160,6 @@ export declare class SwarmIdClient {
|
|
|
172
160
|
* Ensure client is initialized
|
|
173
161
|
*/
|
|
174
162
|
private ensureReady;
|
|
175
|
-
/**
|
|
176
|
-
* Returns the authentication iframe element.
|
|
177
|
-
*
|
|
178
|
-
* The iframe displays authentication UI based on the current auth status:
|
|
179
|
-
* - If not authenticated: shows a "Connect" button
|
|
180
|
-
* - If authenticated: shows identity info and a "Disconnect" button
|
|
181
|
-
*
|
|
182
|
-
* The iframe is positioned fixed in the bottom-right corner of the viewport.
|
|
183
|
-
*
|
|
184
|
-
* @returns The iframe element displaying the authentication UI
|
|
185
|
-
* @throws {SwarmIdError} `invalid-state` if the client is not initialized, or the iframe is not available
|
|
186
|
-
*
|
|
187
|
-
* @example
|
|
188
|
-
* ```typescript
|
|
189
|
-
* const iframe = client.getAuthIframe()
|
|
190
|
-
* // The iframe is already displayed; this returns a reference to it
|
|
191
|
-
* ```
|
|
192
|
-
*/
|
|
193
|
-
getAuthIframe(): HTMLIFrameElement;
|
|
194
163
|
/**
|
|
195
164
|
* Checks the current authentication status with the Swarm ID proxy.
|
|
196
165
|
*
|
|
@@ -280,52 +249,78 @@ export declare class SwarmIdClient {
|
|
|
280
249
|
*/
|
|
281
250
|
disconnect(): Promise<void>;
|
|
282
251
|
/**
|
|
283
|
-
* Opens the Swarm ID
|
|
284
|
-
*
|
|
285
|
-
*
|
|
286
|
-
*
|
|
287
|
-
*
|
|
288
|
-
*
|
|
289
|
-
*
|
|
290
|
-
*
|
|
291
|
-
*
|
|
292
|
-
*
|
|
293
|
-
*
|
|
294
|
-
*
|
|
295
|
-
* - Partitioned, or not proven shared: the proxy opens it, so the popup's
|
|
296
|
-
* `window.opener` points back at the iframe and the session can be handed
|
|
297
|
-
* over directly — the only channel into a partitioned frame. The session
|
|
298
|
-
* is then kept in that partition's own store until it is disconnected or
|
|
299
|
-
* its 7 days are up (#635), so a reload does not re-run this; a handover
|
|
300
|
-
* that arrives without the account view is refused outright rather than
|
|
301
|
-
* producing a session that cannot upload and cannot hear a revoke. A popup
|
|
302
|
-
* blocked on this path falls back to opening from the parent.
|
|
303
|
-
*
|
|
304
|
-
* Safari private mode sessions are ephemeral (lost when the private window
|
|
305
|
-
* closes). The whole partitioned path — handover, stamper, upload — is
|
|
306
|
-
* confirmed on real Safari; see
|
|
307
|
-
* https://github.com/snaha/swarm-id/issues/584
|
|
252
|
+
* Opens the Swarm ID connect window from the site's own control, where the
|
|
253
|
+
* session frame shares Swarm ID's storage: a site on the same site as Swarm
|
|
254
|
+
* ID, such as a self-hosted copy on the site's own domain. The window
|
|
255
|
+
* writes the connection to that storage and the session frame picks it up.
|
|
256
|
+
*
|
|
257
|
+
* Anywhere else the browser partitions the session frame's storage, and the
|
|
258
|
+
* session can reach it only through a window a Swarm ID frame opened from a
|
|
259
|
+
* click inside it. A window opened from here would end on "Connected" with
|
|
260
|
+
* the site still signed out, so this refuses instead and the site shows
|
|
261
|
+
* {@link mountButton}'s button. `connectionInfo.storagePartitioned` and the
|
|
262
|
+
* error's code tell the two apart. The button works in both cases, so a
|
|
263
|
+
* site that always mounts it never needs this.
|
|
308
264
|
*
|
|
309
265
|
* @param options - Configuration options for the connect flow
|
|
310
266
|
* @throws {SwarmIdError} `invalid-state` if the client is not initialized
|
|
311
|
-
* @throws {SwarmIdError} `
|
|
267
|
+
* @throws {SwarmIdError} `button-required` if the session frame's storage is partitioned, or not proven shared
|
|
268
|
+
* @throws {SwarmIdError} `popup-blocked` if the browser blocks the window
|
|
312
269
|
*
|
|
313
270
|
* @example
|
|
314
271
|
* ```typescript
|
|
315
|
-
*
|
|
316
|
-
*
|
|
317
|
-
*
|
|
318
|
-
*
|
|
319
|
-
*
|
|
272
|
+
* try {
|
|
273
|
+
* await client.connect()
|
|
274
|
+
* } catch (error) {
|
|
275
|
+
* if (error instanceof SwarmIdError && error.code === 'button-required') {
|
|
276
|
+
* client.mountButton(container, { action: 'sign-in' })
|
|
277
|
+
* }
|
|
278
|
+
* }
|
|
320
279
|
* ```
|
|
321
280
|
*/
|
|
322
281
|
connect(options?: ConnectOptions): Promise<void>;
|
|
323
282
|
/**
|
|
324
|
-
*
|
|
283
|
+
* Shows a Swarm ID button in `container`: a small frame of Swarm ID's own,
|
|
284
|
+
* apart from the hidden session frame, that fills the container. Its click
|
|
285
|
+
* opens the connect window, which hands the session to the site's Swarm ID
|
|
286
|
+
* frames, and the site hears of it on {@link ClientOptions.onConnectionChange} as from
|
|
287
|
+
* any sign-in. This is how a person signs in, or changes the stamp the
|
|
288
|
+
* site uses, wherever the site and Swarm ID are on different sites.
|
|
289
|
+
*
|
|
290
|
+
* Unmounting removes only the button, at any time. The session stays, and
|
|
291
|
+
* signing out stays {@link disconnect}. A button unmounted while its window
|
|
292
|
+
* is open stays hidden until the window closes, because the window reads
|
|
293
|
+
* from it, as it opens, where to hand the session. Unmounting it, or
|
|
294
|
+
* removing its container, in the moment between the click and the window
|
|
295
|
+
* opening loses that sign-in, and the person signs in again.
|
|
296
|
+
*
|
|
297
|
+
* @param container - The element the button fills. Give it the size the button should have
|
|
298
|
+
* @param options.action - `sign-in`, or `change-stamp` for a person signed in
|
|
299
|
+
* @param options.config - The label, its busy and disabled states, colours and typography
|
|
300
|
+
* @param options.onWindowChange - Called with `open`, `closed` or `blocked` for the button's connect window
|
|
301
|
+
* @returns The button: `ready`, `update()` and `unmount()`, where `update()` refuses a bad value the same way
|
|
302
|
+
* @throws {SwarmIdError} `invalid-state` if the client is not initialized
|
|
303
|
+
* @throws {SwarmIdError} `invalid-request` if `action` or a `config` value is not one the button takes, naming the field
|
|
304
|
+
*
|
|
305
|
+
* @example
|
|
306
|
+
* ```typescript
|
|
307
|
+
* const button = client.mountButton(document.getElementById('sign-in')!, {
|
|
308
|
+
* action: 'sign-in',
|
|
309
|
+
* config: { text: 'Sign in', backgroundColor: '#000', borderRadius: '6px' },
|
|
310
|
+
* })
|
|
311
|
+
* await button.ready
|
|
312
|
+
* // later, closing the panel it sits in
|
|
313
|
+
* button.unmount()
|
|
314
|
+
* ```
|
|
315
|
+
*/
|
|
316
|
+
mountButton(container: HTMLElement, options: MountButtonOptions): MountedButton;
|
|
317
|
+
/**
|
|
318
|
+
* Open the connect window from the site's page, for a session frame that
|
|
319
|
+
* shares Swarm ID's storage.
|
|
325
320
|
*
|
|
326
|
-
* Carries no challenge: a
|
|
321
|
+
* Carries no challenge: a window opened here has the site's page as its
|
|
327
322
|
* `window.opener`, so there is nothing for a handover to attach to, and the
|
|
328
|
-
*
|
|
323
|
+
* window writes the connection to the storage the session frame reads.
|
|
329
324
|
*
|
|
330
325
|
* @returns whether the popup opened — a blocked one returns null, which the
|
|
331
326
|
* caller must not report as a connect in progress.
|
package/dist/swarm-id-proxy.d.ts
CHANGED
|
@@ -8,7 +8,8 @@ export declare const PUBLISH_DEBOUNCE_MS = 1500;
|
|
|
8
8
|
* Swarm ID Proxy - Runs inside the iframe
|
|
9
9
|
*
|
|
10
10
|
* Responsibilities:
|
|
11
|
-
* - Receive app-specific secrets from
|
|
11
|
+
* - Receive app-specific secrets from the connect popup the button frame beside
|
|
12
|
+
* it opened, under the challenge that frame told it
|
|
12
13
|
* - Keep a partitioned session in this partition's own localStorage (#635)
|
|
13
14
|
* - Proxy Bee API calls from parent dApp
|
|
14
15
|
* - Augment requests with authentication
|
|
@@ -25,7 +26,6 @@ export declare class SwarmIdProxy {
|
|
|
25
26
|
private parentIdentifyReceived;
|
|
26
27
|
private siteAllowList;
|
|
27
28
|
private authenticated;
|
|
28
|
-
private authLoading;
|
|
29
29
|
private appSecret;
|
|
30
30
|
/**
|
|
31
31
|
* The chat binding the popup handed over with this session, already checked
|
|
@@ -48,6 +48,14 @@ export declare class SwarmIdProxy {
|
|
|
48
48
|
private stampWorkerPool;
|
|
49
49
|
private storagePartitioned;
|
|
50
50
|
private pendingChallenge;
|
|
51
|
+
/**
|
|
52
|
+
* The challenge of the connect window whose handover this session came
|
|
53
|
+
* from. That window asks for the site's stamp after it handed over, and a
|
|
54
|
+
* stamp picked there reaches this frame as a second handover under the same
|
|
55
|
+
* challenge (`isStampHandover`). Cleared when another window opens or the
|
|
56
|
+
* session ends, so only the newest window can do it.
|
|
57
|
+
*/
|
|
58
|
+
private handedOverChallenge;
|
|
51
59
|
/**
|
|
52
60
|
* Hydrated account view for the storage-partitioning fallback: the synced
|
|
53
61
|
* projection handed over by the connect popup (`AuthData.account`), held in
|
|
@@ -119,9 +127,6 @@ export declare class SwarmIdProxy {
|
|
|
119
127
|
private gnosisRpcUrl;
|
|
120
128
|
private postageStampContractAddress;
|
|
121
129
|
private signalingUrl;
|
|
122
|
-
private authButtonContainer;
|
|
123
|
-
private buttonConfig;
|
|
124
|
-
private popupMode;
|
|
125
130
|
private appMetadata;
|
|
126
131
|
/**
|
|
127
132
|
* Bee clients by the URL they were asked for. Keyed on that input URL, not
|
|
@@ -131,7 +136,6 @@ export declare class SwarmIdProxy {
|
|
|
131
136
|
private unsubscribeStorageListeners;
|
|
132
137
|
private storageWorkQueue;
|
|
133
138
|
private lastConnectionInfo;
|
|
134
|
-
private isConnecting;
|
|
135
139
|
private parentWindow;
|
|
136
140
|
private bus;
|
|
137
141
|
/** Who else is live in the account's room, from their `presence` beats. */
|
|
@@ -250,7 +254,8 @@ export declare class SwarmIdProxy {
|
|
|
250
254
|
* Note: We always set up these listeners, even when storage might be partitioned.
|
|
251
255
|
* In some browsers/configurations (like localhost development), storage events
|
|
252
256
|
* work between same-origin windows even in iframes. If storage IS partitioned,
|
|
253
|
-
* the listeners simply won't fire, and
|
|
257
|
+
* the listeners simply won't fire, and the connect popup the button frame
|
|
258
|
+
* opened hands the session over by postMessage instead.
|
|
254
259
|
*/
|
|
255
260
|
private setupStorageListeners;
|
|
256
261
|
/**
|
|
@@ -330,28 +335,34 @@ export declare class SwarmIdProxy {
|
|
|
330
335
|
*/
|
|
331
336
|
private authenticateFromStorage;
|
|
332
337
|
/**
|
|
333
|
-
*
|
|
334
|
-
*
|
|
338
|
+
* A handover from a connect window the button frame beside this one opened.
|
|
339
|
+
* The only way into a session whose storage is partitioned from the
|
|
340
|
+
* window's, where no storage event arrives.
|
|
335
341
|
*/
|
|
336
342
|
private handlePopupMessage;
|
|
337
343
|
/**
|
|
338
|
-
*
|
|
339
|
-
*
|
|
340
|
-
* The popup cannot be told it was refused — there is no channel back — so it
|
|
341
|
-
* shows "Connected!" while the button here spins on, and the only other
|
|
342
|
-
* thing that ever cleared the flag was the user closing that popup
|
|
343
|
-
* (`checkPopupClosed`), which nothing gave them a reason to do.
|
|
344
|
-
*
|
|
345
|
-
* `isConnecting` first: `showAuthButton` early-returns while it is set, so
|
|
346
|
-
* clearing the flag is what lets the button come back. `authLoading` is
|
|
347
|
-
* already false on every path that reaches here — belt-and-braces, not a
|
|
348
|
-
* second fix.
|
|
349
|
-
*
|
|
350
|
-
* The challenge is deliberately kept. The popup is still open and may yet
|
|
351
|
-
* send a payload this bundle can read; refusing one message ends the
|
|
352
|
-
* attempt's spinner, not the ceremony behind it.
|
|
344
|
+
* Whether a message came from another frame of the page this one is in,
|
|
345
|
+
* which is where the button frame sits. A top-level window is not one.
|
|
353
346
|
*/
|
|
354
|
-
private
|
|
347
|
+
private isSiblingFrame;
|
|
348
|
+
/**
|
|
349
|
+
* The button frame beside this one opened a connect window under
|
|
350
|
+
* `challenge`, so the handover that comes back under it is this session's
|
|
351
|
+
* to take. A window opened before it can no longer hand over a stamp.
|
|
352
|
+
*/
|
|
353
|
+
private awaitHandover;
|
|
354
|
+
/**
|
|
355
|
+
* A second handover from the window this session was handed over by,
|
|
356
|
+
* carrying the stamp the person picked there after the first one. Accepted
|
|
357
|
+
* only for that window's challenge, this parent and this session's secret,
|
|
358
|
+
* so it can move the open session to the stamp the person picked and to
|
|
359
|
+
* nothing else: not another account, not another site, not a session that
|
|
360
|
+
* has ended. Which stamp it is was decided in that window, from the
|
|
361
|
+
* account's own record.
|
|
362
|
+
*/
|
|
363
|
+
private isStampHandover;
|
|
364
|
+
/** Authenticate in storage-partitioned mode from a checked handover */
|
|
365
|
+
private adoptHandover;
|
|
355
366
|
/**
|
|
356
367
|
* The handed-over chat binding, if it names exactly this parent origin, the
|
|
357
368
|
* address of the chat key of the secret it came with and the account it came
|
|
@@ -903,28 +914,6 @@ export declare class SwarmIdProxy {
|
|
|
903
914
|
private handleIsConnected;
|
|
904
915
|
private handleGetNodeInfo;
|
|
905
916
|
private handleDisconnect;
|
|
906
|
-
/**
|
|
907
|
-
* Show authentication button in the UI
|
|
908
|
-
*/
|
|
909
|
-
private showAuthButton;
|
|
910
|
-
private handleConnect;
|
|
911
|
-
/**
|
|
912
|
-
* Open the authentication popup window.
|
|
913
|
-
* Returns true if popup was opened, false if parent origin is not set.
|
|
914
|
-
*/
|
|
915
|
-
private openAuthPopup;
|
|
916
|
-
/**
|
|
917
|
-
* Handle login button click
|
|
918
|
-
*/
|
|
919
|
-
private handleLoginClick;
|
|
920
|
-
/**
|
|
921
|
-
* Handle disconnect button click
|
|
922
|
-
*/
|
|
923
|
-
private handleDisconnectClick;
|
|
924
|
-
/**
|
|
925
|
-
* Set container element for auth button
|
|
926
|
-
*/
|
|
927
|
-
setAuthButtonContainer(container: HTMLElement): void;
|
|
928
917
|
private handleUploadData;
|
|
929
918
|
private handleDownloadData;
|
|
930
919
|
private handleUploadFile;
|
package/dist/swarm-id.esm.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{A as t,S as i,I as r,P as a,a as o,u as d,T as c,b as u,g as h,E as y,c as w,i as R,w as g,d as I,h as q,M as x,N as z,R as b}from"./chunks/chat-binding-DO5aGhPl.js";export{C as CHAT_BINDING_TITLE,D as DEFAULT_BEE_NODE_URL,l as acceptedChatBinding,m as buildChatBindingMessage,f as formatTTL,e as generatedAvatarSvg,n as isCleanSiteOrigin,k as jsonRpcBatch,j as jsonRpcCall,p as parseChatBindingMessage,s as saveMantarayTreeRecursively,v as verifyChatBinding}from"./chunks/chat-binding-DO5aGhPl.js";function F(e){const t=e.webkitRelativePath;return t?t.replace(/^[^/]*\//,""):e.name}function T(e,t,n){return g(e,t,n).catch(e=>{throw e instanceof I?new i("init-failed",e.message,{cause:e}):e})}function K(e){if(!R(e))throw new i("invalid-request","Invalid beeApiUrl: must be an http(s) URL, optionally with a path, and no credentials, query or fragment");return e}class U{constructor(e){if(this.ready=!1,this.pendingRequests=new Map,this.progressListeners=new Map,this.requestIdCounter=0,"undefined"==typeof window)throw new Error("@solarpunkltd/swarm-id runs in the browser only: construct SwarmIdClient in code that runs there (an effect, onMount, or behind `typeof window !== 'undefined'`), not in a server render");this.iframeOrigin=e.iframeOrigin,this.iframePath=e.iframePath||"/proxy",this.timeout=e.timeout??3e4,this.initializationTimeout=e.initializationTimeout??3e4,this.onConnectionChange=e.onConnectionChange,this.popupMode=e.popupMode||"window",this.metadata=e.metadata,this.buttonConfig=e.buttonConfig,this.containerId=e.containerId,this.subsidisedGatewayUrl=e.subsidisedGatewayUrl,void 0!==e.beeApiUrl&&(this.beeApiUrl=K(e.beeApiUrl));try{t.parse(this.metadata)}catch(e){throw new i("invalid-request",`Invalid app metadata: ${e}`,{cause:e})}this.setupMessageListener()}async initialize(){if(this.iframe)throw new i("invalid-state","SwarmIdClient already initialized");let e;if(this.firstConnectionInfoPromise=T(new Promise((e,t)=>{this.firstConnectionInfoResolve=e,this.firstConnectionInfoReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not send initial connectionInfoChanged within ${this.initializationTimeout}ms`),this.firstConnectionInfoPromise.catch(()=>{}),this.proxyInitializedPromise=T(new Promise((e,t)=>{this.proxyInitializedResolve=e,this.proxyInitializedReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not signal readiness within ${this.initializationTimeout}ms`),this.proxyInitializedPromise.catch(()=>{}),this.readyPromise=T(new Promise((e,t)=>{this.readyResolve=e,this.readyReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not respond within ${this.initializationTimeout}ms`),this.readyPromise.catch(()=>{}),this.iframe=document.createElement("iframe"),this.iframe.src=`${this.iframeOrigin}${this.iframePath}`,this.iframe.style.border="none",this.iframe.style.backgroundColor="transparent",this.iframe.style.borderRadius=this.buttonConfig?.borderRadius||"0",this.containerId){if(e=document.getElementById(this.containerId)||void 0,!e)throw new i("invalid-request",`Container element with ID "${this.containerId}" not found`);this.iframe.style.width="100%",this.iframe.style.height="100%",this.iframe.style.display="block"}else this.iframe.style.display="none",this.iframe.style.position="fixed",this.iframe.style.bottom="20px",this.iframe.style.right="20px",this.iframe.style.width="300px",this.iframe.style.height="50px",this.iframe.style.zIndex="999999";await new Promise((t,n)=>{this.iframeLoadReject=n,this.iframe.onload=()=>t(),this.iframe.onerror=()=>n(new i("init-failed","Failed to load Swarm ID iframe")),e?e.appendChild(this.iframe):document.body.appendChild(this.iframe)}),this.iframeLoadReject=void 0,await this.proxyInitializedPromise,this.sendMessage({type:"parentIdentify",requestId:this.generateRequestId(),popupMode:this.popupMode,metadata:this.metadata,buttonConfig:this.buttonConfig,subsidisedGatewayUrl:this.subsidisedGatewayUrl,beeApiUrl:this.beeApiUrl}),await this.readyPromise,await this.firstConnectionInfoPromise}setupMessageListener(){this.messageListener=e=>{if(!this.iframe||e.source!==this.iframe.contentWindow)return;if("proxyInitialized"===e.data?.type)return void(this.proxyInitializedResolve&&(this.proxyInitializedResolve(),this.proxyInitializedResolve=void 0));const t=new URL(this.iframeOrigin).origin;if(e.origin!==t)return void console.warn("[SwarmIdClient] Rejected message from unauthorized origin:",e.origin);let i;try{i=r.parse(e.data)}catch(t){return void console.warn("[SwarmIdClient] Invalid message format:",e.data,t)}this.handleIframeMessage(i)},window.addEventListener("message",this.messageListener)}handleIframeMessage(e){switch(e.type){case"proxyReady":this.ready=!0,this.storageShared=e.storageShared,this.readyResolve&&this.readyResolve(),this.iframe&&(this.iframe.style.display="block");break;case"authStatusResponse":if(this.iframe&&(this.iframe.style.display="block"),"requestId"in e){const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.resolve(e))}break;case"authSuccess":this.iframe&&(this.iframe.style.display="block");break;case"connectionInfoChanged":{const t={canUpload:e.canUpload,storagePartitioned:e.storagePartitioned,uploadMode:e.uploadMode,uploadUnavailableReason:e.uploadUnavailableReason,identity:e.identity,appKey:e.appKey,partition:e.partition,chatBinding:e.chatBinding,beeApiUrl:e.beeApiUrl};this.lastConnectionInfo=t,this.firstConnectionInfoResolve&&(this.firstConnectionInfoResolve(),this.firstConnectionInfoResolve=void 0),this.onConnectionChange&&this.onConnectionChange(t);break}case"initError":console.error("[SwarmIdClient] Proxy initialization error:",e.error),this.readyReject&&this.readyReject(new i("init-failed",e.error));break;case"disconnectResponse":if("requestId"in e){const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.resolve(e))}break;case"error":{const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.reject(i.fromWire(e)));break}case"uploadProgress":this.progressListeners.get(e.requestId)?.({total:e.total,processed:e.processed});break;default:if("requestId"in e){const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.resolve(e))}}}sendMessage(e){if(!this.iframe||!this.iframe.contentWindow)throw new i("invalid-state","Iframe not initialized");try{a.parse(e)}catch(e){throw new i("invalid-request",`Invalid message format: ${e}`,{cause:e})}this.iframe.contentWindow.postMessage(e,this.iframeOrigin)}async sendRequest(e){const t=this.roundTripTimeout(e.requestOptions?.timeout);return new Promise((n,s)=>{const r=setTimeout(()=>{this.pendingRequests.delete(e.requestId),s(new i("timeout",`Request timeout after ${t}ms`))},t);this.pendingRequests.set(e.requestId,{resolve:n,reject:s,timeoutId:r}),this.sendMessage(e)})}roundTripTimeout(e){return void 0===e||e<=0?this.timeout:Math.min(e,2147483647)}generateRequestId(){return`req-${++this.requestIdCounter}-${Date.now()}`}normalizeSocIdentifier(e){return e instanceof o?e.toHex():e instanceof Uint8Array?d(e):e}normalizeSocKey(e){return e instanceof Uint8Array?d(e):e}normalizeFeedTopic(e){return e instanceof c?d(e.toUint8Array()):e instanceof o?e.toHex():e instanceof Uint8Array?d(e):e}normalizeReference(e){return e instanceof Uint8Array?d(e):e}normalizeFeedTimestamp(e){return"bigint"==typeof e?e.toString():"number"==typeof e?BigInt(Math.floor(e)).toString():e}normalizeFeedIndex(e){return"bigint"==typeof e?e.toString():"number"==typeof e?BigInt(Math.floor(e)).toString():e}normalizePayload(e){return e instanceof Uint8Array?e:(new TextEncoder).encode(e)}socChunkFromResponse(e){return{data:e.data,identifier:e.identifier,signature:e.signature,span:e.span,payload:e.payload,address:e.address,owner:e.owner}}ensureReady(){if(!this.ready)throw new i("invalid-state","SwarmIdClient not initialized. Call initialize() first.")}getAuthIframe(){if(this.ensureReady(),!this.iframe)throw new i("invalid-state","Iframe not initialized");return this.iframe}async checkAuthStatus(){this.ensureReady();const e=this.generateRequestId(),t=await this.sendRequest({type:"checkAuth",requestId:e});return{authenticated:t.authenticated,origin:t.origin,beeApiUrl:t.beeApiUrl}}async setBeeApiUrl(e){const t=K(e);this.ensureReady(),await this.sendRequest({type:"setBeeApiUrl",requestId:this.generateRequestId(),beeApiUrl:t}),this.beeApiUrl=t}async getPostageBatch(){this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"getPostageBatch",requestId:e})).postageBatch}async disconnect(){this.ensureReady();const e=this.generateRequestId();if(!(await this.sendRequest({type:"disconnect",requestId:e})).success)throw new i("internal","Failed to disconnect")}async connect(e={}){if(this.ensureReady(),!0===this.storageShared){if(!this.openAuthWindow(e))throw new i("popup-blocked","Failed to open authentication popup");return}const t=this.generateRequestId();if(!(await this.sendRequest({type:"connect",requestId:t,popupMode:e.popupMode})).success&&!this.openAuthWindow(e))throw new i("popup-blocked","Failed to open authentication popup")}openAuthWindow(e){const t=this.iframePath.replace(/\/proxy$/,""),i=u(this.iframeOrigin+t,window.location.origin,this.metadata),n="popup"===(e.popupMode??this.popupMode)?window.open(i,"_blank","width=500,height=600"):window.open(i,"_blank");return Boolean(n)}get connectionInfo(){if(this.ensureReady(),!this.lastConnectionInfo)throw new i("invalid-state","SwarmIdClient connectionInfo not yet available.");return this.lastConnectionInfo}async getAvatar(e={}){const{identity:t}=this.connectionInfo;if(t)return void 0!==e.size&&"generated"===t.avatar.source?h(t.id,e.size):t.avatar}async isBeeConnected(){try{this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"isConnected",requestId:e})).connected}catch{return!1}}async getNodeInfo(){this.ensureReady();const e=this.generateRequestId(),t=await this.sendRequest({type:"getNodeInfo",requestId:e});return{beeMode:t.beeMode,chequebookEnabled:t.chequebookEnabled,swapEnabled:t.swapEnabled}}async uploadData(e,t,i){this.ensureReady();const n=this.generateRequestId(),{onProgress:s,useWebSocket:r,useWorkers:a,workerCount:o,concurrency:d,...c}=t??{},u=this.listenForProgress(n,s);try{const t=await this.sendRequest({type:"uploadData",requestId:n,data:new Uint8Array(e),options:c,requestOptions:i,enableProgress:!!s,useWebSocket:r,useWorkers:a,workerCount:o,concurrency:d});return{reference:t.reference,tagUid:t.tagUid}}finally{u()}}async downloadData(e,t,i){this.ensureReady();const n=this.generateRequestId();return(await this.sendRequest({type:"downloadData",requestId:n,reference:e,options:t,requestOptions:i})).data}async deriveAppSecret(e){this.ensureReady();const t=this.generateRequestId();return(await this.sendRequest({type:"deriveAppSecret",requestId:t,label:e})).secret}async getChatKey(){this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"getChatKey",requestId:e})).chatKey}async stampChunk(e){this.ensureReady();const t=this.generateRequestId(),i="soc"===e.kind?{...e,identifier:this.normalizeSocIdentifier(e.identifier),signer:"app"===e.signer?e.signer:{...e.signer,privateKey:this.normalizeSocKey(e.signer.privateKey)}}:e,n=await this.sendRequest({type:"stampChunk",requestId:t,chunk:i});return{address:n.address,stamp:n.stamp,...void 0!==n.owner&&{owner:n.owner},...void 0!==n.signature&&{signature:n.signature}}}async uploadFile(e,t,i,n){this.ensureReady();const s=this.generateRequestId(),{onProgress:r,useWebSocket:a,useWorkers:o,workerCount:d,concurrency:c,...u}=i??{};let h,p=t;if(e instanceof File){const t=await e.arrayBuffer();h=new Uint8Array(t),p=p||e.name}else h=new Uint8Array(e.buffer.slice(0),e.byteOffset,e.byteLength);const l=this.listenForProgress(s,r);try{const e=await this.sendRequest({type:"uploadFile",requestId:s,data:h,name:p,options:u,requestOptions:n,enableProgress:!!r,useWebSocket:a,useWorkers:o,workerCount:d,concurrency:c});return{reference:e.reference,tagUid:e.tagUid}}finally{l()}}async downloadFile(e,t,i,n){this.ensureReady();const s=this.generateRequestId(),r=await this.sendRequest({type:"downloadFile",requestId:s,reference:e,path:t,options:i,requestOptions:n});return{name:r.name,data:new Uint8Array(r.data)}}async uploadFiles(e,t,i){this.ensureReady();const n=this.generateRequestId(),{onProgress:s,useWorkers:r,workerCount:a,...o}=t??{},d=await Promise.all(Array.from(e,async e=>{const{path:t,file:i}=e instanceof File?{path:F(e),file:e}:e;return{path:t,data:new Uint8Array(await i.arrayBuffer()),contentType:i.type||void 0}})),c=this.listenForProgress(n,s);try{const e=await this.sendRequest({type:"uploadFiles",requestId:n,files:d,options:o,requestOptions:i,enableProgress:!!s,useWorkers:r,workerCount:a});return{reference:e.reference,tagUid:e.tagUid}}finally{c()}}async listFiles(e,t){this.ensureReady();const i=this.generateRequestId();return(await this.sendRequest({type:"listFiles",requestId:i,reference:e,requestOptions:t})).entries}listenForProgress(e,t){return t?(this.progressListeners.set(e,t),()=>{this.progressListeners.delete(e)}):()=>{}}async uploadChunk(e,t,i){this.ensureReady();const n=this.generateRequestId(),{onProgress:s,...r}=t??{};return{reference:(await this.sendRequest({type:"uploadChunk",requestId:n,data:e,options:r,requestOptions:i})).reference}}async downloadChunk(e,t,i){this.ensureReady();const n=this.generateRequestId(),s=await this.sendRequest({type:"downloadChunk",requestId:n,reference:e,options:t,requestOptions:i});return new Uint8Array(s.data)}makeSOCReader(e,t){this.ensureReady();const i=new y(e).toHex(),n=async(e,n)=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"socDownload",requestId:s,owner:i,identifier:this.normalizeSocIdentifier(e),encryptionKey:this.normalizeSocKey(n),requestOptions:t});return this.socChunkFromResponse(r)},s=async(e,n)=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"socRawDownload",requestId:s,owner:i,identifier:this.normalizeSocIdentifier(e),encryptionKey:n?this.normalizeSocKey(n):void 0,requestOptions:t});return this.socChunkFromResponse(r)};return{getOwner:async()=>i,rawDownload:(e,t)=>s(e,t),download:(e,t)=>n(e,t)}}makeSOCWriter(e,t){this.ensureReady();const i=e?new w(e):void 0,n=i?i.toHex():void 0;let s=i?i.publicKey().address().toHex():void 0;const r=async(e,i)=>{const n=this.generateRequestId(),r=await this.sendRequest({type:"socDownload",requestId:n,owner:s,identifier:this.normalizeSocIdentifier(e),encryptionKey:this.normalizeSocKey(i),requestOptions:t});return this.socChunkFromResponse(r)},a=async(e,i)=>{const n=this.generateRequestId(),r=await this.sendRequest({type:"socRawDownload",requestId:n,owner:s,identifier:this.normalizeSocIdentifier(e),encryptionKey:i?this.normalizeSocKey(i):void 0,requestOptions:t});return this.socChunkFromResponse(r)},o=async(e,i,r)=>{const a=this.generateRequestId(),o=await this.sendRequest({type:"socUpload",requestId:a,identifier:this.normalizeSocIdentifier(e),data:new Uint8Array(i),signer:n,options:r,requestOptions:t});return s=o.owner,{reference:o.reference,tagUid:o.tagUid,encryptionKey:o.encryptionKey,owner:o.owner}},d=async(e,i,r)=>{const a=this.generateRequestId(),o=await this.sendRequest({type:"socRawUpload",requestId:a,identifier:this.normalizeSocIdentifier(e),data:new Uint8Array(i),signer:n,options:r,requestOptions:t});return s=o.owner,{reference:o.reference,tagUid:o.tagUid,encryptionKey:o.encryptionKey,owner:o.owner}};return{getOwner:async()=>{if(s)return s;const e=this.generateRequestId(),t=await this.sendRequest({type:"socGetOwner",requestId:e});return s=t.owner,s},rawDownload:(e,t)=>a(e,t),download:(e,t)=>r(e,t),upload:(e,t,i)=>o(e,t,i),rawUpload:(e,t,i)=>d(e,t,i)}}makeEpochFeedReader(e,t){this.ensureReady();const i=this.normalizeFeedTopic(e.topic);let n=e.owner?new y(e.owner).toHex():void 0;const s=async e=>{const s=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),r=this.generateRequestId(),a=(await this.sendRequest({type:"epochFeedDownloadReference",requestId:r,topic:i,owner:n,at:this.normalizeFeedTimestamp(s),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0!==e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t})).reference,o=a&&a.startsWith("0x")?a.slice(2):a;return{reference:a,encryptionKey:o&&128===o.length?o.slice(64):void 0}},r=async e=>{const s=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),r=this.generateRequestId();return{reference:(await this.sendRequest({type:"epochFeedDownloadReference",requestId:r,topic:i,owner:n,at:this.normalizeFeedTimestamp(s),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0,requestOptions:t})).reference,encryptionKey:void 0}};return{getOwner:async()=>{if(n)return n;const e=this.generateRequestId(),t=await this.sendRequest({type:"feedGetOwner",requestId:e});return n=t.owner,n},downloadReference:s,downloadPayload:async e=>{const i=await s(e);if(!i.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const n=await this.downloadData(i.reference,void 0,t);return{reference:i.reference,payload:n,encryptionKey:i.encryptionKey}},downloadRawReference:r,downloadRawPayload:async e=>{const i=await r(e);if(!i.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const n=await this.downloadData(i.reference,void 0,t);return{reference:i.reference,payload:n,encryptionKey:void 0}}}}makeEpochFeedWriter(e,t){this.ensureReady();const i=this.normalizeFeedTopic(e.topic),n=e.signer?new w(e.signer):void 0,s=n?n.toHex():void 0;let r=n?n.publicKey().address().toHex():void 0;const a=async e=>{const n=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),s=this.generateRequestId(),a=(await this.sendRequest({type:"epochFeedDownloadReference",requestId:s,topic:i,owner:r,at:this.normalizeFeedTimestamp(n),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0!==e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t})).reference,o=a&&a.startsWith("0x")?a.slice(2):a;return{reference:a,encryptionKey:o&&128===o.length?o.slice(64):void 0}},o=async e=>{const n=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),s=this.generateRequestId();return{reference:(await this.sendRequest({type:"epochFeedDownloadReference",requestId:s,topic:i,owner:r,at:this.normalizeFeedTimestamp(n),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0,requestOptions:t})).reference,encryptionKey:void 0}};return{getOwner:async()=>{if(r)return r;const e=this.generateRequestId(),t=await this.sendRequest({type:"feedGetOwner",requestId:e});return r=t.owner,r},downloadReference:a,downloadPayload:async e=>{const i=await a(e);if(!i.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const n=await this.downloadData(i.reference,void 0,t);return{reference:i.reference,payload:n,encryptionKey:i.encryptionKey}},downloadRawReference:o,downloadRawPayload:async e=>{const i=await o(e);if(!i.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const n=await this.downloadData(i.reference,void 0,t);return{reference:i.reference,payload:n,encryptionKey:void 0}},uploadReference:async(e,n)=>{const r=void 0!==n?.at?n.at:BigInt(Math.floor(Date.now()/1e3)),a=this.normalizeReference(e),o=a.startsWith("0x")?a.slice(2):a,d=128===o.length?o.slice(64):void 0,c=n?.encryptionKey??d,u=this.generateRequestId(),h=await this.sendRequest({type:"epochFeedUploadReference",requestId:u,topic:i,signer:s,at:this.normalizeFeedTimestamp(r),reference:a,encryptionKey:void 0!==c?this.normalizeSocKey(c):void 0,hints:n?.hints,requestOptions:t});return{socAddress:h.socAddress,reference:a,encryptionKey:d,epoch:h.epoch,timestamp:h.timestamp}},uploadPayload:async(e,n)=>{const r=void 0!==n?.at?n.at:BigInt(Math.floor(Date.now()/1e3)),a=!1!==n?.encrypt,o=await this.uploadData(this.normalizePayload(e),{...n?.uploadOptions,encrypt:a},t),d=o.reference.startsWith("0x")?o.reference.slice(2):o.reference,c=128===d.length?d.slice(64):void 0,u=n?.encryptionKey??c,h=this.generateRequestId(),p=await this.sendRequest({type:"epochFeedUploadReference",requestId:h,topic:i,signer:s,at:this.normalizeFeedTimestamp(r),reference:o.reference,encryptionKey:void 0!==u?this.normalizeSocKey(u):void 0,hints:n?.hints,requestOptions:t}),l=c;return{socAddress:p.socAddress,reference:o.reference,encryptionKey:l,epoch:p.epoch,timestamp:p.timestamp}},uploadRawReference:async(e,n)=>{const r=void 0!==n?.at?n.at:BigInt(Math.floor(Date.now()/1e3)),a=this.normalizeReference(e),o=this.generateRequestId(),d=await this.sendRequest({type:"epochFeedUploadReference",requestId:o,topic:i,signer:s,at:this.normalizeFeedTimestamp(r),reference:a,encryptionKey:void 0,hints:n?.hints,requestOptions:t});return{socAddress:d.socAddress,reference:a,encryptionKey:void 0,epoch:d.epoch,timestamp:d.timestamp}},uploadRawPayload:async(e,n)=>{const r=void 0!==n?.at?n.at:BigInt(Math.floor(Date.now()/1e3)),a=await this.uploadData(this.normalizePayload(e),{...n?.uploadOptions,encrypt:!1},t),o=this.generateRequestId(),d=await this.sendRequest({type:"epochFeedUploadReference",requestId:o,topic:i,signer:s,at:this.normalizeFeedTimestamp(r),reference:a.reference,encryptionKey:void 0,hints:n?.hints,requestOptions:t});return{socAddress:d.socAddress,reference:a.reference,encryptionKey:void 0,epoch:d.epoch,timestamp:d.timestamp}}}}makeSequentialFeedReader(e,t){this.ensureReady();const i=this.normalizeFeedTopic(e.topic);let n=e.owner?new y(e.owner).toHex():void 0;return{getOwner:async()=>{if(n)return n;const e=this.generateRequestId(),t=await this.sendRequest({type:"seqFeedGetOwner",requestId:e});return n=t.owner,n},downloadPayload:async(e,s)=>{const r=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedDownloadPayload",requestId:r,topic:i,owner:n,index:void 0!==s?.index?this.normalizeFeedIndex(s.index):void 0,at:void 0!==s?.at?this.normalizeFeedTimestamp(s.at):void 0,hasTimestamp:s?.hasTimestamp,lookupTimeoutMs:s?.lookupTimeoutMs,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{payload:a.payload,timestamp:a.timestamp,feedIndex:a.feedIndex,feedIndexNext:a.feedIndexNext}},downloadRawPayload:async e=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"seqFeedDownloadRawPayload",requestId:s,topic:i,owner:n,index:void 0!==e?.index?this.normalizeFeedIndex(e.index):void 0,at:void 0!==e?.at?this.normalizeFeedTimestamp(e.at):void 0,hasTimestamp:e?.hasTimestamp,lookupTimeoutMs:e?.lookupTimeoutMs,encryptionKey:e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t});return{payload:r.payload,timestamp:r.timestamp,feedIndex:r.feedIndex,feedIndexNext:r.feedIndexNext}},downloadReference:async(e,s)=>{const r=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedDownloadReference",requestId:r,topic:i,owner:n,index:void 0!==s?.index?this.normalizeFeedIndex(s.index):void 0,at:void 0!==s?.at?this.normalizeFeedTimestamp(s.at):void 0,hasTimestamp:s?.hasTimestamp,lookupTimeoutMs:s?.lookupTimeoutMs,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{reference:a.reference,feedIndex:a.feedIndex,feedIndexNext:a.feedIndexNext}}}}makeSequentialFeedWriter(e,t){this.ensureReady();const i=this.normalizeFeedTopic(e.topic),n=e.signer?new w(e.signer):void 0,s=n?n.toHex():void 0;let r=n?n.publicKey().address().toHex():void 0;return{getOwner:async()=>{if(r)return r;const e=this.generateRequestId(),t=await this.sendRequest({type:"seqFeedGetOwner",requestId:e});return r=t.owner,r},downloadPayload:async(e,n)=>{const s=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedDownloadPayload",requestId:s,topic:i,owner:r,index:void 0!==n?.index?this.normalizeFeedIndex(n.index):void 0,at:void 0!==n?.at?this.normalizeFeedTimestamp(n.at):void 0,hasTimestamp:n?.hasTimestamp,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{payload:a.payload,timestamp:a.timestamp,feedIndex:a.feedIndex,feedIndexNext:a.feedIndexNext}},downloadRawPayload:async e=>{const n=this.generateRequestId(),s=await this.sendRequest({type:"seqFeedDownloadRawPayload",requestId:n,topic:i,owner:r,index:void 0!==e?.index?this.normalizeFeedIndex(e.index):void 0,at:void 0!==e?.at?this.normalizeFeedTimestamp(e.at):void 0,hasTimestamp:e?.hasTimestamp,encryptionKey:e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t});return{payload:s.payload,timestamp:s.timestamp,feedIndex:s.feedIndex,feedIndexNext:s.feedIndexNext}},downloadReference:async(e,n)=>{const s=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedDownloadReference",requestId:s,topic:i,owner:r,index:void 0!==n?.index?this.normalizeFeedIndex(n.index):void 0,at:void 0!==n?.at?this.normalizeFeedTimestamp(n.at):void 0,hasTimestamp:n?.hasTimestamp,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{reference:a.reference,feedIndex:a.feedIndex,feedIndexNext:a.feedIndexNext}},uploadPayload:async(e,n)=>{const a=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedUploadPayload",requestId:a,topic:i,signer:s,data:this.normalizePayload(e),index:void 0!==n?.index?this.normalizeFeedIndex(n.index):void 0,at:void 0!==n?.at?this.normalizeFeedTimestamp(n.at):void 0,hasTimestamp:n?.hasTimestamp,lookupTimeoutMs:n?.lookupTimeoutMs,options:n,requestOptions:t});return r=o.owner,{reference:o.reference,feedIndex:o.feedIndex,owner:o.owner,encryptionKey:o.encryptionKey,tagUid:o.tagUid}},uploadRawPayload:async(e,n)=>{const a=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedUploadRawPayload",requestId:a,topic:i,signer:s,data:this.normalizePayload(e),index:void 0!==n?.index?this.normalizeFeedIndex(n.index):void 0,at:void 0!==n?.at?this.normalizeFeedTimestamp(n.at):void 0,hasTimestamp:n?.hasTimestamp,lookupTimeoutMs:n?.lookupTimeoutMs,encryptionKey:n?.encryptionKey?this.normalizeSocKey(n.encryptionKey):void 0,options:n,requestOptions:t});return r=o.owner,{reference:o.reference,feedIndex:o.feedIndex,owner:o.owner,encryptionKey:o.encryptionKey,tagUid:o.tagUid}},uploadReference:async(e,n)=>{const a=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedUploadReference",requestId:a,topic:i,signer:s,reference:this.normalizeReference(e),index:void 0!==n?.index?this.normalizeFeedIndex(n.index):void 0,at:void 0!==n?.at?this.normalizeFeedTimestamp(n.at):void 0,hasTimestamp:n?.hasTimestamp,lookupTimeoutMs:n?.lookupTimeoutMs,options:n,requestOptions:t});return r=o.owner,{reference:o.reference,feedIndex:o.feedIndex,owner:o.owner,encryptionKey:o.encryptionKey,tagUid:o.tagUid}}}}async createFeedManifest(e,t,i){this.ensureReady();const n=this.normalizeFeedTopic(e),s=this.generateRequestId();return(await this.sendRequest({type:"createFeedManifest",requestId:s,topic:n,owner:t?.owner,feedType:t?.feedType,uploadOptions:t?.uploadOptions,requestOptions:i})).reference}async gsocMine(e,t,i){this.ensureReady();const n=this.generateRequestId();return(await this.sendRequest({type:"gsocMine",requestId:n,targetOverlay:e,identifier:t,proximity:i})).signer}async gsocSend(e,t,i,n,s){this.ensureReady();const r=this.generateRequestId(),a=await this.sendRequest({type:"gsocSend",requestId:r,signer:e,identifier:t,data:new Uint8Array(i),options:n,requestOptions:s});return{reference:a.reference,tagUid:a.tagUid}}async actUploadData(e,t,i,n){this.ensureReady();const s=this.generateRequestId(),{onProgress:r,...a}=i??{},o=this.listenForProgress(s,r);try{const i=await this.sendRequest({type:"actUploadData",requestId:s,data:new Uint8Array(e),grantees:t,options:a,requestOptions:n,enableProgress:!!r});return{encryptedReference:i.encryptedReference,historyReference:i.historyReference,granteeListReference:i.granteeListReference,publisherPubKey:i.publisherPubKey,actReference:i.actReference,tagUid:i.tagUid}}finally{o()}}async actDownloadData(e,t,i,n,s){this.ensureReady();const r=this.generateRequestId();return(await this.sendRequest({type:"actDownloadData",requestId:r,encryptedReference:e,historyReference:t,publisherPubKey:i,timestamp:n,requestOptions:s})).data}async actAddGrantees(e,t,i){this.ensureReady();const n=this.generateRequestId(),s=await this.sendRequest({type:"actAddGrantees",requestId:n,historyReference:e,grantees:t,requestOptions:i});return{historyReference:s.historyReference,granteeListReference:s.granteeListReference,actReference:s.actReference}}async actRevokeGrantees(e,t,i,n){this.ensureReady();const s=this.generateRequestId(),r=await this.sendRequest({type:"actRevokeGrantees",requestId:s,historyReference:e,encryptedReference:t,revokeGrantees:i,requestOptions:n});return{encryptedReference:r.encryptedReference,historyReference:r.historyReference,granteeListReference:r.granteeListReference,actReference:r.actReference}}async actGetGrantees(e,t){this.ensureReady();const i=this.generateRequestId();return(await this.sendRequest({type:"actGetGrantees",requestId:i,historyReference:e,requestOptions:t})).grantees}destroy(){const e=()=>new i("invalid-state","Client destroyed");this.pendingRequests.forEach(t=>{clearTimeout(t.timeoutId),t.reject(e())}),this.pendingRequests.clear(),this.progressListeners.clear(),this.messageListener&&(window.removeEventListener("message",this.messageListener),this.messageListener=void 0),this.iframe&&this.iframe.parentNode&&(this.iframe.parentNode.removeChild(this.iframe),this.iframe=void 0),this.iframeLoadReject?.(e()),this.proxyInitializedReject?.(e()),this.readyReject?.(e()),this.firstConnectionInfoReject?.(e()),this.iframeLoadReject=void 0,this.readyResolve=void 0,this.readyReject=void 0,this.proxyInitializedResolve=void 0,this.proxyInitializedReject=void 0,this.firstConnectionInfoResolve=void 0,this.firstConnectionInfoReject=void 0,this.readyPromise=void 0,this.proxyInitializedPromise=void 0,this.firstConnectionInfoPromise=void 0,this.ready=!1}}function P(e){const t=e instanceof Uint8Array?e:q(e);if(32!==t.length)throw new Error(`Invalid content reference length: ${t.length} (expected 32 bytes)`);const i=new x;return i.addFork("/",z,{"website-index-document":"index.bin"}),i.addFork("index.bin",t,{"Content-Type":"application/octet-stream",Filename:"index.bin"}),{manifestNode:i}}function O(e){let t=0;for(;e;)t+=1&e,e>>>=1;return t}function M(e){for(let t=0;t<e.length;t++)if(0!==e[t])return!1;return!0}function S(e){if(e.length<96)throw new Error(`Manifest too small: ${e.length} bytes (expected at least 96)`);const t=e.slice(64,96);if(M(t))throw new Error("Manifest entry is zero");return new b(t).toHex()}function A(e){if(e.length<192)throw new Error(`Manifest too small: ${e.length} bytes (expected at least 192)`);const t=e.slice(96,128),i=Math.floor(105/8);if(!(2&t[i]))throw new Error('Manifest does not contain "index.bin" fork');let n=0;for(let e=0;e<i;e++)n+=O(t[e]);for(let e=0;e<1;e++)t[i]&1<<e&&n++;let s=128;for(let t=0;t<n;t++){const t=e[s];if(s+=64,!!(16&t)){s+=2+(e[s]<<8|e[s+1])}}const r=e[s],a=e[s+1];if(105!==e[s+2])throw new Error(`Expected "index.bin" prefix, got byte 0x${e[s+2].toString(16)}`);if(a>=9){const t=e.slice(s+2,s+2+9),i=(new TextEncoder).encode("index.bin");t.every((e,t)=>e===i[t])||console.warn('[ManifestBuilder] Prefix does not fully match "index.bin"')}if(!!!(2&r))throw new Error('"index.bin" fork is not a VALUE type');const o=s+32,d=e.slice(o,o+32);if(M(d))throw new Error('Manifest "index.bin" fork has zero reference');return new b(d).toHex()}export{U as SwarmIdClient,i as SwarmIdError,I as TimeoutError,P as buildBzzManifestNode,F as collectionPath,A as extractContentFromFlatManifest,S as extractEntryFromManifest,h as generatedAvatar,q as hexToUint8Array,d as uint8ArrayToHex,g as withTimeout};
|
|
1
|
+
import{A as e,S as t,I as i,P as a,a as d,u as c,T as u,b as h,g as y,E as f,c as w,B as g,d as R,i as I,w as x,e as z,f as b,h as T,j as F,M as K,N as P,R as U}from"./chunks/chat-binding-BirKsDU3.js";export{C as CHAT_BINDING_TITLE,D as DEFAULT_BEE_NODE_URL,o as acceptedChatBinding,p as buildChatBindingMessage,l as formatTTL,k as generatedAvatarSvg,q as isCleanSiteOrigin,n as jsonRpcBatch,m as jsonRpcCall,r as parseChatBindingMessage,s as saveMantarayTreeRecursively,v as verifyChatBinding}from"./chunks/chat-binding-BirKsDU3.js";function O(e){const t=e.webkitRelativePath;return t?t.replace(/^[^/]*\//,""):e.name}function S(e,n,i){return x(e,n,i).catch(e=>{throw e instanceof z?new t("init-failed",e.message,{cause:e}):e})}function M(e){if(void 0===e)return;const n=T.safeParse(e);if(n.success)return n.data;const i=n.error.issues[0];throw new t("invalid-request",`Invalid button config at ${["config",...i.path].join(".")}: ${i.message}`,{cause:n.error})}function A(e){if(b.safeParse(e).success)return e;throw new t("invalid-request",`Invalid button action: ${JSON.stringify(e)}`)}function B(e){if(!I(e))throw new t("invalid-request","Invalid beeApiUrl: must be an http(s) URL, optionally with a path, and no credentials, query or fragment");return e}class L{constructor(n){if(this.mountedButtons=new Map,this.ready=!1,this.pendingRequests=new Map,this.progressListeners=new Map,this.requestIdCounter=0,"undefined"==typeof window)throw new Error("@solarpunkltd/swarm-id runs in the browser only: construct SwarmIdClient in code that runs there (an effect, onMount, or behind `typeof window !== 'undefined'`), not in a server render");this.iframeOrigin=n.iframeOrigin,this.iframePath=n.iframePath||"/proxy",this.timeout=n.timeout??3e4,this.initializationTimeout=n.initializationTimeout??3e4,this.onConnectionChange=n.onConnectionChange,this.popupMode=n.popupMode||"window",this.metadata=n.metadata,this.subsidisedGatewayUrl=n.subsidisedGatewayUrl,void 0!==n.beeApiUrl&&(this.beeApiUrl=B(n.beeApiUrl));try{e.parse(this.metadata)}catch(e){throw new t("invalid-request",`Invalid app metadata: ${e}`,{cause:e})}this.setupMessageListener()}async initialize(){if(this.iframe)throw new t("invalid-state","SwarmIdClient already initialized");this.firstConnectionInfoPromise=S(new Promise((e,t)=>{this.firstConnectionInfoResolve=e,this.firstConnectionInfoReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not send initial connectionInfoChanged within ${this.initializationTimeout}ms`),this.firstConnectionInfoPromise.catch(()=>{}),this.proxyInitializedPromise=S(new Promise((e,t)=>{this.proxyInitializedResolve=e,this.proxyInitializedReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not signal readiness within ${this.initializationTimeout}ms`),this.proxyInitializedPromise.catch(()=>{}),this.readyPromise=S(new Promise((e,t)=>{this.readyResolve=e,this.readyReject=t}),this.initializationTimeout,`Proxy initialization timeout - proxy did not respond within ${this.initializationTimeout}ms`),this.readyPromise.catch(()=>{}),this.iframe=document.createElement("iframe"),this.iframe.src=`${this.iframeOrigin}${this.iframePath}`,this.iframe.style.display="none",await new Promise((e,n)=>{this.iframeLoadReject=n,this.iframe.onload=()=>e(),this.iframe.onerror=()=>n(new t("init-failed","Failed to load Swarm ID iframe")),document.body.appendChild(this.iframe)}),this.iframeLoadReject=void 0,await this.proxyInitializedPromise,this.sendMessage({type:"parentIdentify",requestId:this.generateRequestId(),metadata:this.metadata,subsidisedGatewayUrl:this.subsidisedGatewayUrl,beeApiUrl:this.beeApiUrl}),await this.readyPromise,await this.firstConnectionInfoPromise}setupMessageListener(){this.messageListener=e=>{if(!this.iframe||e.source!==this.iframe.contentWindow)return;if("proxyInitialized"===e.data?.type)return void(this.proxyInitializedResolve&&(this.proxyInitializedResolve(),this.proxyInitializedResolve=void 0));const t=new URL(this.iframeOrigin).origin;if(e.origin!==t)return void console.warn("[SwarmIdClient] Rejected message from unauthorized origin:",e.origin);let n;try{n=i.parse(e.data)}catch(t){return void console.warn("[SwarmIdClient] Invalid message format:",e.data,t)}this.handleIframeMessage(n)},window.addEventListener("message",this.messageListener)}handleIframeMessage(e){switch(e.type){case"proxyReady":this.ready=!0,this.storageShared=e.storageShared,this.readyResolve&&this.readyResolve();break;case"connectionInfoChanged":{const t={canUpload:e.canUpload,storagePartitioned:e.storagePartitioned,uploadMode:e.uploadMode,uploadUnavailableReason:e.uploadUnavailableReason,identity:e.identity,appKey:e.appKey,partition:e.partition,chatBinding:e.chatBinding,beeApiUrl:e.beeApiUrl,postageBatchId:e.postageBatchId};this.lastConnectionInfo=t,this.firstConnectionInfoResolve&&(this.firstConnectionInfoResolve(),this.firstConnectionInfoResolve=void 0),this.onConnectionChange&&this.onConnectionChange(t);break}case"initError":console.error("[SwarmIdClient] Proxy initialization error:",e.error),this.readyReject&&this.readyReject(new t("init-failed",e.error));break;case"disconnectResponse":if("requestId"in e){const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.resolve(e))}break;case"error":{const n=this.pendingRequests.get(e.requestId);n&&(clearTimeout(n.timeoutId),this.pendingRequests.delete(e.requestId),n.reject(t.fromWire(e)));break}case"uploadProgress":this.progressListeners.get(e.requestId)?.({total:e.total,processed:e.processed});break;default:if("requestId"in e){const t=this.pendingRequests.get(e.requestId);t&&(clearTimeout(t.timeoutId),this.pendingRequests.delete(e.requestId),t.resolve(e))}}}sendMessage(e){if(!this.iframe||!this.iframe.contentWindow)throw new t("invalid-state","Iframe not initialized");try{a.parse(e)}catch(e){throw new t("invalid-request",`Invalid message format: ${e}`,{cause:e})}this.iframe.contentWindow.postMessage(e,this.iframeOrigin)}async sendRequest(e){const n=this.roundTripTimeout(e.requestOptions?.timeout);return new Promise((i,s)=>{const r=setTimeout(()=>{this.pendingRequests.delete(e.requestId),s(new t("timeout",`Request timeout after ${n}ms`))},n);this.pendingRequests.set(e.requestId,{resolve:i,reject:s,timeoutId:r}),this.sendMessage(e)})}roundTripTimeout(e){return void 0===e||e<=0?this.timeout:Math.min(e,2147483647)}generateRequestId(){return`req-${++this.requestIdCounter}-${Date.now()}`}normalizeSocIdentifier(e){return e instanceof d?e.toHex():e instanceof Uint8Array?c(e):e}normalizeSocKey(e){return e instanceof Uint8Array?c(e):e}normalizeFeedTopic(e){return e instanceof u?c(e.toUint8Array()):e instanceof d?e.toHex():e instanceof Uint8Array?c(e):e}normalizeReference(e){return e instanceof Uint8Array?c(e):e}normalizeFeedTimestamp(e){return"bigint"==typeof e?e.toString():"number"==typeof e?BigInt(Math.floor(e)).toString():e}normalizeFeedIndex(e){return"bigint"==typeof e?e.toString():"number"==typeof e?BigInt(Math.floor(e)).toString():e}normalizePayload(e){return e instanceof Uint8Array?e:(new TextEncoder).encode(e)}socChunkFromResponse(e){return{data:e.data,identifier:e.identifier,signature:e.signature,span:e.span,payload:e.payload,address:e.address,owner:e.owner}}ensureReady(){if(!this.ready)throw new t("invalid-state","SwarmIdClient not initialized. Call initialize() first.")}async checkAuthStatus(){this.ensureReady();const e=this.generateRequestId(),t=await this.sendRequest({type:"checkAuth",requestId:e});return{authenticated:t.authenticated,origin:t.origin,beeApiUrl:t.beeApiUrl}}async setBeeApiUrl(e){const t=B(e);this.ensureReady(),await this.sendRequest({type:"setBeeApiUrl",requestId:this.generateRequestId(),beeApiUrl:t}),this.beeApiUrl=t}async getPostageBatch(){this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"getPostageBatch",requestId:e})).postageBatch}async disconnect(){this.ensureReady();const e=this.generateRequestId();if(!(await this.sendRequest({type:"disconnect",requestId:e})).success)throw new t("internal","Failed to disconnect")}async connect(e={}){if(this.ensureReady(),!0!==this.storageShared)throw new t("button-required","Swarm ID's frame cannot read Swarm ID's storage here, so a window opened from this page cannot sign it in. Sign in through the button from client.mountButton().");if(!this.openAuthWindow(e))throw new t("popup-blocked","Failed to open authentication popup")}mountButton(e,n){this.ensureReady();const i=this.iframeOrigin,s=new URL(i).origin;let r=A(n.action),o=M(n.config),a=!1,d=!1,c=!1,u=!1;const h=document.createElement("iframe");let p,l;h.src=`${i}${this.iframePath.replace(/\/proxy$/,"")}/button`,h.title="Swarm ID",Object.assign(h.style,{border:"none",backgroundColor:"transparent",width:"100%",height:"100%",display:"block",borderRadius:o?.borderRadius??"0"});const y=S(new Promise((e,t)=>{p=e,l=t}),this.initializationTimeout,`Swarm ID button did not show within ${this.initializationTimeout}ms`);y.then(()=>d=!0,()=>d=!0);const f=e=>h.contentWindow?.postMessage(e,i),m=e=>{if(e.source!==h.contentWindow)return;if(e.data?.type===g)return a=!0,void f({type:"buttonIdentify",action:r,config:o,metadata:this.metadata,popupMode:this.popupMode});if(e.origin!==s)return;const i=R.safeParse(e.data);if(!i.success)return;const d=i.data;"buttonReady"===d.type?p():"buttonInitError"===d.type?l(new t("init-failed",d.error)):(c="open"===d.state,u?c||w():n.onWindowChange?.(d.state))},w=()=>{this.mountedButtons.delete(I),window.removeEventListener("message",m),h.remove(),d||l(new t("invalid-state","Swarm ID button unmounted"))};window.addEventListener("message",m),e.appendChild(h);const I={ready:y,update:e=>{u||(r=void 0===e.action?r:A(e.action),o=void 0===e.config?o:M(e.config),h.style.borderRadius=o?.borderRadius??"0",a&&f({type:"buttonUpdate",action:r,config:o}))},unmount:()=>{!u&&this.mountedButtons.has(I)&&(u=!0,c?h.style.display="none":w())}};return this.mountedButtons.set(I,w),I}openAuthWindow(e){const t=this.iframePath.replace(/\/proxy$/,""),n=h(this.iframeOrigin+t,window.location.origin,this.metadata),i="popup"===(e.popupMode??this.popupMode)?window.open(n,"_blank","width=500,height=600"):window.open(n,"_blank");return Boolean(i)}get connectionInfo(){if(this.ensureReady(),!this.lastConnectionInfo)throw new t("invalid-state","SwarmIdClient connectionInfo not yet available.");return this.lastConnectionInfo}async getAvatar(e={}){const{identity:t}=this.connectionInfo;if(t)return void 0!==e.size&&"generated"===t.avatar.source?y(t.id,e.size):t.avatar}async isBeeConnected(){try{this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"isConnected",requestId:e})).connected}catch{return!1}}async getNodeInfo(){this.ensureReady();const e=this.generateRequestId(),t=await this.sendRequest({type:"getNodeInfo",requestId:e});return{beeMode:t.beeMode,chequebookEnabled:t.chequebookEnabled,swapEnabled:t.swapEnabled}}async uploadData(e,t,n){this.ensureReady();const i=this.generateRequestId(),{onProgress:s,useWebSocket:r,useWorkers:o,workerCount:a,concurrency:d,...c}=t??{},u=this.listenForProgress(i,s);try{const t=await this.sendRequest({type:"uploadData",requestId:i,data:new Uint8Array(e),options:c,requestOptions:n,enableProgress:!!s,useWebSocket:r,useWorkers:o,workerCount:a,concurrency:d});return{reference:t.reference,tagUid:t.tagUid}}finally{u()}}async downloadData(e,t,n){this.ensureReady();const i=this.generateRequestId();return(await this.sendRequest({type:"downloadData",requestId:i,reference:e,options:t,requestOptions:n})).data}async deriveAppSecret(e){this.ensureReady();const t=this.generateRequestId();return(await this.sendRequest({type:"deriveAppSecret",requestId:t,label:e})).secret}async getChatKey(){this.ensureReady();const e=this.generateRequestId();return(await this.sendRequest({type:"getChatKey",requestId:e})).chatKey}async stampChunk(e){this.ensureReady();const t=this.generateRequestId(),n="soc"===e.kind?{...e,identifier:this.normalizeSocIdentifier(e.identifier),signer:"app"===e.signer?e.signer:{...e.signer,privateKey:this.normalizeSocKey(e.signer.privateKey)}}:e,i=await this.sendRequest({type:"stampChunk",requestId:t,chunk:n});return{address:i.address,stamp:i.stamp,...void 0!==i.owner&&{owner:i.owner},...void 0!==i.signature&&{signature:i.signature}}}async uploadFile(e,t,n,i){this.ensureReady();const s=this.generateRequestId(),{onProgress:r,useWebSocket:o,useWorkers:a,workerCount:d,concurrency:c,...u}=n??{};let h,p=t;if(e instanceof File){const t=await e.arrayBuffer();h=new Uint8Array(t),p=p||e.name}else h=new Uint8Array(e.buffer.slice(0),e.byteOffset,e.byteLength);const l=this.listenForProgress(s,r);try{const e=await this.sendRequest({type:"uploadFile",requestId:s,data:h,name:p,options:u,requestOptions:i,enableProgress:!!r,useWebSocket:o,useWorkers:a,workerCount:d,concurrency:c});return{reference:e.reference,tagUid:e.tagUid}}finally{l()}}async downloadFile(e,t,n,i){this.ensureReady();const s=this.generateRequestId(),r=await this.sendRequest({type:"downloadFile",requestId:s,reference:e,path:t,options:n,requestOptions:i});return{name:r.name,data:new Uint8Array(r.data)}}async uploadFiles(e,t,n){this.ensureReady();const i=this.generateRequestId(),{onProgress:s,useWorkers:r,workerCount:o,...a}=t??{},d=await Promise.all(Array.from(e,async e=>{const{path:t,file:n}=e instanceof File?{path:O(e),file:e}:e;return{path:t,data:new Uint8Array(await n.arrayBuffer()),contentType:n.type||void 0}})),c=this.listenForProgress(i,s);try{const e=await this.sendRequest({type:"uploadFiles",requestId:i,files:d,options:a,requestOptions:n,enableProgress:!!s,useWorkers:r,workerCount:o});return{reference:e.reference,tagUid:e.tagUid}}finally{c()}}async listFiles(e,t){this.ensureReady();const n=this.generateRequestId();return(await this.sendRequest({type:"listFiles",requestId:n,reference:e,requestOptions:t})).entries}listenForProgress(e,t){return t?(this.progressListeners.set(e,t),()=>{this.progressListeners.delete(e)}):()=>{}}async uploadChunk(e,t,n){this.ensureReady();const i=this.generateRequestId(),{onProgress:s,...r}=t??{};return{reference:(await this.sendRequest({type:"uploadChunk",requestId:i,data:e,options:r,requestOptions:n})).reference}}async downloadChunk(e,t,n){this.ensureReady();const i=this.generateRequestId(),s=await this.sendRequest({type:"downloadChunk",requestId:i,reference:e,options:t,requestOptions:n});return new Uint8Array(s.data)}makeSOCReader(e,t){this.ensureReady();const n=new f(e).toHex(),i=async(e,i)=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"socDownload",requestId:s,owner:n,identifier:this.normalizeSocIdentifier(e),encryptionKey:this.normalizeSocKey(i),requestOptions:t});return this.socChunkFromResponse(r)},s=async(e,i)=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"socRawDownload",requestId:s,owner:n,identifier:this.normalizeSocIdentifier(e),encryptionKey:i?this.normalizeSocKey(i):void 0,requestOptions:t});return this.socChunkFromResponse(r)};return{getOwner:async()=>n,rawDownload:(e,t)=>s(e,t),download:(e,t)=>i(e,t)}}makeSOCWriter(e,t){this.ensureReady();const n=e?new w(e):void 0,i=n?n.toHex():void 0;let s=n?n.publicKey().address().toHex():void 0;const r=async(e,n)=>{const i=this.generateRequestId(),r=await this.sendRequest({type:"socDownload",requestId:i,owner:s,identifier:this.normalizeSocIdentifier(e),encryptionKey:this.normalizeSocKey(n),requestOptions:t});return this.socChunkFromResponse(r)},o=async(e,n)=>{const i=this.generateRequestId(),r=await this.sendRequest({type:"socRawDownload",requestId:i,owner:s,identifier:this.normalizeSocIdentifier(e),encryptionKey:n?this.normalizeSocKey(n):void 0,requestOptions:t});return this.socChunkFromResponse(r)},a=async(e,n,r)=>{const o=this.generateRequestId(),a=await this.sendRequest({type:"socUpload",requestId:o,identifier:this.normalizeSocIdentifier(e),data:new Uint8Array(n),signer:i,options:r,requestOptions:t});return s=a.owner,{reference:a.reference,tagUid:a.tagUid,encryptionKey:a.encryptionKey,owner:a.owner}},d=async(e,n,r)=>{const o=this.generateRequestId(),a=await this.sendRequest({type:"socRawUpload",requestId:o,identifier:this.normalizeSocIdentifier(e),data:new Uint8Array(n),signer:i,options:r,requestOptions:t});return s=a.owner,{reference:a.reference,tagUid:a.tagUid,encryptionKey:a.encryptionKey,owner:a.owner}};return{getOwner:async()=>{if(s)return s;const e=this.generateRequestId(),t=await this.sendRequest({type:"socGetOwner",requestId:e});return s=t.owner,s},rawDownload:(e,t)=>o(e,t),download:(e,t)=>r(e,t),upload:(e,t,n)=>a(e,t,n),rawUpload:(e,t,n)=>d(e,t,n)}}makeEpochFeedReader(e,t){this.ensureReady();const n=this.normalizeFeedTopic(e.topic);let i=e.owner?new f(e.owner).toHex():void 0;const s=async e=>{const s=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),r=this.generateRequestId(),o=(await this.sendRequest({type:"epochFeedDownloadReference",requestId:r,topic:n,owner:i,at:this.normalizeFeedTimestamp(s),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0!==e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t})).reference,a=o&&o.startsWith("0x")?o.slice(2):o;return{reference:o,encryptionKey:a&&128===a.length?a.slice(64):void 0}},r=async e=>{const s=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),r=this.generateRequestId();return{reference:(await this.sendRequest({type:"epochFeedDownloadReference",requestId:r,topic:n,owner:i,at:this.normalizeFeedTimestamp(s),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0,requestOptions:t})).reference,encryptionKey:void 0}};return{getOwner:async()=>{if(i)return i;const e=this.generateRequestId(),t=await this.sendRequest({type:"feedGetOwner",requestId:e});return i=t.owner,i},downloadReference:s,downloadPayload:async e=>{const n=await s(e);if(!n.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const i=await this.downloadData(n.reference,void 0,t);return{reference:n.reference,payload:i,encryptionKey:n.encryptionKey}},downloadRawReference:r,downloadRawPayload:async e=>{const n=await r(e);if(!n.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const i=await this.downloadData(n.reference,void 0,t);return{reference:n.reference,payload:i,encryptionKey:void 0}}}}makeEpochFeedWriter(e,t){this.ensureReady();const n=this.normalizeFeedTopic(e.topic),i=e.signer?new w(e.signer):void 0,s=i?i.toHex():void 0;let r=i?i.publicKey().address().toHex():void 0;const o=async e=>{const i=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),s=this.generateRequestId(),o=(await this.sendRequest({type:"epochFeedDownloadReference",requestId:s,topic:n,owner:r,at:this.normalizeFeedTimestamp(i),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0!==e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t})).reference,a=o&&o.startsWith("0x")?o.slice(2):o;return{reference:o,encryptionKey:a&&128===a.length?a.slice(64):void 0}},a=async e=>{const i=void 0!==e?.at?e.at:BigInt(Math.floor(Date.now()/1e3)),s=this.generateRequestId();return{reference:(await this.sendRequest({type:"epochFeedDownloadReference",requestId:s,topic:n,owner:r,at:this.normalizeFeedTimestamp(i),after:void 0!==e?.after?this.normalizeFeedTimestamp(e.after):void 0,encryptionKey:void 0,requestOptions:t})).reference,encryptionKey:void 0}};return{getOwner:async()=>{if(r)return r;const e=this.generateRequestId(),t=await this.sendRequest({type:"feedGetOwner",requestId:e});return r=t.owner,r},downloadReference:o,downloadPayload:async e=>{const n=await o(e);if(!n.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const i=await this.downloadData(n.reference,void 0,t);return{reference:n.reference,payload:i,encryptionKey:n.encryptionKey}},downloadRawReference:a,downloadRawPayload:async e=>{const n=await a(e);if(!n.reference)return{reference:void 0,payload:void 0,encryptionKey:void 0};const i=await this.downloadData(n.reference,void 0,t);return{reference:n.reference,payload:i,encryptionKey:void 0}},uploadReference:async(e,i)=>{const r=void 0!==i?.at?i.at:BigInt(Math.floor(Date.now()/1e3)),o=this.normalizeReference(e),a=o.startsWith("0x")?o.slice(2):o,d=128===a.length?a.slice(64):void 0,c=i?.encryptionKey??d,u=this.generateRequestId(),h=await this.sendRequest({type:"epochFeedUploadReference",requestId:u,topic:n,signer:s,at:this.normalizeFeedTimestamp(r),reference:o,encryptionKey:void 0!==c?this.normalizeSocKey(c):void 0,hints:i?.hints,requestOptions:t});return{socAddress:h.socAddress,reference:o,encryptionKey:d,epoch:h.epoch,timestamp:h.timestamp}},uploadPayload:async(e,i)=>{const r=void 0!==i?.at?i.at:BigInt(Math.floor(Date.now()/1e3)),o=!1!==i?.encrypt,a=await this.uploadData(this.normalizePayload(e),{...i?.uploadOptions,encrypt:o},t),d=a.reference.startsWith("0x")?a.reference.slice(2):a.reference,c=128===d.length?d.slice(64):void 0,u=i?.encryptionKey??c,h=this.generateRequestId(),p=await this.sendRequest({type:"epochFeedUploadReference",requestId:h,topic:n,signer:s,at:this.normalizeFeedTimestamp(r),reference:a.reference,encryptionKey:void 0!==u?this.normalizeSocKey(u):void 0,hints:i?.hints,requestOptions:t}),l=c;return{socAddress:p.socAddress,reference:a.reference,encryptionKey:l,epoch:p.epoch,timestamp:p.timestamp}},uploadRawReference:async(e,i)=>{const r=void 0!==i?.at?i.at:BigInt(Math.floor(Date.now()/1e3)),o=this.normalizeReference(e),a=this.generateRequestId(),d=await this.sendRequest({type:"epochFeedUploadReference",requestId:a,topic:n,signer:s,at:this.normalizeFeedTimestamp(r),reference:o,encryptionKey:void 0,hints:i?.hints,requestOptions:t});return{socAddress:d.socAddress,reference:o,encryptionKey:void 0,epoch:d.epoch,timestamp:d.timestamp}},uploadRawPayload:async(e,i)=>{const r=void 0!==i?.at?i.at:BigInt(Math.floor(Date.now()/1e3)),o=await this.uploadData(this.normalizePayload(e),{...i?.uploadOptions,encrypt:!1},t),a=this.generateRequestId(),d=await this.sendRequest({type:"epochFeedUploadReference",requestId:a,topic:n,signer:s,at:this.normalizeFeedTimestamp(r),reference:o.reference,encryptionKey:void 0,hints:i?.hints,requestOptions:t});return{socAddress:d.socAddress,reference:o.reference,encryptionKey:void 0,epoch:d.epoch,timestamp:d.timestamp}}}}makeSequentialFeedReader(e,t){this.ensureReady();const n=this.normalizeFeedTopic(e.topic);let i=e.owner?new f(e.owner).toHex():void 0;return{getOwner:async()=>{if(i)return i;const e=this.generateRequestId(),t=await this.sendRequest({type:"seqFeedGetOwner",requestId:e});return i=t.owner,i},downloadPayload:async(e,s)=>{const r=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedDownloadPayload",requestId:r,topic:n,owner:i,index:void 0!==s?.index?this.normalizeFeedIndex(s.index):void 0,at:void 0!==s?.at?this.normalizeFeedTimestamp(s.at):void 0,hasTimestamp:s?.hasTimestamp,lookupTimeoutMs:s?.lookupTimeoutMs,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{payload:o.payload,timestamp:o.timestamp,feedIndex:o.feedIndex,feedIndexNext:o.feedIndexNext}},downloadRawPayload:async e=>{const s=this.generateRequestId(),r=await this.sendRequest({type:"seqFeedDownloadRawPayload",requestId:s,topic:n,owner:i,index:void 0!==e?.index?this.normalizeFeedIndex(e.index):void 0,at:void 0!==e?.at?this.normalizeFeedTimestamp(e.at):void 0,hasTimestamp:e?.hasTimestamp,lookupTimeoutMs:e?.lookupTimeoutMs,encryptionKey:e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t});return{payload:r.payload,timestamp:r.timestamp,feedIndex:r.feedIndex,feedIndexNext:r.feedIndexNext}},downloadReference:async(e,s)=>{const r=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedDownloadReference",requestId:r,topic:n,owner:i,index:void 0!==s?.index?this.normalizeFeedIndex(s.index):void 0,at:void 0!==s?.at?this.normalizeFeedTimestamp(s.at):void 0,hasTimestamp:s?.hasTimestamp,lookupTimeoutMs:s?.lookupTimeoutMs,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{reference:o.reference,feedIndex:o.feedIndex,feedIndexNext:o.feedIndexNext}}}}makeSequentialFeedWriter(e,t){this.ensureReady();const n=this.normalizeFeedTopic(e.topic),i=e.signer?new w(e.signer):void 0,s=i?i.toHex():void 0;let r=i?i.publicKey().address().toHex():void 0;return{getOwner:async()=>{if(r)return r;const e=this.generateRequestId(),t=await this.sendRequest({type:"seqFeedGetOwner",requestId:e});return r=t.owner,r},downloadPayload:async(e,i)=>{const s=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedDownloadPayload",requestId:s,topic:n,owner:r,index:void 0!==i?.index?this.normalizeFeedIndex(i.index):void 0,at:void 0!==i?.at?this.normalizeFeedTimestamp(i.at):void 0,hasTimestamp:i?.hasTimestamp,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{payload:o.payload,timestamp:o.timestamp,feedIndex:o.feedIndex,feedIndexNext:o.feedIndexNext}},downloadRawPayload:async e=>{const i=this.generateRequestId(),s=await this.sendRequest({type:"seqFeedDownloadRawPayload",requestId:i,topic:n,owner:r,index:void 0!==e?.index?this.normalizeFeedIndex(e.index):void 0,at:void 0!==e?.at?this.normalizeFeedTimestamp(e.at):void 0,hasTimestamp:e?.hasTimestamp,encryptionKey:e?.encryptionKey?this.normalizeSocKey(e.encryptionKey):void 0,requestOptions:t});return{payload:s.payload,timestamp:s.timestamp,feedIndex:s.feedIndex,feedIndexNext:s.feedIndexNext}},downloadReference:async(e,i)=>{const s=this.generateRequestId(),o=await this.sendRequest({type:"seqFeedDownloadReference",requestId:s,topic:n,owner:r,index:void 0!==i?.index?this.normalizeFeedIndex(i.index):void 0,at:void 0!==i?.at?this.normalizeFeedTimestamp(i.at):void 0,hasTimestamp:i?.hasTimestamp,encryptionKey:this.normalizeSocKey(e),requestOptions:t});return{reference:o.reference,feedIndex:o.feedIndex,feedIndexNext:o.feedIndexNext}},uploadPayload:async(e,i)=>{const o=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedUploadPayload",requestId:o,topic:n,signer:s,data:this.normalizePayload(e),index:void 0!==i?.index?this.normalizeFeedIndex(i.index):void 0,at:void 0!==i?.at?this.normalizeFeedTimestamp(i.at):void 0,hasTimestamp:i?.hasTimestamp,lookupTimeoutMs:i?.lookupTimeoutMs,options:i,requestOptions:t});return r=a.owner,{reference:a.reference,feedIndex:a.feedIndex,owner:a.owner,encryptionKey:a.encryptionKey,tagUid:a.tagUid}},uploadRawPayload:async(e,i)=>{const o=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedUploadRawPayload",requestId:o,topic:n,signer:s,data:this.normalizePayload(e),index:void 0!==i?.index?this.normalizeFeedIndex(i.index):void 0,at:void 0!==i?.at?this.normalizeFeedTimestamp(i.at):void 0,hasTimestamp:i?.hasTimestamp,lookupTimeoutMs:i?.lookupTimeoutMs,encryptionKey:i?.encryptionKey?this.normalizeSocKey(i.encryptionKey):void 0,options:i,requestOptions:t});return r=a.owner,{reference:a.reference,feedIndex:a.feedIndex,owner:a.owner,encryptionKey:a.encryptionKey,tagUid:a.tagUid}},uploadReference:async(e,i)=>{const o=this.generateRequestId(),a=await this.sendRequest({type:"seqFeedUploadReference",requestId:o,topic:n,signer:s,reference:this.normalizeReference(e),index:void 0!==i?.index?this.normalizeFeedIndex(i.index):void 0,at:void 0!==i?.at?this.normalizeFeedTimestamp(i.at):void 0,hasTimestamp:i?.hasTimestamp,lookupTimeoutMs:i?.lookupTimeoutMs,options:i,requestOptions:t});return r=a.owner,{reference:a.reference,feedIndex:a.feedIndex,owner:a.owner,encryptionKey:a.encryptionKey,tagUid:a.tagUid}}}}async createFeedManifest(e,t,n){this.ensureReady();const i=this.normalizeFeedTopic(e),s=this.generateRequestId();return(await this.sendRequest({type:"createFeedManifest",requestId:s,topic:i,owner:t?.owner,feedType:t?.feedType,uploadOptions:t?.uploadOptions,requestOptions:n})).reference}async gsocMine(e,t,n){this.ensureReady();const i=this.generateRequestId();return(await this.sendRequest({type:"gsocMine",requestId:i,targetOverlay:e,identifier:t,proximity:n})).signer}async gsocSend(e,t,n,i,s){this.ensureReady();const r=this.generateRequestId(),o=await this.sendRequest({type:"gsocSend",requestId:r,signer:e,identifier:t,data:new Uint8Array(n),options:i,requestOptions:s});return{reference:o.reference,tagUid:o.tagUid}}async actUploadData(e,t,n,i){this.ensureReady();const s=this.generateRequestId(),{onProgress:r,...o}=n??{},a=this.listenForProgress(s,r);try{const n=await this.sendRequest({type:"actUploadData",requestId:s,data:new Uint8Array(e),grantees:t,options:o,requestOptions:i,enableProgress:!!r});return{encryptedReference:n.encryptedReference,historyReference:n.historyReference,granteeListReference:n.granteeListReference,publisherPubKey:n.publisherPubKey,actReference:n.actReference,tagUid:n.tagUid}}finally{a()}}async actDownloadData(e,t,n,i,s){this.ensureReady();const r=this.generateRequestId();return(await this.sendRequest({type:"actDownloadData",requestId:r,encryptedReference:e,historyReference:t,publisherPubKey:n,timestamp:i,requestOptions:s})).data}async actAddGrantees(e,t,n){this.ensureReady();const i=this.generateRequestId(),s=await this.sendRequest({type:"actAddGrantees",requestId:i,historyReference:e,grantees:t,requestOptions:n});return{historyReference:s.historyReference,granteeListReference:s.granteeListReference,actReference:s.actReference}}async actRevokeGrantees(e,t,n,i){this.ensureReady();const s=this.generateRequestId(),r=await this.sendRequest({type:"actRevokeGrantees",requestId:s,historyReference:e,encryptedReference:t,revokeGrantees:n,requestOptions:i});return{encryptedReference:r.encryptedReference,historyReference:r.historyReference,granteeListReference:r.granteeListReference,actReference:r.actReference}}async actGetGrantees(e,t){this.ensureReady();const n=this.generateRequestId();return(await this.sendRequest({type:"actGetGrantees",requestId:n,historyReference:e,requestOptions:t})).grantees}destroy(){const e=()=>new t("invalid-state","Client destroyed");for(const e of[...this.mountedButtons.values()])e();this.pendingRequests.forEach(t=>{clearTimeout(t.timeoutId),t.reject(e())}),this.pendingRequests.clear(),this.progressListeners.clear(),this.messageListener&&(window.removeEventListener("message",this.messageListener),this.messageListener=void 0),this.iframe&&this.iframe.parentNode&&(this.iframe.parentNode.removeChild(this.iframe),this.iframe=void 0),this.iframeLoadReject?.(e()),this.proxyInitializedReject?.(e()),this.readyReject?.(e()),this.firstConnectionInfoReject?.(e()),this.iframeLoadReject=void 0,this.readyResolve=void 0,this.readyReject=void 0,this.proxyInitializedResolve=void 0,this.proxyInitializedReject=void 0,this.firstConnectionInfoResolve=void 0,this.firstConnectionInfoReject=void 0,this.readyPromise=void 0,this.proxyInitializedPromise=void 0,this.firstConnectionInfoPromise=void 0,this.ready=!1}}function E(e){const t=e instanceof Uint8Array?e:F(e);if(32!==t.length)throw new Error(`Invalid content reference length: ${t.length} (expected 32 bytes)`);const n=new K;return n.addFork("/",P,{"website-index-document":"index.bin"}),n.addFork("index.bin",t,{"Content-Type":"application/octet-stream",Filename:"index.bin"}),{manifestNode:n}}function j(e){let t=0;for(;e;)t+=1&e,e>>>=1;return t}function W(e){for(let t=0;t<e.length;t++)if(0!==e[t])return!1;return!0}function N(e){if(e.length<96)throw new Error(`Manifest too small: ${e.length} bytes (expected at least 96)`);const t=e.slice(64,96);if(W(t))throw new Error("Manifest entry is zero");return new U(t).toHex()}function $(e){if(e.length<192)throw new Error(`Manifest too small: ${e.length} bytes (expected at least 192)`);const t=e.slice(96,128),n=Math.floor(105/8);if(!(2&t[n]))throw new Error('Manifest does not contain "index.bin" fork');let i=0;for(let e=0;e<n;e++)i+=j(t[e]);for(let e=0;e<1;e++)t[n]&1<<e&&i++;let s=128;for(let t=0;t<i;t++){const t=e[s];if(s+=64,!!(16&t)){s+=2+(e[s]<<8|e[s+1])}}const r=e[s],o=e[s+1];if(105!==e[s+2])throw new Error(`Expected "index.bin" prefix, got byte 0x${e[s+2].toString(16)}`);if(o>=9){const t=e.slice(s+2,s+2+9),n=(new TextEncoder).encode("index.bin");t.every((e,t)=>e===n[t])||console.warn('[ManifestBuilder] Prefix does not fully match "index.bin"')}if(!!!(2&r))throw new Error('"index.bin" fork is not a VALUE type');const a=s+32,d=e.slice(a,a+32);if(W(d))throw new Error('Manifest "index.bin" fork has zero reference');return new U(d).toHex()}export{L as SwarmIdClient,t as SwarmIdError,z as TimeoutError,E as buildBzzManifestNode,O as collectionPath,$ as extractContentFromFlatManifest,N as extractEntryFromManifest,y as generatedAvatar,F as hexToUint8Array,c as uint8ArrayToHex,x as withTimeout};
|
|
2
2
|
//# sourceMappingURL=swarm-id.esm.js.map
|