@metamask/connect-multichain 0.2.0 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (42) hide show
  1. package/CHANGELOG.md +8 -1
  2. package/dist/browser/es/connect-multichain.d.mts +25 -1
  3. package/dist/browser/es/connect-multichain.mjs +437 -234
  4. package/dist/browser/es/connect-multichain.mjs.map +1 -1
  5. package/dist/browser/es/metafile-esm.json +1 -1
  6. package/dist/browser/iife/connect-multichain.d.ts +25 -1
  7. package/dist/browser/iife/connect-multichain.js +21353 -14490
  8. package/dist/browser/iife/connect-multichain.js.map +1 -1
  9. package/dist/browser/iife/metafile-iife.json +1 -1
  10. package/dist/browser/umd/connect-multichain.d.ts +25 -1
  11. package/dist/browser/umd/connect-multichain.js +434 -231
  12. package/dist/browser/umd/connect-multichain.js.map +1 -1
  13. package/dist/browser/umd/metafile-cjs.json +1 -1
  14. package/dist/node/cjs/connect-multichain.d.ts +25 -1
  15. package/dist/node/cjs/connect-multichain.js +437 -232
  16. package/dist/node/cjs/connect-multichain.js.map +1 -1
  17. package/dist/node/cjs/metafile-cjs.json +1 -1
  18. package/dist/node/es/connect-multichain.d.mts +25 -1
  19. package/dist/node/es/connect-multichain.mjs +438 -235
  20. package/dist/node/es/connect-multichain.mjs.map +1 -1
  21. package/dist/node/es/metafile-esm.json +1 -1
  22. package/dist/react-native/es/connect-multichain.d.mts +25 -1
  23. package/dist/react-native/es/connect-multichain.mjs +437 -234
  24. package/dist/react-native/es/connect-multichain.mjs.map +1 -1
  25. package/dist/react-native/es/metafile-esm.json +1 -1
  26. package/dist/src/domain/utils/index.d.ts +1 -0
  27. package/dist/src/domain/utils/index.d.ts.map +1 -1
  28. package/dist/src/domain/utils/index.js +1 -0
  29. package/dist/src/domain/utils/index.js.map +1 -1
  30. package/dist/src/multichain/index.d.ts.map +1 -1
  31. package/dist/src/multichain/index.js +73 -17
  32. package/dist/src/multichain/index.js.map +1 -1
  33. package/dist/src/multichain/rpc/requestRouter.d.ts +1 -0
  34. package/dist/src/multichain/rpc/requestRouter.d.ts.map +1 -1
  35. package/dist/src/multichain/rpc/requestRouter.js +69 -13
  36. package/dist/src/multichain/rpc/requestRouter.js.map +1 -1
  37. package/dist/src/multichain/utils/analytics.d.ts +39 -0
  38. package/dist/src/multichain/utils/analytics.d.ts.map +1 -0
  39. package/dist/src/multichain/utils/analytics.js +83 -0
  40. package/dist/src/multichain/utils/analytics.js.map +1 -0
  41. package/dist/types/connect-multichain.d.ts +25 -1
  42. package/package.json +2 -2
@@ -604,13 +604,262 @@ var init_ui = __esm({
604
604
  }
605
605
  });
606
606
 
607
+ // src/multichain/utils/index.ts
608
+ function base64Encode(str) {
609
+ if (typeof btoa !== "undefined") {
610
+ return btoa(str);
611
+ } else if (typeof Buffer !== "undefined") {
612
+ return Buffer.from(str).toString("base64");
613
+ }
614
+ throw new Error("No base64 encoding method available");
615
+ }
616
+ function compressString(str) {
617
+ const compressed = (0, import_pako.deflate)(str);
618
+ const binaryString = String.fromCharCode.apply(null, Array.from(compressed));
619
+ return base64Encode(binaryString);
620
+ }
621
+ function getDappId(dapp) {
622
+ var _a, _b;
623
+ if (typeof window === "undefined" || typeof window.location === "undefined") {
624
+ return (_b = (_a = dapp == null ? void 0 : dapp.name) != null ? _a : dapp == null ? void 0 : dapp.url) != null ? _b : "N/A";
625
+ }
626
+ return window.location.hostname;
627
+ }
628
+ function openDeeplink(options, deeplink, universalLink) {
629
+ const { mobile } = options;
630
+ const useDeeplink = mobile && mobile.useDeeplink !== void 0 ? mobile.useDeeplink : true;
631
+ if (useDeeplink) {
632
+ if (typeof window !== "undefined") {
633
+ window.location.href = deeplink;
634
+ }
635
+ } else if (typeof document !== "undefined") {
636
+ const link = document.createElement("a");
637
+ link.href = universalLink;
638
+ link.target = "_self";
639
+ link.rel = "noreferrer noopener";
640
+ link.click();
641
+ }
642
+ }
643
+ function getOptionalScopes(scopes) {
644
+ return scopes.reduce(
645
+ (prev, scope) => __spreadProps(__spreadValues({}, prev), {
646
+ [scope]: {
647
+ methods: [],
648
+ notifications: [],
649
+ accounts: []
650
+ }
651
+ }),
652
+ {}
653
+ );
654
+ }
655
+ function setupDappMetadata(options) {
656
+ var _a;
657
+ const platform = getPlatformType();
658
+ const isBrowser = platform === "web-desktop" /* DesktopWeb */ || platform === "web-mobile" /* MobileWeb */ || platform === "in-app-browser" /* MetaMaskMobileWebview */;
659
+ if (!((_a = options.dapp) == null ? void 0 : _a.url)) {
660
+ if (isBrowser) {
661
+ options.dapp = __spreadProps(__spreadValues({}, options.dapp), {
662
+ url: `${window.location.protocol}//${window.location.host}`
663
+ });
664
+ } else {
665
+ throw new Error("You must provide dapp url");
666
+ }
667
+ }
668
+ const BASE_64_ICON_MAX_LENGTH = 163400;
669
+ const urlPattern = /^(http|https):\/\/[^\s]*$/;
670
+ if (options.dapp) {
671
+ if ("iconUrl" in options.dapp) {
672
+ if (options.dapp.iconUrl && !urlPattern.test(options.dapp.iconUrl)) {
673
+ console.warn(
674
+ "Invalid dappMetadata.iconUrl: URL must start with http:// or https://"
675
+ );
676
+ options.dapp.iconUrl = void 0;
677
+ }
678
+ }
679
+ if ("base64Icon" in options.dapp) {
680
+ if (options.dapp.base64Icon && options.dapp.base64Icon.length > BASE_64_ICON_MAX_LENGTH) {
681
+ console.warn(
682
+ "Invalid dappMetadata.base64Icon: Base64-encoded icon string length must be less than 163400 characters"
683
+ );
684
+ options.dapp.base64Icon = void 0;
685
+ }
686
+ }
687
+ if (options.dapp.url && !urlPattern.test(options.dapp.url)) {
688
+ console.warn(
689
+ "Invalid dappMetadata.url: URL must start with http:// or https://"
690
+ );
691
+ }
692
+ const favicon = extractFavicon();
693
+ if (favicon && !("iconUrl" in options.dapp) && !("base64Icon" in options.dapp)) {
694
+ const faviconUrl = `${window.location.protocol}//${window.location.host}${favicon}`;
695
+ options.dapp.iconUrl = faviconUrl;
696
+ }
697
+ }
698
+ return options;
699
+ }
700
+ function isSameScopesAndAccounts(currentScopes, proposedScopes, walletSession, proposedCaipAccountIds) {
701
+ const isSameScopes = currentScopes.every((scope) => proposedScopes.includes(scope)) && proposedScopes.every((scope) => currentScopes.includes(scope));
702
+ if (!isSameScopes) {
703
+ return false;
704
+ }
705
+ const existingAccountIds = Object.values(
706
+ walletSession.sessionScopes
707
+ ).filter(({ accounts }) => Boolean(accounts)).flatMap(({ accounts }) => accounts != null ? accounts : []);
708
+ const allProposedAccountsIncluded = proposedCaipAccountIds.every(
709
+ (proposedAccountId) => existingAccountIds.includes(proposedAccountId)
710
+ );
711
+ return allProposedAccountsIncluded;
712
+ }
713
+ function getValidAccounts(caipAccountIds) {
714
+ return caipAccountIds.reduce(
715
+ (caipAccounts, caipAccountId) => {
716
+ try {
717
+ return [...caipAccounts, (0, import_utils.parseCaipAccountId)(caipAccountId)];
718
+ } catch (err) {
719
+ const stringifiedAccountId = JSON.stringify(caipAccountId);
720
+ console.error(`Invalid CAIP account ID: ${stringifiedAccountId}`, err);
721
+ return caipAccounts;
722
+ }
723
+ },
724
+ []
725
+ );
726
+ }
727
+ function addValidAccounts(optionalScopes, validAccounts) {
728
+ var _a;
729
+ if (!optionalScopes || !(validAccounts == null ? void 0 : validAccounts.length)) {
730
+ return optionalScopes;
731
+ }
732
+ const result = Object.fromEntries(
733
+ Object.entries(optionalScopes).map(([scope, scopeData]) => {
734
+ var _a2, _b, _c;
735
+ return [
736
+ scope,
737
+ {
738
+ methods: [...(_a2 = scopeData == null ? void 0 : scopeData.methods) != null ? _a2 : []],
739
+ notifications: [...(_b = scopeData == null ? void 0 : scopeData.notifications) != null ? _b : []],
740
+ accounts: [...(_c = scopeData == null ? void 0 : scopeData.accounts) != null ? _c : []]
741
+ }
742
+ ];
743
+ })
744
+ );
745
+ const accountsByChain = /* @__PURE__ */ new Map();
746
+ for (const account of validAccounts) {
747
+ const chainKey = `${account.chain.namespace}:${account.chain.reference}`;
748
+ const accountId = `${account.chainId}:${account.address}`;
749
+ if (!accountsByChain.has(chainKey)) {
750
+ accountsByChain.set(chainKey, []);
751
+ }
752
+ (_a = accountsByChain.get(chainKey)) == null ? void 0 : _a.push(accountId);
753
+ }
754
+ for (const [scopeKey, scopeData] of Object.entries(result)) {
755
+ if (!(scopeData == null ? void 0 : scopeData.accounts)) {
756
+ continue;
757
+ }
758
+ try {
759
+ const scope = scopeKey;
760
+ const scopeDetails = (0, import_utils.parseCaipChainId)(scope);
761
+ const chainKey = `${scopeDetails.namespace}:${scopeDetails.reference}`;
762
+ const matchingAccounts = accountsByChain.get(chainKey);
763
+ if (matchingAccounts) {
764
+ const existingAccounts = new Set(scopeData.accounts);
765
+ const newAccounts = matchingAccounts.filter(
766
+ (account) => !existingAccounts.has(account)
767
+ );
768
+ scopeData.accounts.push(...newAccounts);
769
+ }
770
+ } catch (error) {
771
+ console.error(`Invalid scope format: ${scopeKey}`, error);
772
+ }
773
+ }
774
+ return result;
775
+ }
776
+ var import_pako, import_utils, extractFavicon;
777
+ var init_utils = __esm({
778
+ "src/multichain/utils/index.ts"() {
779
+ "use strict";
780
+ import_pako = require("pako");
781
+ import_utils = require("@metamask/utils");
782
+ init_domain();
783
+ extractFavicon = () => {
784
+ var _a;
785
+ if (typeof document === "undefined") {
786
+ return void 0;
787
+ }
788
+ let favicon;
789
+ const nodeList = document.getElementsByTagName("link");
790
+ for (let i = 0; i < nodeList.length; i++) {
791
+ if (nodeList[i].getAttribute("rel") === "icon" || nodeList[i].getAttribute("rel") === "shortcut icon") {
792
+ favicon = (_a = nodeList[i].getAttribute("href")) != null ? _a : void 0;
793
+ }
794
+ }
795
+ return favicon;
796
+ };
797
+ }
798
+ });
799
+
800
+ // src/multichain/utils/analytics.ts
801
+ function isRejectionError(error) {
802
+ var _a, _b;
803
+ if (typeof error !== "object" || error === null) {
804
+ return false;
805
+ }
806
+ const errorObj = error;
807
+ const errorCode = errorObj.code;
808
+ const errorMessage = (_b = (_a = errorObj.message) == null ? void 0 : _a.toLowerCase()) != null ? _b : "";
809
+ return errorCode === 4001 || // User rejected request (common EIP-1193 code)
810
+ errorCode === 4100 || // Unauthorized (common rejection code)
811
+ errorMessage.includes("reject") || errorMessage.includes("denied") || errorMessage.includes("cancel") || errorMessage.includes("user");
812
+ }
813
+ function getBaseAnalyticsProperties(options, storage) {
814
+ return __async(this, null, function* () {
815
+ var _a, _b;
816
+ const version = getVersion();
817
+ const dappId = getDappId(options.dapp);
818
+ const platform = getPlatformType();
819
+ const anonId = yield storage.getAnonId();
820
+ const integrationType = (_b = (_a = options.analytics) == null ? void 0 : _a.integrationType) != null ? _b : "unknown" /* UNKNOWN */;
821
+ return {
822
+ mmconnect_version: version,
823
+ dapp_id: dappId,
824
+ platform,
825
+ integration_type: integrationType,
826
+ anon_id: anonId
827
+ };
828
+ });
829
+ }
830
+ function getWalletActionAnalyticsProperties(options, storage, invokeOptions) {
831
+ return __async(this, null, function* () {
832
+ var _a, _b;
833
+ const version = getVersion();
834
+ const dappId = getDappId(options.dapp);
835
+ const anonId = yield storage.getAnonId();
836
+ const integrationType = (_b = (_a = options.analytics) == null ? void 0 : _a.integrationType) != null ? _b : "unknown";
837
+ return {
838
+ mmconnect_version: version,
839
+ dapp_id: dappId,
840
+ method: invokeOptions.request.method,
841
+ integration_type: integrationType,
842
+ caip_chain_id: invokeOptions.scope,
843
+ anon_id: anonId
844
+ };
845
+ });
846
+ }
847
+ var init_analytics = __esm({
848
+ "src/multichain/utils/analytics.ts"() {
849
+ "use strict";
850
+ init_utils();
851
+ init_domain();
852
+ }
853
+ });
854
+
607
855
  // src/domain/utils/index.ts
608
856
  function getVersion() {
609
857
  return "0.0.0";
610
858
  }
611
- var init_utils = __esm({
859
+ var init_utils2 = __esm({
612
860
  "src/domain/utils/index.ts"() {
613
861
  "use strict";
862
+ init_analytics();
614
863
  }
615
864
  });
616
865
 
@@ -625,7 +874,7 @@ var init_domain = __esm({
625
874
  init_platform();
626
875
  init_store();
627
876
  init_ui();
628
- init_utils();
877
+ init_utils2();
629
878
  }
630
879
  });
631
880
 
@@ -672,7 +921,7 @@ function shouldLogCountdown(remainingSeconds) {
672
921
  return remainingSeconds % 60 === 0;
673
922
  }
674
923
  }
675
- var init_utils2 = __esm({
924
+ var init_utils3 = __esm({
676
925
  "src/ui/modals/base/utils.ts"() {
677
926
  "use strict";
678
927
  }
@@ -684,7 +933,7 @@ var init_AbstractInstallModal = __esm({
684
933
  "src/ui/modals/base/AbstractInstallModal.ts"() {
685
934
  "use strict";
686
935
  init_domain();
687
- init_utils2();
936
+ init_utils3();
688
937
  logger3 = createLogger("metamask-sdk:ui");
689
938
  AbstractInstallModal = class extends Modal {
690
939
  constructor() {
@@ -778,7 +1027,7 @@ var init_install = __esm({
778
1027
  init_domain();
779
1028
  init_qr();
780
1029
  init_AbstractInstallModal();
781
- init_utils2();
1030
+ init_utils3();
782
1031
  logger4 = createLogger("metamask-sdk:ui");
783
1032
  InstallModal = class extends AbstractInstallModal {
784
1033
  displayQRWithCountdown(qrCodeLink, expiresInMs) {
@@ -933,16 +1182,18 @@ __export(index_node_exports, {
933
1182
  getPlatformType: () => getPlatformType,
934
1183
  getTransportType: () => getTransportType,
935
1184
  getVersion: () => getVersion,
1185
+ getWalletActionAnalyticsProperties: () => getWalletActionAnalyticsProperties,
936
1186
  hasExtension: () => hasExtension,
937
1187
  infuraRpcUrls: () => infuraRpcUrls,
938
1188
  isEnabled: () => isEnabled,
939
1189
  isMetamaskExtensionInstalled: () => isMetamaskExtensionInstalled,
1190
+ isRejectionError: () => isRejectionError,
940
1191
  isSecure: () => isSecure
941
1192
  });
942
1193
  module.exports = __toCommonJS(index_node_exports);
943
1194
 
944
1195
  // src/multichain/index.ts
945
- var import_analytics = require("@metamask/analytics");
1196
+ var import_analytics4 = require("@metamask/analytics");
946
1197
  var import_mobile_wallet_protocol_core2 = require("@metamask/mobile-wallet-protocol-core");
947
1198
  var import_mobile_wallet_protocol_dapp_client = require("@metamask/mobile-wallet-protocol-dapp-client");
948
1199
  var import_multichain_api_client3 = require("@metamask/multichain-api-client");
@@ -954,6 +1205,7 @@ var METAMASK_DEEPLINK_BASE = "metamask://connect";
954
1205
 
955
1206
  // src/multichain/index.ts
956
1207
  init_domain();
1208
+ init_analytics();
957
1209
  init_logger();
958
1210
  init_multichain();
959
1211
  init_platform();
@@ -1054,201 +1306,17 @@ var RpcClient = class {
1054
1306
  };
1055
1307
 
1056
1308
  // src/multichain/rpc/requestRouter.ts
1309
+ var import_analytics2 = require("@metamask/analytics");
1057
1310
  init_domain();
1058
-
1059
- // src/multichain/utils/index.ts
1060
- var import_pako = require("pako");
1061
- var import_utils = require("@metamask/utils");
1062
- init_domain();
1063
- function base64Encode(str) {
1064
- if (typeof btoa !== "undefined") {
1065
- return btoa(str);
1066
- } else if (typeof Buffer !== "undefined") {
1067
- return Buffer.from(str).toString("base64");
1068
- }
1069
- throw new Error("No base64 encoding method available");
1070
- }
1071
- function compressString(str) {
1072
- const compressed = (0, import_pako.deflate)(str);
1073
- const binaryString = String.fromCharCode.apply(null, Array.from(compressed));
1074
- return base64Encode(binaryString);
1075
- }
1076
- function getDappId(dapp) {
1077
- var _a, _b;
1078
- if (typeof window === "undefined" || typeof window.location === "undefined") {
1079
- return (_b = (_a = dapp == null ? void 0 : dapp.name) != null ? _a : dapp == null ? void 0 : dapp.url) != null ? _b : "N/A";
1080
- }
1081
- return window.location.hostname;
1082
- }
1083
- function openDeeplink(options, deeplink, universalLink) {
1084
- const { mobile } = options;
1085
- const useDeeplink = mobile && mobile.useDeeplink !== void 0 ? mobile.useDeeplink : true;
1086
- if (useDeeplink) {
1087
- if (typeof window !== "undefined") {
1088
- window.location.href = deeplink;
1089
- }
1090
- } else if (typeof document !== "undefined") {
1091
- const link = document.createElement("a");
1092
- link.href = universalLink;
1093
- link.target = "_self";
1094
- link.rel = "noreferrer noopener";
1095
- link.click();
1096
- }
1097
- }
1098
- function getOptionalScopes(scopes) {
1099
- return scopes.reduce(
1100
- (prev, scope) => __spreadProps(__spreadValues({}, prev), {
1101
- [scope]: {
1102
- methods: [],
1103
- notifications: [],
1104
- accounts: []
1105
- }
1106
- }),
1107
- {}
1108
- );
1109
- }
1110
- var extractFavicon = () => {
1111
- var _a;
1112
- if (typeof document === "undefined") {
1113
- return void 0;
1114
- }
1115
- let favicon;
1116
- const nodeList = document.getElementsByTagName("link");
1117
- for (let i = 0; i < nodeList.length; i++) {
1118
- if (nodeList[i].getAttribute("rel") === "icon" || nodeList[i].getAttribute("rel") === "shortcut icon") {
1119
- favicon = (_a = nodeList[i].getAttribute("href")) != null ? _a : void 0;
1120
- }
1121
- }
1122
- return favicon;
1123
- };
1124
- function setupDappMetadata(options) {
1125
- var _a;
1126
- const platform = getPlatformType();
1127
- const isBrowser = platform === "web-desktop" /* DesktopWeb */ || platform === "web-mobile" /* MobileWeb */ || platform === "in-app-browser" /* MetaMaskMobileWebview */;
1128
- if (!((_a = options.dapp) == null ? void 0 : _a.url)) {
1129
- if (isBrowser) {
1130
- options.dapp = __spreadProps(__spreadValues({}, options.dapp), {
1131
- url: `${window.location.protocol}//${window.location.host}`
1132
- });
1133
- } else {
1134
- throw new Error("You must provide dapp url");
1135
- }
1136
- }
1137
- const BASE_64_ICON_MAX_LENGTH = 163400;
1138
- const urlPattern = /^(http|https):\/\/[^\s]*$/;
1139
- if (options.dapp) {
1140
- if ("iconUrl" in options.dapp) {
1141
- if (options.dapp.iconUrl && !urlPattern.test(options.dapp.iconUrl)) {
1142
- console.warn(
1143
- "Invalid dappMetadata.iconUrl: URL must start with http:// or https://"
1144
- );
1145
- options.dapp.iconUrl = void 0;
1146
- }
1147
- }
1148
- if ("base64Icon" in options.dapp) {
1149
- if (options.dapp.base64Icon && options.dapp.base64Icon.length > BASE_64_ICON_MAX_LENGTH) {
1150
- console.warn(
1151
- "Invalid dappMetadata.base64Icon: Base64-encoded icon string length must be less than 163400 characters"
1152
- );
1153
- options.dapp.base64Icon = void 0;
1154
- }
1155
- }
1156
- if (options.dapp.url && !urlPattern.test(options.dapp.url)) {
1157
- console.warn(
1158
- "Invalid dappMetadata.url: URL must start with http:// or https://"
1159
- );
1160
- }
1161
- const favicon = extractFavicon();
1162
- if (favicon && !("iconUrl" in options.dapp) && !("base64Icon" in options.dapp)) {
1163
- const faviconUrl = `${window.location.protocol}//${window.location.host}${favicon}`;
1164
- options.dapp.iconUrl = faviconUrl;
1165
- }
1166
- }
1167
- return options;
1168
- }
1169
- function isSameScopesAndAccounts(currentScopes, proposedScopes, walletSession, proposedCaipAccountIds) {
1170
- const isSameScopes = currentScopes.every((scope) => proposedScopes.includes(scope)) && proposedScopes.every((scope) => currentScopes.includes(scope));
1171
- if (!isSameScopes) {
1172
- return false;
1173
- }
1174
- const existingAccountIds = Object.values(
1175
- walletSession.sessionScopes
1176
- ).filter(({ accounts }) => Boolean(accounts)).flatMap(({ accounts }) => accounts != null ? accounts : []);
1177
- const allProposedAccountsIncluded = proposedCaipAccountIds.every(
1178
- (proposedAccountId) => existingAccountIds.includes(proposedAccountId)
1179
- );
1180
- return allProposedAccountsIncluded;
1181
- }
1182
- function getValidAccounts(caipAccountIds) {
1183
- return caipAccountIds.reduce(
1184
- (caipAccounts, caipAccountId) => {
1185
- try {
1186
- return [...caipAccounts, (0, import_utils.parseCaipAccountId)(caipAccountId)];
1187
- } catch (err) {
1188
- const stringifiedAccountId = JSON.stringify(caipAccountId);
1189
- console.error(`Invalid CAIP account ID: ${stringifiedAccountId}`, err);
1190
- return caipAccounts;
1191
- }
1192
- },
1193
- []
1194
- );
1195
- }
1196
- function addValidAccounts(optionalScopes, validAccounts) {
1197
- var _a;
1198
- if (!optionalScopes || !(validAccounts == null ? void 0 : validAccounts.length)) {
1199
- return optionalScopes;
1200
- }
1201
- const result = Object.fromEntries(
1202
- Object.entries(optionalScopes).map(([scope, scopeData]) => {
1203
- var _a2, _b, _c;
1204
- return [
1205
- scope,
1206
- {
1207
- methods: [...(_a2 = scopeData == null ? void 0 : scopeData.methods) != null ? _a2 : []],
1208
- notifications: [...(_b = scopeData == null ? void 0 : scopeData.notifications) != null ? _b : []],
1209
- accounts: [...(_c = scopeData == null ? void 0 : scopeData.accounts) != null ? _c : []]
1210
- }
1211
- ];
1212
- })
1213
- );
1214
- const accountsByChain = /* @__PURE__ */ new Map();
1215
- for (const account of validAccounts) {
1216
- const chainKey = `${account.chain.namespace}:${account.chain.reference}`;
1217
- const accountId = `${account.chainId}:${account.address}`;
1218
- if (!accountsByChain.has(chainKey)) {
1219
- accountsByChain.set(chainKey, []);
1220
- }
1221
- (_a = accountsByChain.get(chainKey)) == null ? void 0 : _a.push(accountId);
1222
- }
1223
- for (const [scopeKey, scopeData] of Object.entries(result)) {
1224
- if (!(scopeData == null ? void 0 : scopeData.accounts)) {
1225
- continue;
1226
- }
1227
- try {
1228
- const scope = scopeKey;
1229
- const scopeDetails = (0, import_utils.parseCaipChainId)(scope);
1230
- const chainKey = `${scopeDetails.namespace}:${scopeDetails.reference}`;
1231
- const matchingAccounts = accountsByChain.get(chainKey);
1232
- if (matchingAccounts) {
1233
- const existingAccounts = new Set(scopeData.accounts);
1234
- const newAccounts = matchingAccounts.filter(
1235
- (account) => !existingAccounts.has(account)
1236
- );
1237
- scopeData.accounts.push(...newAccounts);
1238
- }
1239
- } catch (error) {
1240
- console.error(`Invalid scope format: ${scopeKey}`, error);
1241
- }
1242
- }
1243
- return result;
1244
- }
1245
-
1246
- // src/multichain/rpc/requestRouter.ts
1311
+ init_utils();
1312
+ init_analytics();
1313
+ var _RequestRouter_instances, withAnalyticsTracking_fn, trackWalletActionRequested_fn, trackWalletActionSucceeded_fn, trackWalletActionFailed_fn, trackWalletActionRejected_fn;
1247
1314
  var RequestRouter = class {
1248
1315
  constructor(transport, rpcClient, config) {
1249
1316
  this.transport = transport;
1250
1317
  this.rpcClient = rpcClient;
1251
1318
  this.config = config;
1319
+ __privateAdd(this, _RequestRouter_instances);
1252
1320
  }
1253
1321
  /**
1254
1322
  * The main entry point for invoking an RPC method.
@@ -1272,7 +1340,7 @@ var RequestRouter = class {
1272
1340
  */
1273
1341
  handleWithWallet(options) {
1274
1342
  return __async(this, null, function* () {
1275
- try {
1343
+ return __privateMethod(this, _RequestRouter_instances, withAnalyticsTracking_fn).call(this, options, () => __async(this, null, function* () {
1276
1344
  const request = this.transport.request({
1277
1345
  method: "wallet_invokeMethod",
1278
1346
  params: options
@@ -1295,9 +1363,7 @@ var RequestRouter = class {
1295
1363
  throw new RPCInvokeMethodErr(`RPC Request failed with code ${response.error.code}: ${response.error.message}`);
1296
1364
  }
1297
1365
  return response.result;
1298
- } catch (error) {
1299
- throw new RPCInvokeMethodErr(error.message);
1300
- }
1366
+ }));
1301
1367
  });
1302
1368
  }
1303
1369
  /**
@@ -1305,14 +1371,16 @@ var RequestRouter = class {
1305
1371
  */
1306
1372
  handleWithRpcNode(options) {
1307
1373
  return __async(this, null, function* () {
1308
- try {
1309
- return yield this.rpcClient.request(options);
1310
- } catch (error) {
1311
- if (error instanceof MissingRpcEndpointErr) {
1312
- return this.handleWithWallet(options);
1374
+ return __privateMethod(this, _RequestRouter_instances, withAnalyticsTracking_fn).call(this, options, () => __async(this, null, function* () {
1375
+ try {
1376
+ return yield this.rpcClient.request(options);
1377
+ } catch (error) {
1378
+ if (error instanceof MissingRpcEndpointErr) {
1379
+ return this.handleWithWallet(options);
1380
+ }
1381
+ throw error;
1313
1382
  }
1314
- throw error;
1315
- }
1383
+ }));
1316
1384
  });
1317
1385
  }
1318
1386
  /**
@@ -1325,9 +1393,60 @@ var RequestRouter = class {
1325
1393
  });
1326
1394
  }
1327
1395
  };
1396
+ _RequestRouter_instances = new WeakSet();
1397
+ withAnalyticsTracking_fn = function(options, execute) {
1398
+ return __async(this, null, function* () {
1399
+ var _a, _b, _c;
1400
+ if ((_a = this.config.analytics) == null ? void 0 : _a.enabled) {
1401
+ yield __privateMethod(this, _RequestRouter_instances, trackWalletActionRequested_fn).call(this, options);
1402
+ }
1403
+ try {
1404
+ const result = yield execute();
1405
+ if ((_b = this.config.analytics) == null ? void 0 : _b.enabled) {
1406
+ yield __privateMethod(this, _RequestRouter_instances, trackWalletActionSucceeded_fn).call(this, options);
1407
+ }
1408
+ return result;
1409
+ } catch (error) {
1410
+ if ((_c = this.config.analytics) == null ? void 0 : _c.enabled) {
1411
+ const isRejection = isRejectionError(error);
1412
+ if (isRejection) {
1413
+ yield __privateMethod(this, _RequestRouter_instances, trackWalletActionRejected_fn).call(this, options);
1414
+ } else {
1415
+ yield __privateMethod(this, _RequestRouter_instances, trackWalletActionFailed_fn).call(this, options);
1416
+ }
1417
+ }
1418
+ throw new RPCInvokeMethodErr(error.message);
1419
+ }
1420
+ });
1421
+ };
1422
+ trackWalletActionRequested_fn = function(options) {
1423
+ return __async(this, null, function* () {
1424
+ const props = yield getWalletActionAnalyticsProperties(this.config, this.config.storage, options);
1425
+ import_analytics2.analytics.track("mmconnect_wallet_action_requested", props);
1426
+ });
1427
+ };
1428
+ trackWalletActionSucceeded_fn = function(options) {
1429
+ return __async(this, null, function* () {
1430
+ const props = yield getWalletActionAnalyticsProperties(this.config, this.config.storage, options);
1431
+ import_analytics2.analytics.track("mmconnect_wallet_action_succeeded", props);
1432
+ });
1433
+ };
1434
+ trackWalletActionFailed_fn = function(options) {
1435
+ return __async(this, null, function* () {
1436
+ const props = yield getWalletActionAnalyticsProperties(this.config, this.config.storage, options);
1437
+ import_analytics2.analytics.track("mmconnect_wallet_action_failed", props);
1438
+ });
1439
+ };
1440
+ trackWalletActionRejected_fn = function(options) {
1441
+ return __async(this, null, function* () {
1442
+ const props = yield getWalletActionAnalyticsProperties(this.config, this.config.storage, options);
1443
+ import_analytics2.analytics.track("mmconnect_wallet_action_rejected", props);
1444
+ });
1445
+ };
1328
1446
 
1329
1447
  // src/multichain/transports/default/index.ts
1330
1448
  var import_multichain_api_client = require("@metamask/multichain-api-client");
1449
+ init_utils();
1331
1450
  var DEFAULT_REQUEST_TIMEOUT = 60 * 1e3;
1332
1451
  var _notificationCallbacks, _transport, _defaultRequestOptions, _reqId, _pendingRequests, _handleResponseListener, _handleNotificationListener, _DefaultTransport_instances, notifyCallbacks_fn, isMetamaskProviderEvent_fn, handleResponse_fn, handleNotification_fn, setupMessageListener_fn;
1333
1452
  var DefaultTransport = class {
@@ -1556,6 +1675,7 @@ setupMessageListener_fn = function() {
1556
1675
  var import_mobile_wallet_protocol_core = require("@metamask/mobile-wallet-protocol-core");
1557
1676
  var import_multichain_api_client2 = require("@metamask/multichain-api-client");
1558
1677
  init_domain();
1678
+ init_utils();
1559
1679
 
1560
1680
  // src/multichain/transports/constants.ts
1561
1681
  var MULTICHAIN_PROVIDER_STREAM_NAME = "metamask-multichain-provider";
@@ -2029,20 +2149,22 @@ var KeyManager = class {
2029
2149
  var keymanager = new KeyManager();
2030
2150
 
2031
2151
  // src/multichain/index.ts
2152
+ init_utils();
2032
2153
  var logger2 = createLogger("metamask-sdk:core");
2033
2154
  var MultichainSDK = class _MultichainSDK extends MultichainCore {
2034
2155
  constructor(options) {
2035
- var _a, _b, _c, _d, _e, _f;
2156
+ var _a, _b, _c, _d, _e, _f, _g;
2036
2157
  const withDappMetadata = setupDappMetadata(options);
2158
+ const integrationType = ((_a = options.analytics) == null ? void 0 : _a.enabled) ? options.analytics.integrationType : "direct";
2037
2159
  const allOptions = __spreadProps(__spreadValues({}, withDappMetadata), {
2038
2160
  ui: __spreadProps(__spreadValues({}, withDappMetadata.ui), {
2039
- preferExtension: (_a = withDappMetadata.ui.preferExtension) != null ? _a : true,
2040
- showInstallModal: (_b = withDappMetadata.ui.showInstallModal) != null ? _b : false,
2041
- headless: (_c = withDappMetadata.ui.headless) != null ? _c : false
2161
+ preferExtension: (_b = withDappMetadata.ui.preferExtension) != null ? _b : true,
2162
+ showInstallModal: (_c = withDappMetadata.ui.showInstallModal) != null ? _c : false,
2163
+ headless: (_d = withDappMetadata.ui.headless) != null ? _d : false
2042
2164
  }),
2043
- analytics: __spreadProps(__spreadValues({}, (_d = options.analytics) != null ? _d : {}), {
2044
- enabled: (_f = (_e = options.analytics) == null ? void 0 : _e.enabled) != null ? _f : true,
2045
- integrationType: "unknown"
2165
+ analytics: __spreadProps(__spreadValues({}, (_e = options.analytics) != null ? _e : {}), {
2166
+ enabled: (_g = (_f = options.analytics) == null ? void 0 : _f.enabled) != null ? _g : true,
2167
+ integrationType
2046
2168
  })
2047
2169
  });
2048
2170
  super(allOptions);
@@ -2126,12 +2248,12 @@ var MultichainSDK = class _MultichainSDK extends MultichainCore {
2126
2248
  const { integrationType } = (_b = this.options.analytics) != null ? _b : {
2127
2249
  integrationType: ""
2128
2250
  };
2129
- import_analytics.analytics.setGlobalProperty("sdk_version", version);
2130
- import_analytics.analytics.setGlobalProperty("dapp_id", dappId);
2131
- import_analytics.analytics.setGlobalProperty("anon_id", anonId);
2132
- import_analytics.analytics.setGlobalProperty("platform", platform);
2133
- import_analytics.analytics.setGlobalProperty("integration_type", integrationType);
2134
- import_analytics.analytics.enable();
2251
+ import_analytics4.analytics.setGlobalProperty("mmconnect_version", version);
2252
+ import_analytics4.analytics.setGlobalProperty("dapp_id", dappId);
2253
+ import_analytics4.analytics.setGlobalProperty("anon_id", anonId);
2254
+ import_analytics4.analytics.setGlobalProperty("platform", platform);
2255
+ import_analytics4.analytics.setGlobalProperty("integration_type", integrationType);
2256
+ import_analytics4.analytics.enable();
2135
2257
  });
2136
2258
  }
2137
2259
  onTransportNotification(payload) {
@@ -2193,14 +2315,24 @@ var MultichainSDK = class _MultichainSDK extends MultichainCore {
2193
2315
  }
2194
2316
  init() {
2195
2317
  return __async(this, null, function* () {
2196
- var _a;
2318
+ var _a, _b;
2197
2319
  try {
2198
2320
  if (typeof window !== "undefined" && ((_a = window.mmsdk) == null ? void 0 : _a.isInitialized)) {
2199
2321
  logger2("MetaMaskSDK: init already initialized");
2200
2322
  } else {
2201
2323
  yield this.setupAnalytics();
2202
2324
  yield this.setupTransport();
2203
- import_analytics.analytics.track("sdk_initialized", {});
2325
+ if ((_b = this.options.analytics) == null ? void 0 : _b.enabled) {
2326
+ try {
2327
+ const baseProps = yield getBaseAnalyticsProperties(
2328
+ this.options,
2329
+ this.storage
2330
+ );
2331
+ import_analytics4.analytics.track("mmconnect_initialized", baseProps);
2332
+ } catch (error) {
2333
+ logger2("Error tracking initialized event", error);
2334
+ }
2335
+ }
2204
2336
  if (typeof window !== "undefined") {
2205
2337
  window.mmsdk = this;
2206
2338
  }
@@ -2402,27 +2534,87 @@ var MultichainSDK = class _MultichainSDK extends MultichainCore {
2402
2534
  }));
2403
2535
  });
2404
2536
  }
2405
- handleConnection(promise) {
2537
+ handleConnection(promise, scopes, transportType) {
2406
2538
  return __async(this, null, function* () {
2407
2539
  this.state = "connecting";
2408
- return promise.then(() => {
2540
+ return promise.then(() => __async(this, null, function* () {
2541
+ var _a;
2409
2542
  this.state = "connected";
2410
- }).catch((error) => {
2543
+ if ((_a = this.options.analytics) == null ? void 0 : _a.enabled) {
2544
+ try {
2545
+ const baseProps = yield getBaseAnalyticsProperties(
2546
+ this.options,
2547
+ this.storage
2548
+ );
2549
+ import_analytics4.analytics.track("mmconnect_connection_established", __spreadProps(__spreadValues({}, baseProps), {
2550
+ transport_type: transportType,
2551
+ user_permissioned_chains: scopes
2552
+ }));
2553
+ } catch (error) {
2554
+ logger2("Error tracking connection_established event", error);
2555
+ }
2556
+ }
2557
+ })).catch((error) => __async(this, null, function* () {
2558
+ var _a;
2411
2559
  this.state = "disconnected";
2560
+ if ((_a = this.options.analytics) == null ? void 0 : _a.enabled) {
2561
+ try {
2562
+ const baseProps = yield getBaseAnalyticsProperties(
2563
+ this.options,
2564
+ this.storage
2565
+ );
2566
+ const isRejection = isRejectionError(error);
2567
+ if (isRejection) {
2568
+ import_analytics4.analytics.track("mmconnect_connection_rejected", __spreadProps(__spreadValues({}, baseProps), {
2569
+ transport_type: transportType
2570
+ }));
2571
+ } else {
2572
+ import_analytics4.analytics.track("mmconnect_connection_failed", __spreadProps(__spreadValues({}, baseProps), {
2573
+ transport_type: transportType
2574
+ }));
2575
+ }
2576
+ } catch (e) {
2577
+ logger2("Error tracking connection failed/rejected event", error);
2578
+ }
2579
+ }
2412
2580
  return Promise.reject(error);
2413
- });
2581
+ }));
2414
2582
  });
2415
2583
  }
2416
2584
  connect(scopes, caipAccountIds, forceRequest) {
2417
2585
  return __async(this, null, function* () {
2418
- var _a;
2586
+ var _a, _b;
2419
2587
  const { ui } = this.options;
2420
2588
  const platformType = getPlatformType();
2421
2589
  const isWeb = platformType === "in-app-browser" /* MetaMaskMobileWebview */ || platformType === "web-desktop" /* DesktopWeb */;
2422
2590
  const { preferExtension = true, showInstallModal = false } = ui;
2423
2591
  const secure = isSecure();
2424
2592
  const hasExtensionInstalled = yield hasExtension();
2425
- if (((_a = this.__transport) == null ? void 0 : _a.isConnected()) && !secure) {
2593
+ let transportType;
2594
+ if (platformType === "in-app-browser" /* MetaMaskMobileWebview */ || isWeb && hasExtensionInstalled && preferExtension) {
2595
+ transportType = "browser" /* Browser */;
2596
+ } else {
2597
+ transportType = "mwp" /* MWP */;
2598
+ }
2599
+ if ((_a = this.options.analytics) == null ? void 0 : _a.enabled) {
2600
+ try {
2601
+ const baseProps = yield getBaseAnalyticsProperties(
2602
+ this.options,
2603
+ this.storage
2604
+ );
2605
+ const dappConfiguredChains = Object.keys(
2606
+ this.options.api.supportedNetworks
2607
+ );
2608
+ import_analytics4.analytics.track("mmconnect_connection_initiated", __spreadProps(__spreadValues({}, baseProps), {
2609
+ transport_type: transportType,
2610
+ dapp_configured_chains: dappConfiguredChains,
2611
+ dapp_requested_chains: scopes
2612
+ }));
2613
+ } catch (error) {
2614
+ logger2("Error tracking connection_initiated event", error);
2615
+ }
2616
+ }
2617
+ if (((_b = this.__transport) == null ? void 0 : _b.isConnected()) && !secure) {
2426
2618
  return this.handleConnection(
2427
2619
  this.__transport.connect({ scopes, caipAccountIds, forceRequest }).then(() => {
2428
2620
  if (this.__transport instanceof MWPTransport) {
@@ -2430,30 +2622,40 @@ var MultichainSDK = class _MultichainSDK extends MultichainCore {
2430
2622
  } else {
2431
2623
  return this.storage.setTransport("browser" /* Browser */);
2432
2624
  }
2433
- })
2625
+ }),
2626
+ scopes,
2627
+ transportType
2434
2628
  );
2435
2629
  }
2436
2630
  if (platformType === "in-app-browser" /* MetaMaskMobileWebview */) {
2437
2631
  const defaultTransport = yield this.setupDefaultTransport();
2438
2632
  return this.handleConnection(
2439
- defaultTransport.connect({ scopes, caipAccountIds, forceRequest })
2633
+ defaultTransport.connect({ scopes, caipAccountIds, forceRequest }),
2634
+ scopes,
2635
+ transportType
2440
2636
  );
2441
2637
  }
2442
2638
  if (isWeb && hasExtensionInstalled && preferExtension) {
2443
2639
  const defaultTransport = yield this.setupDefaultTransport();
2444
2640
  return this.handleConnection(
2445
- defaultTransport.connect({ scopes, caipAccountIds, forceRequest })
2641
+ defaultTransport.connect({ scopes, caipAccountIds, forceRequest }),
2642
+ scopes,
2643
+ transportType
2446
2644
  );
2447
2645
  }
2448
2646
  yield this.setupMWP();
2449
2647
  const shouldShowInstallModal = hasExtensionInstalled ? showInstallModal : !preferExtension || showInstallModal;
2450
2648
  if (secure && !shouldShowInstallModal) {
2451
2649
  return this.handleConnection(
2452
- this.deeplinkConnect(scopes, caipAccountIds)
2650
+ this.deeplinkConnect(scopes, caipAccountIds),
2651
+ scopes,
2652
+ transportType
2453
2653
  );
2454
2654
  }
2455
2655
  return this.handleConnection(
2456
- this.showInstallModal(shouldShowInstallModal, scopes, caipAccountIds)
2656
+ this.showInstallModal(shouldShowInstallModal, scopes, caipAccountIds),
2657
+ scopes,
2658
+ transportType
2457
2659
  );
2458
2660
  });
2459
2661
  }
@@ -2693,6 +2895,7 @@ var Store = class extends StoreClient {
2693
2895
  var import_onboarding = __toESM(require("@metamask/onboarding"));
2694
2896
  init_domain();
2695
2897
  init_qr();
2898
+ init_utils();
2696
2899
  var __instance;
2697
2900
  function preload() {
2698
2901
  return __async(this, null, function* () {
@@ -2902,10 +3105,12 @@ var createMetamaskConnect = (options) => __async(null, null, function* () {
2902
3105
  getPlatformType,
2903
3106
  getTransportType,
2904
3107
  getVersion,
3108
+ getWalletActionAnalyticsProperties,
2905
3109
  hasExtension,
2906
3110
  infuraRpcUrls,
2907
3111
  isEnabled,
2908
3112
  isMetamaskExtensionInstalled,
3113
+ isRejectionError,
2909
3114
  isSecure
2910
3115
  });
2911
3116
  //# sourceMappingURL=connect-multichain.js.map