@xmtp/browser-sdk 6.5.0 → 7.0.0-dev.b5cdc06
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 -0
- package/dist/index.d.ts +291 -51
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/workers/client.js +1 -1
- package/dist/workers/client.js.map +1 -1
- package/package.json +17 -8
- package/src/Client.ts +360 -14
- package/src/WorkerClient.ts +77 -8
- package/src/WorkerConversation.ts +4 -4
- package/src/constants.ts +5 -0
- package/src/index.ts +10 -1
- package/src/types/actions/client.ts +90 -2
- package/src/types/options.ts +44 -11
- package/src/utils/WorkerBridge.ts +1 -1
- package/src/utils/createBackend.ts +45 -0
- package/src/utils/createClient.ts +65 -27
- package/src/utils/inboxId.ts +5 -15
- package/src/utils/inboxState.ts +5 -9
- package/src/utils/installations.ts +8 -17
- package/src/utils/signer.ts +37 -1
- package/src/workers/client.ts +52 -2
package/src/Client.ts
CHANGED
|
@@ -1,6 +1,18 @@
|
|
|
1
1
|
import { type ContentCodec } from "@xmtp/content-type-primitives";
|
|
2
|
-
import {
|
|
2
|
+
import {
|
|
3
|
+
Backend,
|
|
4
|
+
BackupElementSelectionOption,
|
|
5
|
+
IdentifierKind,
|
|
6
|
+
LogLevel,
|
|
7
|
+
type ArchiveMetadata,
|
|
8
|
+
type ArchiveOptions,
|
|
9
|
+
type AvailableArchiveInfo,
|
|
10
|
+
type GroupSyncSummary,
|
|
11
|
+
type Identifier,
|
|
12
|
+
type InboxState,
|
|
13
|
+
} from "@xmtp/wasm-bindings";
|
|
3
14
|
import { CodecRegistry } from "@/CodecRegistry";
|
|
15
|
+
import { HistorySyncUrls } from "@/constants";
|
|
4
16
|
import { Conversations } from "@/Conversations";
|
|
5
17
|
import { DebugInformation } from "@/DebugInformation";
|
|
6
18
|
import { Preferences } from "@/Preferences";
|
|
@@ -10,6 +22,8 @@ import type {
|
|
|
10
22
|
ExtractCodecContentTypes,
|
|
11
23
|
XmtpEnv,
|
|
12
24
|
} from "@/types/options";
|
|
25
|
+
import { createBackend } from "@/utils/createBackend";
|
|
26
|
+
import { createClient as createLowLevelClient } from "@/utils/createClient";
|
|
13
27
|
import {
|
|
14
28
|
AccountAlreadyAssociatedError,
|
|
15
29
|
InboxReassignError,
|
|
@@ -22,6 +36,45 @@ import { toSafeSigner, type SafeSigner, type Signer } from "@/utils/signer";
|
|
|
22
36
|
import { uuid } from "@/utils/uuid";
|
|
23
37
|
import { WorkerBridge } from "@/utils/WorkerBridge";
|
|
24
38
|
|
|
39
|
+
/**
|
|
40
|
+
* Resolves a `Backend` instance from either a `Backend` or an `XmtpEnv` string.
|
|
41
|
+
*
|
|
42
|
+
* @param envOrBackend - A `Backend` instance, or an `XmtpEnv` string
|
|
43
|
+
* @param gatewayHost - Optional gateway host (only used when `envOrBackend` is an `XmtpEnv`)
|
|
44
|
+
* @returns A `Backend` instance
|
|
45
|
+
*/
|
|
46
|
+
const resolveBackend = async (
|
|
47
|
+
envOrBackend?: XmtpEnv | Backend,
|
|
48
|
+
gatewayHost?: string,
|
|
49
|
+
): Promise<Backend> => {
|
|
50
|
+
if (envOrBackend instanceof Backend) {
|
|
51
|
+
return envOrBackend;
|
|
52
|
+
}
|
|
53
|
+
return createBackend({ env: envOrBackend, gatewayHost });
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
const createEphemeralIdentifier = (): Identifier => {
|
|
57
|
+
const bytes = new Uint8Array(20);
|
|
58
|
+
globalThis.crypto.getRandomValues(bytes);
|
|
59
|
+
|
|
60
|
+
return {
|
|
61
|
+
identifier: `0x${Array.from(bytes, (byte) =>
|
|
62
|
+
byte.toString(16).padStart(2, "0"),
|
|
63
|
+
).join("")}`,
|
|
64
|
+
identifierKind: IdentifierKind.Ethereum,
|
|
65
|
+
};
|
|
66
|
+
};
|
|
67
|
+
|
|
68
|
+
const toInboxUpdatesCountMap = (
|
|
69
|
+
value: Map<string, number> | Record<string, number>,
|
|
70
|
+
) => {
|
|
71
|
+
if (value instanceof Map) {
|
|
72
|
+
return value;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
return new Map(Object.entries(value));
|
|
76
|
+
};
|
|
77
|
+
|
|
25
78
|
/**
|
|
26
79
|
* Client for interacting with the XMTP network
|
|
27
80
|
*/
|
|
@@ -30,6 +83,7 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
30
83
|
#codecRegistry: CodecRegistry;
|
|
31
84
|
#conversations: Conversations<ContentTypes>;
|
|
32
85
|
#debugInformation: DebugInformation;
|
|
86
|
+
#env?: XmtpEnv;
|
|
33
87
|
#identifier?: Identifier;
|
|
34
88
|
#inboxId?: string;
|
|
35
89
|
#installationId?: string;
|
|
@@ -97,6 +151,7 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
97
151
|
options: this.#options,
|
|
98
152
|
});
|
|
99
153
|
this.#appVersion = result.appVersion;
|
|
154
|
+
this.#env = result.env as XmtpEnv;
|
|
100
155
|
this.#identifier = identifier;
|
|
101
156
|
this.#inboxId = result.inboxId;
|
|
102
157
|
this.#installationId = result.installationId;
|
|
@@ -246,6 +301,13 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
246
301
|
return this.#appVersion;
|
|
247
302
|
}
|
|
248
303
|
|
|
304
|
+
/**
|
|
305
|
+
* Gets the XMTP environment used by this client
|
|
306
|
+
*/
|
|
307
|
+
get env() {
|
|
308
|
+
return this.#env;
|
|
309
|
+
}
|
|
310
|
+
|
|
249
311
|
/**
|
|
250
312
|
* Creates signature text for creating a new inbox
|
|
251
313
|
*
|
|
@@ -421,6 +483,7 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
421
483
|
return this.#worker.action("client.registerIdentity", {
|
|
422
484
|
signer,
|
|
423
485
|
signatureRequestId,
|
|
486
|
+
waitForRegistrationVisible: this.#options?.waitForRegistrationVisible,
|
|
424
487
|
});
|
|
425
488
|
}
|
|
426
489
|
|
|
@@ -559,10 +622,27 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
559
622
|
/**
|
|
560
623
|
* Revokes specific installations of the client's inbox without a client
|
|
561
624
|
*
|
|
562
|
-
* @param env - The environment to use
|
|
563
625
|
* @param signer - The signer to use
|
|
564
626
|
* @param inboxId - The inbox ID to revoke installations for
|
|
565
627
|
* @param installationIds - The installation IDs to revoke
|
|
628
|
+
* @param backend - Optional `Backend` instance created with `createBackend()`
|
|
629
|
+
*/
|
|
630
|
+
static async revokeInstallations(
|
|
631
|
+
signer: Signer,
|
|
632
|
+
inboxId: string,
|
|
633
|
+
installationIds: Uint8Array[],
|
|
634
|
+
backend?: Backend,
|
|
635
|
+
): Promise<void>;
|
|
636
|
+
/**
|
|
637
|
+
* Revokes specific installations of the client's inbox without a client
|
|
638
|
+
*
|
|
639
|
+
* @param signer - The signer to use
|
|
640
|
+
* @param inboxId - The inbox ID to revoke installations for
|
|
641
|
+
* @param installationIds - The installation IDs to revoke
|
|
642
|
+
* @param env - The environment to use
|
|
643
|
+
* @param gatewayHost - Optional gateway host
|
|
644
|
+
* @deprecated Pass a `Backend` instance created with `createBackend()` instead
|
|
645
|
+
* of `XmtpEnv` and `gatewayHost`.
|
|
566
646
|
*/
|
|
567
647
|
static async revokeInstallations(
|
|
568
648
|
signer: Signer,
|
|
@@ -570,30 +650,53 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
570
650
|
installationIds: Uint8Array[],
|
|
571
651
|
env?: XmtpEnv,
|
|
572
652
|
gatewayHost?: string,
|
|
653
|
+
): Promise<void>;
|
|
654
|
+
static async revokeInstallations(
|
|
655
|
+
signer: Signer,
|
|
656
|
+
inboxId: string,
|
|
657
|
+
installationIds: Uint8Array[],
|
|
658
|
+
envOrBackend?: XmtpEnv | Backend,
|
|
659
|
+
gatewayHost?: string,
|
|
573
660
|
) {
|
|
574
|
-
await
|
|
575
|
-
|
|
576
|
-
inboxId,
|
|
577
|
-
installationIds,
|
|
578
|
-
env,
|
|
579
|
-
gatewayHost,
|
|
580
|
-
);
|
|
661
|
+
const backend = await resolveBackend(envOrBackend, gatewayHost);
|
|
662
|
+
await utilsRevokeInstallations(backend, signer, inboxId, installationIds);
|
|
581
663
|
}
|
|
582
664
|
|
|
665
|
+
/**
|
|
666
|
+
* Fetches the inbox states for the specified inbox IDs from the network
|
|
667
|
+
* without a client
|
|
668
|
+
*
|
|
669
|
+
* @param inboxIds - The inbox IDs to get the state for
|
|
670
|
+
* @param backend - Optional `Backend` instance created with `createBackend()`
|
|
671
|
+
* @returns The inbox states for the specified inbox IDs
|
|
672
|
+
*/
|
|
673
|
+
static async fetchInboxStates(
|
|
674
|
+
inboxIds: string[],
|
|
675
|
+
backend?: Backend,
|
|
676
|
+
): Promise<InboxState[]>;
|
|
583
677
|
/**
|
|
584
678
|
* Fetches the inbox states for the specified inbox IDs from the network
|
|
585
679
|
* without a client
|
|
586
680
|
*
|
|
587
681
|
* @param inboxIds - The inbox IDs to get the state for
|
|
588
682
|
* @param env - The environment to use
|
|
683
|
+
* @param gatewayHost - Optional gateway host
|
|
589
684
|
* @returns The inbox states for the specified inbox IDs
|
|
685
|
+
* @deprecated Pass a `Backend` instance created with `createBackend()` instead
|
|
686
|
+
* of `XmtpEnv` and `gatewayHost`.
|
|
590
687
|
*/
|
|
591
688
|
static async fetchInboxStates(
|
|
592
689
|
inboxIds: string[],
|
|
593
690
|
env?: XmtpEnv,
|
|
594
691
|
gatewayHost?: string,
|
|
692
|
+
): Promise<InboxState[]>;
|
|
693
|
+
static async fetchInboxStates(
|
|
694
|
+
inboxIds: string[],
|
|
695
|
+
envOrBackend?: XmtpEnv | Backend,
|
|
696
|
+
gatewayHost?: string,
|
|
595
697
|
) {
|
|
596
|
-
|
|
698
|
+
const backend = await resolveBackend(envOrBackend, gatewayHost);
|
|
699
|
+
return utilsInboxStateFromInboxIds(backend, inboxIds);
|
|
597
700
|
}
|
|
598
701
|
|
|
599
702
|
/**
|
|
@@ -640,17 +743,66 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
640
743
|
return this.#worker.action("client.canMessage", { identifiers });
|
|
641
744
|
}
|
|
642
745
|
|
|
746
|
+
/**
|
|
747
|
+
* Fetches the latest inbox updates count for the specified inbox IDs
|
|
748
|
+
*
|
|
749
|
+
* @param inboxIds - The inbox IDs to check
|
|
750
|
+
* @returns Map of inbox IDs to their updates count
|
|
751
|
+
*/
|
|
752
|
+
async fetchLatestInboxUpdatesCount(inboxIds: string[]) {
|
|
753
|
+
const result = await this.#worker.action(
|
|
754
|
+
"client.fetchLatestInboxUpdatesCount",
|
|
755
|
+
{
|
|
756
|
+
inboxIds,
|
|
757
|
+
},
|
|
758
|
+
);
|
|
759
|
+
|
|
760
|
+
return toInboxUpdatesCountMap(result);
|
|
761
|
+
}
|
|
762
|
+
|
|
763
|
+
/**
|
|
764
|
+
* Fetches the latest inbox updates count for the client's inbox
|
|
765
|
+
*
|
|
766
|
+
* @returns The latest inbox updates count
|
|
767
|
+
*/
|
|
768
|
+
async fetchOwnInboxUpdatesCount() {
|
|
769
|
+
return this.#worker.action("client.fetchOwnInboxUpdatesCount", {});
|
|
770
|
+
}
|
|
771
|
+
|
|
772
|
+
/**
|
|
773
|
+
* Checks if the specified identifiers can be messaged
|
|
774
|
+
*
|
|
775
|
+
* @param identifiers - The identifiers to check
|
|
776
|
+
* @param backend - Optional `Backend` instance created with `createBackend()`
|
|
777
|
+
* @returns Map of identifiers to whether they can be messaged
|
|
778
|
+
*/
|
|
779
|
+
static async canMessage(
|
|
780
|
+
identifiers: Identifier[],
|
|
781
|
+
backend?: Backend,
|
|
782
|
+
): Promise<Map<string, boolean>>;
|
|
643
783
|
/**
|
|
644
784
|
* Checks if the specified identifiers can be messaged
|
|
645
785
|
*
|
|
646
786
|
* @param identifiers - The identifiers to check
|
|
647
787
|
* @param env - Optional XMTP environment
|
|
648
788
|
* @returns Map of identifiers to whether they can be messaged
|
|
789
|
+
* @deprecated Pass a `Backend` instance created with `createBackend()` instead
|
|
790
|
+
* of `XmtpEnv`.
|
|
649
791
|
*/
|
|
650
|
-
|
|
792
|
+
/* eslint-disable @typescript-eslint/unified-signatures */
|
|
793
|
+
static async canMessage(
|
|
794
|
+
identifiers: Identifier[],
|
|
795
|
+
env?: XmtpEnv,
|
|
796
|
+
): Promise<Map<string, boolean>>;
|
|
797
|
+
/* eslint-enable @typescript-eslint/unified-signatures */
|
|
798
|
+
static async canMessage(
|
|
799
|
+
identifiers: Identifier[],
|
|
800
|
+
envOrBackend?: XmtpEnv | Backend,
|
|
801
|
+
) {
|
|
802
|
+
const backend = await resolveBackend(envOrBackend);
|
|
651
803
|
const canMessageMap = new Map<string, boolean>();
|
|
652
804
|
for (const identifier of identifiers) {
|
|
653
|
-
const inboxId = await getInboxIdForIdentifier(
|
|
805
|
+
const inboxId = await getInboxIdForIdentifier(backend, identifier);
|
|
654
806
|
canMessageMap.set(
|
|
655
807
|
identifier.identifier.toLowerCase(),
|
|
656
808
|
inboxId !== undefined,
|
|
@@ -659,6 +811,60 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
659
811
|
return canMessageMap;
|
|
660
812
|
}
|
|
661
813
|
|
|
814
|
+
/**
|
|
815
|
+
* Fetches the latest inbox updates count for the specified inbox IDs
|
|
816
|
+
* without a client
|
|
817
|
+
*
|
|
818
|
+
* @param inboxIds - The inbox IDs to check
|
|
819
|
+
* @param backend - Optional `Backend` instance created with `createBackend()`
|
|
820
|
+
* @returns Map of inbox IDs to their updates count
|
|
821
|
+
*/
|
|
822
|
+
static async fetchLatestInboxUpdatesCount(
|
|
823
|
+
inboxIds: string[],
|
|
824
|
+
backendOrEnv?: Backend | XmtpEnv,
|
|
825
|
+
): Promise<Map<string, number>>;
|
|
826
|
+
/**
|
|
827
|
+
* Fetches the latest inbox updates count for the specified inbox IDs
|
|
828
|
+
* without a client
|
|
829
|
+
*
|
|
830
|
+
* @param inboxIds - The inbox IDs to check
|
|
831
|
+
* @param env - Optional XMTP environment
|
|
832
|
+
* @param gatewayHost - Optional gateway host
|
|
833
|
+
* @returns Map of inbox IDs to their updates count
|
|
834
|
+
* @deprecated Pass a `Backend` instance created with `createBackend()` instead
|
|
835
|
+
* of `XmtpEnv` and `gatewayHost`.
|
|
836
|
+
*/
|
|
837
|
+
static async fetchLatestInboxUpdatesCount(
|
|
838
|
+
inboxIds: string[],
|
|
839
|
+
env?: XmtpEnv,
|
|
840
|
+
gatewayHost?: string,
|
|
841
|
+
): Promise<Map<string, number>>;
|
|
842
|
+
static async fetchLatestInboxUpdatesCount(
|
|
843
|
+
inboxIds: string[],
|
|
844
|
+
envOrBackend?: XmtpEnv | Backend,
|
|
845
|
+
gatewayHost?: string,
|
|
846
|
+
) {
|
|
847
|
+
const backend = await resolveBackend(envOrBackend, gatewayHost);
|
|
848
|
+
const { client } = await createLowLevelClient(createEphemeralIdentifier(), {
|
|
849
|
+
backend,
|
|
850
|
+
dbPath: null,
|
|
851
|
+
disableDeviceSync: true,
|
|
852
|
+
});
|
|
853
|
+
// The wasm-bindings Client holds WASM-linear-memory allocations that are
|
|
854
|
+
// not reclaimed by the JS GC. Free the ephemeral client in finally so the
|
|
855
|
+
// allocation is released even if the fetch rejects.
|
|
856
|
+
try {
|
|
857
|
+
const result = (await client.fetchLatestInboxUpdatesCount(
|
|
858
|
+
true,
|
|
859
|
+
inboxIds,
|
|
860
|
+
)) as Record<string, number> | Map<string, number>;
|
|
861
|
+
|
|
862
|
+
return toInboxUpdatesCountMap(result);
|
|
863
|
+
} finally {
|
|
864
|
+
client.free();
|
|
865
|
+
}
|
|
866
|
+
}
|
|
867
|
+
|
|
662
868
|
/**
|
|
663
869
|
* Fetches the inbox ID for a given identifier from the local database
|
|
664
870
|
* If not found, fetches from the network
|
|
@@ -732,12 +938,152 @@ export class Client<ContentTypes = ExtractCodecContentTypes> {
|
|
|
732
938
|
});
|
|
733
939
|
}
|
|
734
940
|
|
|
941
|
+
/**
|
|
942
|
+
* Get the default archive options (consent and messages)
|
|
943
|
+
*/
|
|
944
|
+
#getDefaultArchiveOptions(): ArchiveOptions {
|
|
945
|
+
return {
|
|
946
|
+
elements: [
|
|
947
|
+
BackupElementSelectionOption.Consent,
|
|
948
|
+
BackupElementSelectionOption.Messages,
|
|
949
|
+
],
|
|
950
|
+
excludeDisappearingMessages: false,
|
|
951
|
+
};
|
|
952
|
+
}
|
|
953
|
+
|
|
954
|
+
/**
|
|
955
|
+
* Get the default server URL based on the environment
|
|
956
|
+
*/
|
|
957
|
+
#getDefaultServerUrl(): string {
|
|
958
|
+
const env = this.#env ?? "dev";
|
|
959
|
+
return HistorySyncUrls[env];
|
|
960
|
+
}
|
|
961
|
+
|
|
735
962
|
/**
|
|
736
963
|
* Send a sync request to other devices on the network
|
|
737
964
|
*
|
|
965
|
+
* @param options - Archive options specifying what to sync (defaults to consent and messages)
|
|
966
|
+
* @param serverUrl - The server URL for the sync request (defaults to environment-specific URL)
|
|
738
967
|
* @returns Promise that resolves when the sync request is sent
|
|
739
968
|
*/
|
|
740
|
-
async sendSyncRequest() {
|
|
741
|
-
|
|
969
|
+
async sendSyncRequest(options?: ArchiveOptions, serverUrl?: string) {
|
|
970
|
+
const resolvedOptions = options ?? this.#getDefaultArchiveOptions();
|
|
971
|
+
const resolvedServerUrl = serverUrl ?? this.#getDefaultServerUrl();
|
|
972
|
+
|
|
973
|
+
return this.#worker.action("client.sendSyncRequest", {
|
|
974
|
+
options: resolvedOptions,
|
|
975
|
+
serverUrl: resolvedServerUrl,
|
|
976
|
+
});
|
|
977
|
+
}
|
|
978
|
+
|
|
979
|
+
/**
|
|
980
|
+
* Send a sync archive to the sync group
|
|
981
|
+
*
|
|
982
|
+
* @param pin - The pin used for reference when importing
|
|
983
|
+
* @param options - Archive options specifying what to sync (defaults to consent and messages)
|
|
984
|
+
* @param serverUrl - The server URL for the sync archive (defaults to environment-specific URL)
|
|
985
|
+
* @returns Promise that resolves when the sync archive is sent
|
|
986
|
+
*/
|
|
987
|
+
async sendSyncArchive(
|
|
988
|
+
pin: string,
|
|
989
|
+
options?: ArchiveOptions,
|
|
990
|
+
serverUrl?: string,
|
|
991
|
+
) {
|
|
992
|
+
const resolvedOptions = options ?? this.#getDefaultArchiveOptions();
|
|
993
|
+
const resolvedServerUrl = serverUrl ?? this.#getDefaultServerUrl();
|
|
994
|
+
|
|
995
|
+
return this.#worker.action("client.sendSyncArchive", {
|
|
996
|
+
options: resolvedOptions,
|
|
997
|
+
serverUrl: resolvedServerUrl,
|
|
998
|
+
pin,
|
|
999
|
+
});
|
|
1000
|
+
}
|
|
1001
|
+
|
|
1002
|
+
/**
|
|
1003
|
+
* Process a sync archive that matches the pin given
|
|
1004
|
+
*
|
|
1005
|
+
* @param archivePin - Optional pin to match. If not provided, processes the last archive sent
|
|
1006
|
+
* @returns Promise that resolves when the archive is processed
|
|
1007
|
+
*/
|
|
1008
|
+
async processSyncArchive(archivePin?: string | null) {
|
|
1009
|
+
return this.#worker.action("client.processSyncArchive", {
|
|
1010
|
+
archivePin,
|
|
1011
|
+
});
|
|
1012
|
+
}
|
|
1013
|
+
|
|
1014
|
+
/**
|
|
1015
|
+
* List the archives available for import in the sync group
|
|
1016
|
+
*
|
|
1017
|
+
* You may need to manually sync the sync group before calling
|
|
1018
|
+
* this function to see recently uploaded archives.
|
|
1019
|
+
*
|
|
1020
|
+
* @param daysCutoff - Number of days to look back for archives
|
|
1021
|
+
* @returns Promise that resolves with array of available archive information
|
|
1022
|
+
*/
|
|
1023
|
+
async listAvailableArchives(
|
|
1024
|
+
daysCutoff: number,
|
|
1025
|
+
): Promise<AvailableArchiveInfo[]> {
|
|
1026
|
+
return this.#worker.action("client.listAvailableArchives", {
|
|
1027
|
+
daysCutoff,
|
|
1028
|
+
});
|
|
1029
|
+
}
|
|
1030
|
+
|
|
1031
|
+
/**
|
|
1032
|
+
* Export archive data to bytes for later restoration
|
|
1033
|
+
*
|
|
1034
|
+
* @param key - Encryption key for the archive
|
|
1035
|
+
* @param opts - Archive options specifying what to include (defaults to consent and messages)
|
|
1036
|
+
* @returns Promise that resolves with the archive data as bytes
|
|
1037
|
+
*/
|
|
1038
|
+
async createArchive(
|
|
1039
|
+
key: Uint8Array,
|
|
1040
|
+
opts?: ArchiveOptions,
|
|
1041
|
+
): Promise<Uint8Array> {
|
|
1042
|
+
const resolvedOpts = opts ?? this.#getDefaultArchiveOptions();
|
|
1043
|
+
|
|
1044
|
+
return this.#worker.action("client.createArchive", {
|
|
1045
|
+
opts: resolvedOpts,
|
|
1046
|
+
key,
|
|
1047
|
+
});
|
|
1048
|
+
}
|
|
1049
|
+
|
|
1050
|
+
/**
|
|
1051
|
+
* Import an archive from bytes
|
|
1052
|
+
*
|
|
1053
|
+
* @param data - The archive data as bytes
|
|
1054
|
+
* @param key - Encryption key for the archive
|
|
1055
|
+
* @returns Promise that resolves when the archive is imported
|
|
1056
|
+
*/
|
|
1057
|
+
async importArchive(data: Uint8Array, key: Uint8Array) {
|
|
1058
|
+
return this.#worker.action("client.importArchive", {
|
|
1059
|
+
data,
|
|
1060
|
+
key,
|
|
1061
|
+
});
|
|
1062
|
+
}
|
|
1063
|
+
|
|
1064
|
+
/**
|
|
1065
|
+
* Load the metadata for an archive to see what it contains
|
|
1066
|
+
*
|
|
1067
|
+
* @param data - The archive data as bytes
|
|
1068
|
+
* @param key - Encryption key for the archive
|
|
1069
|
+
* @returns Promise that resolves with the archive metadata
|
|
1070
|
+
*/
|
|
1071
|
+
async archiveMetadata(
|
|
1072
|
+
data: Uint8Array,
|
|
1073
|
+
key: Uint8Array,
|
|
1074
|
+
): Promise<ArchiveMetadata> {
|
|
1075
|
+
return this.#worker.action("client.archiveMetadata", {
|
|
1076
|
+
data,
|
|
1077
|
+
key,
|
|
1078
|
+
});
|
|
1079
|
+
}
|
|
1080
|
+
|
|
1081
|
+
/**
|
|
1082
|
+
* Manually sync all device sync groups
|
|
1083
|
+
*
|
|
1084
|
+
* @returns Promise that resolves with a summary of the sync operation
|
|
1085
|
+
*/
|
|
1086
|
+
async syncAllDeviceSyncGroups(): Promise<GroupSyncSummary> {
|
|
1087
|
+
return this.#worker.action("client.syncAllDeviceSyncGroups");
|
|
742
1088
|
}
|
|
743
1089
|
}
|
package/src/WorkerClient.ts
CHANGED
|
@@ -1,11 +1,19 @@
|
|
|
1
1
|
import {
|
|
2
2
|
verifySignedWithPublicKey,
|
|
3
|
+
type ArchiveMetadata,
|
|
4
|
+
type ArchiveOptions,
|
|
5
|
+
type AvailableArchiveInfo,
|
|
3
6
|
type Client,
|
|
7
|
+
type GroupSyncSummary,
|
|
4
8
|
type Identifier,
|
|
5
9
|
type KeyPackageStatus,
|
|
6
10
|
type SignatureRequestHandle,
|
|
7
11
|
} from "@xmtp/wasm-bindings";
|
|
8
|
-
import type {
|
|
12
|
+
import type {
|
|
13
|
+
ClientOptions,
|
|
14
|
+
VisibilityConfirmationOptions,
|
|
15
|
+
XmtpEnv,
|
|
16
|
+
} from "@/types/options";
|
|
9
17
|
import { createClient } from "@/utils/createClient";
|
|
10
18
|
import type { SafeSigner } from "@/utils/signer";
|
|
11
19
|
import { WorkerConversations } from "@/WorkerConversations";
|
|
@@ -16,10 +24,12 @@ export class WorkerClient {
|
|
|
16
24
|
#client: Client;
|
|
17
25
|
#conversations: WorkerConversations;
|
|
18
26
|
#debugInformation: WorkerDebugInformation;
|
|
27
|
+
#env: XmtpEnv;
|
|
19
28
|
#preferences: WorkerPreferences;
|
|
20
29
|
|
|
21
|
-
constructor(client: Client) {
|
|
30
|
+
constructor(client: Client, env: XmtpEnv) {
|
|
22
31
|
this.#client = client;
|
|
32
|
+
this.#env = env;
|
|
23
33
|
const conversations = client.conversations();
|
|
24
34
|
this.#conversations = new WorkerConversations(this, conversations);
|
|
25
35
|
this.#debugInformation = new WorkerDebugInformation(client);
|
|
@@ -30,8 +40,8 @@ export class WorkerClient {
|
|
|
30
40
|
identifier: Identifier,
|
|
31
41
|
options?: Omit<ClientOptions, "codecs">,
|
|
32
42
|
) {
|
|
33
|
-
const client = await createClient(identifier, options);
|
|
34
|
-
return new WorkerClient(client);
|
|
43
|
+
const { client, env } = await createClient(identifier, options);
|
|
44
|
+
return new WorkerClient(client, env);
|
|
35
45
|
}
|
|
36
46
|
|
|
37
47
|
get libxmtpVersion() {
|
|
@@ -42,6 +52,10 @@ export class WorkerClient {
|
|
|
42
52
|
return this.#client.appVersion;
|
|
43
53
|
}
|
|
44
54
|
|
|
55
|
+
get env() {
|
|
56
|
+
return this.#env;
|
|
57
|
+
}
|
|
58
|
+
|
|
45
59
|
get accountIdentifier() {
|
|
46
60
|
return this.#client.accountIdentifier;
|
|
47
61
|
}
|
|
@@ -80,6 +94,19 @@ export class WorkerClient {
|
|
|
80
94
|
>;
|
|
81
95
|
}
|
|
82
96
|
|
|
97
|
+
async fetchLatestInboxUpdatesCount(inboxIds: string[]) {
|
|
98
|
+
const result = (await this.#client.fetchLatestInboxUpdatesCount(
|
|
99
|
+
true,
|
|
100
|
+
inboxIds,
|
|
101
|
+
)) as Map<string, number> | Record<string, number>;
|
|
102
|
+
|
|
103
|
+
return result instanceof Map ? Object.fromEntries(result) : result;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
async fetchOwnInboxUpdatesCount() {
|
|
107
|
+
return this.#client.fetchOwnInboxUpdatesCount(true);
|
|
108
|
+
}
|
|
109
|
+
|
|
83
110
|
async addSignature(
|
|
84
111
|
signatureRequest: SignatureRequestHandle,
|
|
85
112
|
signer: SafeSigner,
|
|
@@ -138,13 +165,17 @@ export class WorkerClient {
|
|
|
138
165
|
async registerIdentity(
|
|
139
166
|
signer: SafeSigner,
|
|
140
167
|
signatureRequest: SignatureRequestHandle,
|
|
168
|
+
visibilityConfirmationOptions?: VisibilityConfirmationOptions,
|
|
141
169
|
) {
|
|
142
170
|
await this.addSignature(signatureRequest, signer);
|
|
143
|
-
await this.#client.registerIdentity(
|
|
171
|
+
await this.#client.registerIdentity(
|
|
172
|
+
signatureRequest,
|
|
173
|
+
visibilityConfirmationOptions,
|
|
174
|
+
);
|
|
144
175
|
}
|
|
145
176
|
|
|
146
177
|
async getInboxIdByIdentifier(identifier: Identifier) {
|
|
147
|
-
return this.#client.
|
|
178
|
+
return this.#client.findInboxIdByIdentity(identifier);
|
|
148
179
|
}
|
|
149
180
|
|
|
150
181
|
signWithInstallationKey(signatureText: string) {
|
|
@@ -185,7 +216,45 @@ export class WorkerClient {
|
|
|
185
216
|
) as Promise<Map<string, KeyPackageStatus>>;
|
|
186
217
|
}
|
|
187
218
|
|
|
188
|
-
async sendSyncRequest() {
|
|
189
|
-
return this.#client.sendSyncRequest();
|
|
219
|
+
async sendSyncRequest(options: ArchiveOptions, serverUrl: string) {
|
|
220
|
+
return this.#client.device_sync().sendSyncRequest(options, serverUrl);
|
|
221
|
+
}
|
|
222
|
+
|
|
223
|
+
async sendSyncArchive(
|
|
224
|
+
options: ArchiveOptions,
|
|
225
|
+
serverUrl: string,
|
|
226
|
+
pin: string,
|
|
227
|
+
) {
|
|
228
|
+
return this.#client.device_sync().sendSyncArchive(options, serverUrl, pin);
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
async processSyncArchive(archivePin?: string | null) {
|
|
232
|
+
return this.#client.device_sync().processSyncArchive(archivePin);
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
listAvailableArchives(daysCutoff: number): AvailableArchiveInfo[] {
|
|
236
|
+
return this.#client.device_sync().listAvailableArchives(BigInt(daysCutoff));
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
async createArchive(
|
|
240
|
+
opts: ArchiveOptions,
|
|
241
|
+
key: Uint8Array,
|
|
242
|
+
): Promise<Uint8Array> {
|
|
243
|
+
return this.#client.device_sync().createArchive(opts, key);
|
|
244
|
+
}
|
|
245
|
+
|
|
246
|
+
async importArchive(data: Uint8Array, key: Uint8Array) {
|
|
247
|
+
return this.#client.device_sync().importArchive(data, key);
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
async archiveMetadata(
|
|
251
|
+
data: Uint8Array,
|
|
252
|
+
key: Uint8Array,
|
|
253
|
+
): Promise<ArchiveMetadata> {
|
|
254
|
+
return this.#client.device_sync().archiveMetadata(data, key);
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
async syncAllDeviceSyncGroups(): Promise<GroupSyncSummary> {
|
|
258
|
+
return this.#client.device_sync().syncAllDeviceSyncGroups();
|
|
190
259
|
}
|
|
191
260
|
}
|
|
@@ -153,19 +153,19 @@ export class WorkerConversation {
|
|
|
153
153
|
}
|
|
154
154
|
|
|
155
155
|
async addMembersByIdentifiers(identifiers: Identifier[]) {
|
|
156
|
-
return this.#group.
|
|
156
|
+
return this.#group.addMembersByIdentity(identifiers);
|
|
157
157
|
}
|
|
158
158
|
|
|
159
159
|
async addMembers(inboxIds: string[]) {
|
|
160
|
-
return this.#group.
|
|
160
|
+
return this.#group.addMembers(inboxIds);
|
|
161
161
|
}
|
|
162
162
|
|
|
163
163
|
async removeMembersByIdentifiers(identifiers: Identifier[]) {
|
|
164
|
-
return this.#group.
|
|
164
|
+
return this.#group.removeMembersByIdentity(identifiers);
|
|
165
165
|
}
|
|
166
166
|
|
|
167
167
|
async removeMembers(inboxIds: string[]) {
|
|
168
|
-
return this.#group.
|
|
168
|
+
return this.#group.removeMembers(inboxIds);
|
|
169
169
|
}
|
|
170
170
|
|
|
171
171
|
async addAdmin(inboxId: string) {
|
package/src/constants.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Pre-configured URLs for the XMTP network based on the environment
|
|
3
3
|
*
|
|
4
|
+
* @deprecated Use `createBackend()` instead.
|
|
4
5
|
* @constant
|
|
5
6
|
* @property {string} local - The local URL for the XMTP network
|
|
6
7
|
* @property {string} dev - The development URL for the XMTP network
|
|
@@ -24,4 +25,8 @@ export const HistorySyncUrls = {
|
|
|
24
25
|
local: "http://localhost:5558",
|
|
25
26
|
dev: "https://message-history.dev.ephemera.network",
|
|
26
27
|
production: "https://message-history.production.ephemera.network",
|
|
28
|
+
"testnet-staging": "https://message-history.dev.ephemera.network",
|
|
29
|
+
"testnet-dev": "https://message-history.dev.ephemera.network",
|
|
30
|
+
testnet: "https://message-history.dev.ephemera.network",
|
|
31
|
+
mainnet: "https://message-history.production.ephemera.network",
|
|
27
32
|
} as const;
|