@volr/react 0.1.132 → 0.1.134

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/dist/index.cjs CHANGED
@@ -9797,8 +9797,8 @@ var AUTHENTICATOR_SELECTION_CROSS_DEVICE = {
9797
9797
  residentKey: "required",
9798
9798
  authenticatorAttachment: "cross-platform"
9799
9799
  };
9800
- function getAuthenticatorSelection() {
9801
- if (shouldForceCrossDevice()) {
9800
+ function getAuthenticatorSelection(options) {
9801
+ if (shouldForceCrossDevice() && !options?.allowPlatform) {
9802
9802
  return AUTHENTICATOR_SELECTION_CROSS_DEVICE;
9803
9803
  }
9804
9804
  return AUTHENTICATOR_SELECTION;
@@ -9861,6 +9861,16 @@ var WebAuthnBusyError = class _WebAuthnBusyError extends Error {
9861
9861
  Object.setPrototypeOf(this, _WebAuthnBusyError.prototype);
9862
9862
  }
9863
9863
  };
9864
+ var InAppBrowserNotSupportedError = class _InAppBrowserNotSupportedError extends Error {
9865
+ constructor(message) {
9866
+ super(
9867
+ message || "Passkeys aren't supported in in-app browsers. Please open this page in your device browser (Chrome on Android, Safari on iOS)."
9868
+ );
9869
+ this.code = "INAPP_BROWSER_NOT_SUPPORTED";
9870
+ this.name = "InAppBrowserNotSupportedError";
9871
+ Object.setPrototypeOf(this, _InAppBrowserNotSupportedError.prototype);
9872
+ }
9873
+ };
9864
9874
  function isUserCancelledError(error) {
9865
9875
  if (error instanceof UserCancelledError) {
9866
9876
  return true;
@@ -9891,83 +9901,424 @@ function isWebAuthnBusyError(error) {
9891
9901
  }
9892
9902
  return false;
9893
9903
  }
9894
-
9895
- // src/adapters/passkey.ts
9896
- var pendingWebAuthnPromise = null;
9897
- async function withWebAuthnLock(fn) {
9898
- if (pendingWebAuthnPromise) {
9899
- try {
9900
- await pendingWebAuthnPromise;
9901
- } catch {
9902
- }
9904
+ function isInAppBrowserNotSupportedError(error) {
9905
+ if (error instanceof InAppBrowserNotSupportedError) {
9906
+ return true;
9903
9907
  }
9904
- const promise = fn();
9905
- pendingWebAuthnPromise = promise;
9906
- try {
9907
- const result = await promise;
9908
- return result;
9909
- } finally {
9910
- if (pendingWebAuthnPromise === promise) {
9911
- pendingWebAuthnPromise = null;
9908
+ if (error instanceof Error) {
9909
+ if (error.code === "INAPP_BROWSER_NOT_SUPPORTED") {
9910
+ return true;
9912
9911
  }
9913
9912
  }
9913
+ return false;
9914
9914
  }
9915
- function createPasskeyAdapter(options = {}) {
9916
- const rpId = options.rpId || (typeof window !== "undefined" ? window.location.hostname : "localhost");
9917
- return {
9918
- async getPublicKey() {
9919
- const credential = await navigator.credentials.get({
9920
- publicKey: {
9921
- challenge: new Uint8Array(32),
9922
- // Dummy challenge for getting public key
9923
- allowCredentials: [],
9924
- // Empty = any credential
9925
- userVerification: "required"
9926
- }
9927
- });
9928
- if (!credential || !("response" in credential)) {
9929
- throw new Error("Failed to get passkey credential");
9915
+
9916
+ // src/utils/platform-check.ts
9917
+ function detectPlatform() {
9918
+ if (typeof navigator === "undefined") return "Unknown";
9919
+ const ua = navigator.userAgent;
9920
+ const platform = navigator.platform || "";
9921
+ if (/iPhone|iPad|iPod/.test(ua) || platform === "MacIntel" && navigator.maxTouchPoints > 1) {
9922
+ return "iOS";
9923
+ }
9924
+ if (/Android/.test(ua)) {
9925
+ return "Android";
9926
+ }
9927
+ if (/Mac/.test(platform)) {
9928
+ return "macOS";
9929
+ }
9930
+ if (/Win/.test(platform)) {
9931
+ return "Windows";
9932
+ }
9933
+ if (/CrOS/.test(ua)) {
9934
+ return "ChromeOS";
9935
+ }
9936
+ if (/Linux/.test(platform)) {
9937
+ return "Linux";
9938
+ }
9939
+ return "Unknown";
9940
+ }
9941
+ function detectBrowser() {
9942
+ if (typeof navigator === "undefined") return "Unknown";
9943
+ const ua = navigator.userAgent;
9944
+ if (/KAKAOTALK/i.test(ua)) return "KakaoTalk-InApp";
9945
+ if (/NAVER\(/i.test(ua)) return "Naver-InApp";
9946
+ if (/Line\//i.test(ua)) return "Line-InApp";
9947
+ if (/MetaMaskMobile/i.test(ua)) return "MetaMask-InApp";
9948
+ if (/FB_IAB|FBAN/i.test(ua)) return "Facebook-InApp";
9949
+ if (/Instagram/i.test(ua)) return "Instagram-InApp";
9950
+ if (/Telegram/i.test(ua)) return "Telegram-InApp";
9951
+ if (/SamsungBrowser/i.test(ua)) return "Samsung";
9952
+ if (/Whale/i.test(ua)) return "Whale";
9953
+ if (/Edg/.test(ua)) return "Edge";
9954
+ if (/Chrome/.test(ua) && !/Chromium/.test(ua)) return "Chrome";
9955
+ if (/Safari/.test(ua) && !/Chrome/.test(ua)) return "Safari";
9956
+ if (/Firefox/.test(ua)) return "Firefox";
9957
+ if (/Opera|OPR/.test(ua)) return "Opera";
9958
+ return "Unknown";
9959
+ }
9960
+ function isInAppBrowser() {
9961
+ const browser = detectBrowser();
9962
+ return browser.includes("-InApp");
9963
+ }
9964
+ function getBrowserVersion() {
9965
+ if (typeof navigator === "undefined") return { browser: "Unknown", version: 0 };
9966
+ const ua = navigator.userAgent;
9967
+ const edgeMatch = ua.match(/Edg\/(\d+)/);
9968
+ if (edgeMatch) return { browser: "Edge", version: parseInt(edgeMatch[1]) };
9969
+ const samsungMatch = ua.match(/SamsungBrowser\/(\d+)/);
9970
+ if (samsungMatch) return { browser: "Samsung", version: parseInt(samsungMatch[1]) };
9971
+ const chromeMatch = ua.match(/Chrome\/(\d+)/);
9972
+ if (chromeMatch && !/Edg/.test(ua)) return { browser: "Chrome", version: parseInt(chromeMatch[1]) };
9973
+ const safariMatch = ua.match(/Version\/(\d+)\.(\d+)/);
9974
+ if (safariMatch && /Safari/.test(ua) && !/Chrome/.test(ua)) {
9975
+ return { browser: "Safari", version: parseFloat(`${safariMatch[1]}.${safariMatch[2]}`) };
9976
+ }
9977
+ const firefoxMatch = ua.match(/Firefox\/(\d+)/);
9978
+ if (firefoxMatch) return { browser: "Firefox", version: parseInt(firefoxMatch[1]) };
9979
+ return { browser: "Unknown", version: 0 };
9980
+ }
9981
+ function getIOSVersion() {
9982
+ if (typeof navigator === "undefined") return null;
9983
+ const ua = navigator.userAgent;
9984
+ const match = ua.match(/OS (\d+)_(\d+)/);
9985
+ if (match) {
9986
+ return parseFloat(`${match[1]}.${match[2]}`);
9987
+ }
9988
+ return null;
9989
+ }
9990
+ function checkPrfSupport() {
9991
+ const platform = detectPlatform();
9992
+ const browser = detectBrowser();
9993
+ if (typeof navigator === "undefined" || !navigator.credentials) {
9994
+ return {
9995
+ prfSupported: false,
9996
+ crossDeviceAvailable: false,
9997
+ message: "WebAuthn is not supported in this environment.",
9998
+ platform,
9999
+ browser
10000
+ };
10001
+ }
10002
+ let prfSupported = false;
10003
+ let message;
10004
+ switch (platform) {
10005
+ case "iOS":
10006
+ if (browser === "Safari") {
10007
+ prfSupported = true;
10008
+ } else {
10009
+ prfSupported = true;
9930
10010
  }
9931
- throw new Error(
9932
- "getPublicKey not implemented - use credential creation response"
9933
- );
9934
- },
9935
- async signP256(msgHash32) {
9936
- if (msgHash32.length !== 32) {
9937
- throw new Error("Message hash must be 32 bytes");
10011
+ break;
10012
+ case "Android":
10013
+ if (browser === "Chrome" || browser === "Edge") {
10014
+ prfSupported = true;
10015
+ } else if (browser === "Firefox") {
10016
+ prfSupported = false;
10017
+ message = "Firefox on Android does not support passkey encryption. Please use Chrome.";
10018
+ } else {
10019
+ prfSupported = true;
9938
10020
  }
9939
- const credential = await navigator.credentials.get({
9940
- publicKey: {
9941
- challenge: msgHash32,
9942
- allowCredentials: [],
9943
- // Empty = any credential
9944
- userVerification: "required"
9945
- }
9946
- });
9947
- if (!credential || !("response" in credential)) {
9948
- throw new Error("Failed to get passkey credential for signing");
10021
+ break;
10022
+ case "macOS":
10023
+ if (browser === "Safari" || browser === "Chrome" || browser === "Edge") {
10024
+ prfSupported = true;
10025
+ } else if (browser === "Firefox") {
10026
+ prfSupported = false;
10027
+ message = "Firefox may not support passkey encryption. Please use Safari or Chrome.";
10028
+ } else {
10029
+ prfSupported = true;
9949
10030
  }
9950
- const response = credential.response;
9951
- const signature = response.signature;
9952
- const derSignature = new Uint8Array(signature);
9953
- if (derSignature[0] !== 48) {
9954
- throw new Error("Invalid DER signature format");
10031
+ break;
10032
+ case "Windows":
10033
+ if (browser === "Chrome" || browser === "Edge") {
10034
+ prfSupported = true;
10035
+ message = "If your device does not support passkey encryption, you can use your mobile device by scanning a QR code.";
10036
+ } else {
10037
+ prfSupported = false;
10038
+ message = "Please use Chrome or Edge for passkey encryption support.";
9955
10039
  }
9956
- let offset = 2;
9957
- if (derSignature[offset] !== 2) {
9958
- throw new Error("Invalid DER signature: expected r marker");
10040
+ break;
10041
+ case "ChromeOS":
10042
+ prfSupported = true;
10043
+ break;
10044
+ case "Linux":
10045
+ if (browser === "Chrome" || browser === "Edge") {
10046
+ prfSupported = true;
10047
+ message = "If your device does not support passkey encryption, you can use your mobile device by scanning a QR code.";
10048
+ } else {
10049
+ prfSupported = false;
10050
+ message = "Please use Chrome for passkey encryption support.";
9959
10051
  }
9960
- offset++;
9961
- const rLength = derSignature[offset++];
9962
- const rBytes = derSignature.slice(offset, offset + rLength);
9963
- offset += rLength;
9964
- if (derSignature[offset] !== 2) {
9965
- throw new Error("Invalid DER signature: expected s marker");
10052
+ break;
10053
+ default:
10054
+ prfSupported = false;
10055
+ message = "Unknown platform. Passkey encryption may not be supported.";
10056
+ }
10057
+ const crossDeviceAvailable = true;
10058
+ return {
10059
+ prfSupported,
10060
+ crossDeviceAvailable,
10061
+ message,
10062
+ platform,
10063
+ browser
10064
+ };
10065
+ }
10066
+ function getPasskeyAuthGuidance(passkeyPlatform) {
10067
+ const { platform: currentPlatform, prfSupported } = checkPrfSupport();
10068
+ if (prfSupported && (!passkeyPlatform || passkeyPlatform === currentPlatform)) {
10069
+ return "";
10070
+ }
10071
+ if (passkeyPlatform && passkeyPlatform !== currentPlatform) {
10072
+ const platformDisplayName = getPlatformDisplayName(passkeyPlatform);
10073
+ return `Your passkey was registered on ${platformDisplayName}. You can use your ${platformDisplayName} device to authenticate by scanning a QR code.`;
10074
+ }
10075
+ if (!prfSupported) {
10076
+ return "This device may not support passkey encryption. You can use your mobile device by scanning a QR code.";
10077
+ }
10078
+ return "";
10079
+ }
10080
+ function getPlatformDisplayName(platform) {
10081
+ const displayNames = {
10082
+ iOS: "iPhone/iPad",
10083
+ Android: "Android",
10084
+ macOS: "Mac",
10085
+ Windows: "Windows PC",
10086
+ ChromeOS: "Chromebook",
10087
+ Linux: "Linux"
10088
+ };
10089
+ return displayNames[platform] || platform;
10090
+ }
10091
+ async function checkPrfExtensionAvailable() {
10092
+ if (typeof PublicKeyCredential === "undefined") {
10093
+ return false;
10094
+ }
10095
+ if ("getClientCapabilities" in PublicKeyCredential) {
10096
+ try {
10097
+ const capabilities = await PublicKeyCredential.getClientCapabilities();
10098
+ if (capabilities && typeof capabilities.extensions?.prf === "boolean") {
10099
+ return capabilities.extensions.prf;
9966
10100
  }
9967
- offset++;
9968
- const sLength = derSignature[offset++];
9969
- const sBytes = derSignature.slice(offset, offset + sLength);
9970
- const r = new Uint8Array(32);
10101
+ } catch {
10102
+ }
10103
+ }
10104
+ const { prfSupported } = checkPrfSupport();
10105
+ return prfSupported;
10106
+ }
10107
+ var MIN_BROWSER_VERSIONS = {
10108
+ Chrome: 109,
10109
+ Edge: 109,
10110
+ Safari: 17.4,
10111
+ Samsung: 21
10112
+ // Samsung Internet 21+ is based on Chromium 109+
10113
+ };
10114
+ var MIN_IOS_VERSION = 17.4;
10115
+ function checkPrfCompatibility() {
10116
+ const platform = detectPlatform();
10117
+ const browser = detectBrowser();
10118
+ const { browser: browserName, version: browserVersion } = getBrowserVersion();
10119
+ const baseResult = {
10120
+ platform,
10121
+ browser,
10122
+ browserVersion
10123
+ };
10124
+ if (isInAppBrowser()) {
10125
+ return {
10126
+ ...baseResult,
10127
+ supported: false,
10128
+ reason: "inapp-browser",
10129
+ messageKey: "passkey.compatibility.inAppBrowser",
10130
+ action: "use-external-browser"
10131
+ };
10132
+ }
10133
+ if (browserName === "Firefox") {
10134
+ return {
10135
+ ...baseResult,
10136
+ supported: false,
10137
+ reason: "unsupported-browser",
10138
+ messageKey: "passkey.compatibility.firefoxNotSupported",
10139
+ action: "use-chrome"
10140
+ };
10141
+ }
10142
+ if (browser === "Whale") {
10143
+ return {
10144
+ ...baseResult,
10145
+ supported: false,
10146
+ reason: "unsupported-browser",
10147
+ messageKey: "passkey.compatibility.whaleNotSupported",
10148
+ action: "use-chrome"
10149
+ };
10150
+ }
10151
+ if (browserName === "Chrome" && browserVersion < MIN_BROWSER_VERSIONS.Chrome) {
10152
+ return {
10153
+ ...baseResult,
10154
+ supported: false,
10155
+ reason: "outdated-browser",
10156
+ messageKey: "passkey.compatibility.outdatedChrome",
10157
+ action: "update-browser"
10158
+ };
10159
+ }
10160
+ if (browserName === "Edge" && browserVersion < MIN_BROWSER_VERSIONS.Edge) {
10161
+ return {
10162
+ ...baseResult,
10163
+ supported: false,
10164
+ reason: "outdated-browser",
10165
+ messageKey: "passkey.compatibility.outdatedEdge",
10166
+ action: "update-browser"
10167
+ };
10168
+ }
10169
+ if (browserName === "Safari" && browserVersion < MIN_BROWSER_VERSIONS.Safari) {
10170
+ return {
10171
+ ...baseResult,
10172
+ supported: false,
10173
+ reason: "outdated-browser",
10174
+ messageKey: "passkey.compatibility.outdatedSafari",
10175
+ action: "update-browser"
10176
+ };
10177
+ }
10178
+ if (browserName === "Samsung" && browserVersion < MIN_BROWSER_VERSIONS.Samsung) {
10179
+ return {
10180
+ ...baseResult,
10181
+ supported: false,
10182
+ reason: "outdated-browser",
10183
+ messageKey: "passkey.compatibility.outdatedSamsung",
10184
+ action: "update-browser"
10185
+ };
10186
+ }
10187
+ if (platform === "iOS") {
10188
+ const iosVersion = getIOSVersion();
10189
+ if (iosVersion && iosVersion < MIN_IOS_VERSION) {
10190
+ return {
10191
+ ...baseResult,
10192
+ supported: false,
10193
+ reason: "outdated-os",
10194
+ messageKey: "passkey.compatibility.outdatedIOS",
10195
+ action: "update-os"
10196
+ };
10197
+ }
10198
+ }
10199
+ if (browserName === "Unknown") {
10200
+ return {
10201
+ ...baseResult,
10202
+ supported: true,
10203
+ messageKey: "passkey.compatibility.unknownBrowser"
10204
+ };
10205
+ }
10206
+ return {
10207
+ ...baseResult,
10208
+ supported: true
10209
+ };
10210
+ }
10211
+ function getPlatformHint(platform) {
10212
+ switch (platform) {
10213
+ case "macOS":
10214
+ return {
10215
+ hintKey: "passkey.hint.macOS",
10216
+ noteKey: "passkey.hint.note"
10217
+ };
10218
+ case "iOS":
10219
+ return {
10220
+ hintKey: "passkey.hint.iOS",
10221
+ noteKey: "passkey.hint.note"
10222
+ };
10223
+ case "Android":
10224
+ return {
10225
+ hintKey: "passkey.hint.android",
10226
+ noteKey: "passkey.hint.note"
10227
+ };
10228
+ case "Windows":
10229
+ return {
10230
+ hintKey: "passkey.hint.windows",
10231
+ noteKey: "passkey.hint.windowsNote"
10232
+ };
10233
+ case "Linux":
10234
+ return {
10235
+ hintKey: "passkey.hint.linux",
10236
+ noteKey: "passkey.hint.windowsNote"
10237
+ };
10238
+ default:
10239
+ return {
10240
+ hintKey: "passkey.hint.default",
10241
+ noteKey: "passkey.hint.note"
10242
+ };
10243
+ }
10244
+ }
10245
+
10246
+ // src/adapters/passkey.ts
10247
+ var pendingWebAuthnPromise = null;
10248
+ async function withWebAuthnLock(fn) {
10249
+ if (pendingWebAuthnPromise) {
10250
+ try {
10251
+ await pendingWebAuthnPromise;
10252
+ } catch {
10253
+ }
10254
+ }
10255
+ const promise = fn();
10256
+ pendingWebAuthnPromise = promise;
10257
+ try {
10258
+ const result = await promise;
10259
+ return result;
10260
+ } finally {
10261
+ if (pendingWebAuthnPromise === promise) {
10262
+ pendingWebAuthnPromise = null;
10263
+ }
10264
+ }
10265
+ }
10266
+ function createPasskeyAdapter(options = {}) {
10267
+ const rpId = options.rpId || (typeof window !== "undefined" ? window.location.hostname : "localhost");
10268
+ return {
10269
+ async getPublicKey() {
10270
+ const credential = await navigator.credentials.get({
10271
+ publicKey: {
10272
+ challenge: new Uint8Array(32),
10273
+ // Dummy challenge for getting public key
10274
+ allowCredentials: [],
10275
+ // Empty = any credential
10276
+ userVerification: "required"
10277
+ }
10278
+ });
10279
+ if (!credential || !("response" in credential)) {
10280
+ throw new Error("Failed to get passkey credential");
10281
+ }
10282
+ throw new Error(
10283
+ "getPublicKey not implemented - use credential creation response"
10284
+ );
10285
+ },
10286
+ async signP256(msgHash32) {
10287
+ if (msgHash32.length !== 32) {
10288
+ throw new Error("Message hash must be 32 bytes");
10289
+ }
10290
+ const credential = await navigator.credentials.get({
10291
+ publicKey: {
10292
+ challenge: msgHash32,
10293
+ allowCredentials: [],
10294
+ // Empty = any credential
10295
+ userVerification: "required"
10296
+ }
10297
+ });
10298
+ if (!credential || !("response" in credential)) {
10299
+ throw new Error("Failed to get passkey credential for signing");
10300
+ }
10301
+ const response = credential.response;
10302
+ const signature = response.signature;
10303
+ const derSignature = new Uint8Array(signature);
10304
+ if (derSignature[0] !== 48) {
10305
+ throw new Error("Invalid DER signature format");
10306
+ }
10307
+ let offset = 2;
10308
+ if (derSignature[offset] !== 2) {
10309
+ throw new Error("Invalid DER signature: expected r marker");
10310
+ }
10311
+ offset++;
10312
+ const rLength = derSignature[offset++];
10313
+ const rBytes = derSignature.slice(offset, offset + rLength);
10314
+ offset += rLength;
10315
+ if (derSignature[offset] !== 2) {
10316
+ throw new Error("Invalid DER signature: expected s marker");
10317
+ }
10318
+ offset++;
10319
+ const sLength = derSignature[offset++];
10320
+ const sBytes = derSignature.slice(offset, offset + sLength);
10321
+ const r = new Uint8Array(32);
9971
10322
  const s = new Uint8Array(32);
9972
10323
  if (rBytes.length > 32 || sBytes.length > 32) {
9973
10324
  throw new Error("Signature r or s exceeds 32 bytes");
@@ -9977,6 +10328,11 @@ function createPasskeyAdapter(options = {}) {
9977
10328
  return { r, s };
9978
10329
  },
9979
10330
  async authenticate(prfInput) {
10331
+ if (isInAppBrowser()) {
10332
+ throw new InAppBrowserNotSupportedError(
10333
+ "Passkeys aren't supported in in-app browsers. Please open this page in your device browser (Chrome on Android, Safari on iOS)."
10334
+ );
10335
+ }
9980
10336
  const allowCredentials = [];
9981
10337
  if (prfInput.credentialId) {
9982
10338
  const hexString = prfInput.credentialId.startsWith("0x") ? prfInput.credentialId.slice(2) : prfInput.credentialId;
@@ -10051,6 +10407,11 @@ function createPasskeyAdapter(options = {}) {
10051
10407
  "Another passkey authentication is in progress. Please wait a moment and try again."
10052
10408
  );
10053
10409
  }
10410
+ if (isInAppBrowser()) {
10411
+ throw new InAppBrowserNotSupportedError(
10412
+ "Passkeys aren't supported in in-app browsers. Please open this page in your device browser (Chrome on Android, Safari on iOS)."
10413
+ );
10414
+ }
10054
10415
  if (error?.name === "NotAllowedError") {
10055
10416
  throw new UserCancelledError(
10056
10417
  "User cancelled the passkey prompt or authentication was denied."
@@ -19646,7 +20007,7 @@ function blobToBase64(blob) {
19646
20007
  reader.readAsDataURL(blob);
19647
20008
  });
19648
20009
  }
19649
- function detectPlatform() {
20010
+ function detectPlatform2() {
19650
20011
  if (typeof navigator === "undefined") return "Unknown";
19651
20012
  const ua = navigator.userAgent;
19652
20013
  const platform = navigator.platform || "";
@@ -19720,7 +20081,7 @@ async function enrollPasskey(params) {
19720
20081
  };
19721
20082
  const prfSalt = sdkCore.deriveWrapKey(tempPrfInput);
19722
20083
  const displayName = buildDisplayName(userEmail, userEvmAddress, userId);
19723
- const authenticatorSelection = getAuthenticatorSelection();
20084
+ const authenticatorSelection = getAuthenticatorSelection({ allowPlatform: true });
19724
20085
  const hints = getWebAuthnHints();
19725
20086
  const publicKeyCredentialCreationOptions = {
19726
20087
  challenge: challenge2,
@@ -19798,7 +20159,7 @@ async function enrollPasskey(params) {
19798
20159
  }
19799
20160
  const keypair = sdkCore.deriveEvmKey({ masterSeed: masterKeyHandle.seed });
19800
20161
  const address = keypair.address;
19801
- const platform = detectPlatform();
20162
+ const platform = detectPlatform2();
19802
20163
  const registerResponse = await client.post("/wallet/provider/register", {
19803
20164
  keyStorageType: "passkey",
19804
20165
  credentialId,
@@ -20624,336 +20985,6 @@ async function debugTransactionFailure(publicClient, failingWallet, workingWalle
20624
20985
  analysis
20625
20986
  };
20626
20987
  }
20627
-
20628
- // src/utils/platform-check.ts
20629
- function detectPlatform2() {
20630
- if (typeof navigator === "undefined") return "Unknown";
20631
- const ua = navigator.userAgent;
20632
- const platform = navigator.platform || "";
20633
- if (/iPhone|iPad|iPod/.test(ua) || platform === "MacIntel" && navigator.maxTouchPoints > 1) {
20634
- return "iOS";
20635
- }
20636
- if (/Android/.test(ua)) {
20637
- return "Android";
20638
- }
20639
- if (/Mac/.test(platform)) {
20640
- return "macOS";
20641
- }
20642
- if (/Win/.test(platform)) {
20643
- return "Windows";
20644
- }
20645
- if (/CrOS/.test(ua)) {
20646
- return "ChromeOS";
20647
- }
20648
- if (/Linux/.test(platform)) {
20649
- return "Linux";
20650
- }
20651
- return "Unknown";
20652
- }
20653
- function detectBrowser() {
20654
- if (typeof navigator === "undefined") return "Unknown";
20655
- const ua = navigator.userAgent;
20656
- if (/KAKAOTALK/i.test(ua)) return "KakaoTalk-InApp";
20657
- if (/NAVER\(/i.test(ua)) return "Naver-InApp";
20658
- if (/Line\//i.test(ua)) return "Line-InApp";
20659
- if (/MetaMaskMobile/i.test(ua)) return "MetaMask-InApp";
20660
- if (/FB_IAB|FBAN/i.test(ua)) return "Facebook-InApp";
20661
- if (/Instagram/i.test(ua)) return "Instagram-InApp";
20662
- if (/Telegram/i.test(ua)) return "Telegram-InApp";
20663
- if (/SamsungBrowser/i.test(ua)) return "Samsung";
20664
- if (/Whale/i.test(ua)) return "Whale";
20665
- if (/Edg/.test(ua)) return "Edge";
20666
- if (/Chrome/.test(ua) && !/Chromium/.test(ua)) return "Chrome";
20667
- if (/Safari/.test(ua) && !/Chrome/.test(ua)) return "Safari";
20668
- if (/Firefox/.test(ua)) return "Firefox";
20669
- if (/Opera|OPR/.test(ua)) return "Opera";
20670
- return "Unknown";
20671
- }
20672
- function isInAppBrowser() {
20673
- const browser = detectBrowser();
20674
- return browser.includes("-InApp");
20675
- }
20676
- function getBrowserVersion() {
20677
- if (typeof navigator === "undefined") return { browser: "Unknown", version: 0 };
20678
- const ua = navigator.userAgent;
20679
- const edgeMatch = ua.match(/Edg\/(\d+)/);
20680
- if (edgeMatch) return { browser: "Edge", version: parseInt(edgeMatch[1]) };
20681
- const samsungMatch = ua.match(/SamsungBrowser\/(\d+)/);
20682
- if (samsungMatch) return { browser: "Samsung", version: parseInt(samsungMatch[1]) };
20683
- const chromeMatch = ua.match(/Chrome\/(\d+)/);
20684
- if (chromeMatch && !/Edg/.test(ua)) return { browser: "Chrome", version: parseInt(chromeMatch[1]) };
20685
- const safariMatch = ua.match(/Version\/(\d+)\.(\d+)/);
20686
- if (safariMatch && /Safari/.test(ua) && !/Chrome/.test(ua)) {
20687
- return { browser: "Safari", version: parseFloat(`${safariMatch[1]}.${safariMatch[2]}`) };
20688
- }
20689
- const firefoxMatch = ua.match(/Firefox\/(\d+)/);
20690
- if (firefoxMatch) return { browser: "Firefox", version: parseInt(firefoxMatch[1]) };
20691
- return { browser: "Unknown", version: 0 };
20692
- }
20693
- function getIOSVersion() {
20694
- if (typeof navigator === "undefined") return null;
20695
- const ua = navigator.userAgent;
20696
- const match = ua.match(/OS (\d+)_(\d+)/);
20697
- if (match) {
20698
- return parseFloat(`${match[1]}.${match[2]}`);
20699
- }
20700
- return null;
20701
- }
20702
- function checkPrfSupport() {
20703
- const platform = detectPlatform2();
20704
- const browser = detectBrowser();
20705
- if (typeof navigator === "undefined" || !navigator.credentials) {
20706
- return {
20707
- prfSupported: false,
20708
- crossDeviceAvailable: false,
20709
- message: "WebAuthn is not supported in this environment.",
20710
- platform,
20711
- browser
20712
- };
20713
- }
20714
- let prfSupported = false;
20715
- let message;
20716
- switch (platform) {
20717
- case "iOS":
20718
- if (browser === "Safari") {
20719
- prfSupported = true;
20720
- } else {
20721
- prfSupported = true;
20722
- }
20723
- break;
20724
- case "Android":
20725
- if (browser === "Chrome" || browser === "Edge") {
20726
- prfSupported = true;
20727
- } else if (browser === "Firefox") {
20728
- prfSupported = false;
20729
- message = "Firefox on Android does not support passkey encryption. Please use Chrome.";
20730
- } else {
20731
- prfSupported = true;
20732
- }
20733
- break;
20734
- case "macOS":
20735
- if (browser === "Safari" || browser === "Chrome" || browser === "Edge") {
20736
- prfSupported = true;
20737
- } else if (browser === "Firefox") {
20738
- prfSupported = false;
20739
- message = "Firefox may not support passkey encryption. Please use Safari or Chrome.";
20740
- } else {
20741
- prfSupported = true;
20742
- }
20743
- break;
20744
- case "Windows":
20745
- if (browser === "Chrome" || browser === "Edge") {
20746
- prfSupported = true;
20747
- message = "If your device does not support passkey encryption, you can use your mobile device by scanning a QR code.";
20748
- } else {
20749
- prfSupported = false;
20750
- message = "Please use Chrome or Edge for passkey encryption support.";
20751
- }
20752
- break;
20753
- case "ChromeOS":
20754
- prfSupported = true;
20755
- break;
20756
- case "Linux":
20757
- if (browser === "Chrome" || browser === "Edge") {
20758
- prfSupported = true;
20759
- message = "If your device does not support passkey encryption, you can use your mobile device by scanning a QR code.";
20760
- } else {
20761
- prfSupported = false;
20762
- message = "Please use Chrome for passkey encryption support.";
20763
- }
20764
- break;
20765
- default:
20766
- prfSupported = false;
20767
- message = "Unknown platform. Passkey encryption may not be supported.";
20768
- }
20769
- const crossDeviceAvailable = true;
20770
- return {
20771
- prfSupported,
20772
- crossDeviceAvailable,
20773
- message,
20774
- platform,
20775
- browser
20776
- };
20777
- }
20778
- function getPasskeyAuthGuidance(passkeyPlatform) {
20779
- const { platform: currentPlatform, prfSupported } = checkPrfSupport();
20780
- if (prfSupported && (!passkeyPlatform || passkeyPlatform === currentPlatform)) {
20781
- return "";
20782
- }
20783
- if (passkeyPlatform && passkeyPlatform !== currentPlatform) {
20784
- const platformDisplayName = getPlatformDisplayName(passkeyPlatform);
20785
- return `Your passkey was registered on ${platformDisplayName}. You can use your ${platformDisplayName} device to authenticate by scanning a QR code.`;
20786
- }
20787
- if (!prfSupported) {
20788
- return "This device may not support passkey encryption. You can use your mobile device by scanning a QR code.";
20789
- }
20790
- return "";
20791
- }
20792
- function getPlatformDisplayName(platform) {
20793
- const displayNames = {
20794
- iOS: "iPhone/iPad",
20795
- Android: "Android",
20796
- macOS: "Mac",
20797
- Windows: "Windows PC",
20798
- ChromeOS: "Chromebook",
20799
- Linux: "Linux"
20800
- };
20801
- return displayNames[platform] || platform;
20802
- }
20803
- async function checkPrfExtensionAvailable() {
20804
- if (typeof PublicKeyCredential === "undefined") {
20805
- return false;
20806
- }
20807
- if ("getClientCapabilities" in PublicKeyCredential) {
20808
- try {
20809
- const capabilities = await PublicKeyCredential.getClientCapabilities();
20810
- if (capabilities && typeof capabilities.extensions?.prf === "boolean") {
20811
- return capabilities.extensions.prf;
20812
- }
20813
- } catch {
20814
- }
20815
- }
20816
- const { prfSupported } = checkPrfSupport();
20817
- return prfSupported;
20818
- }
20819
- var MIN_BROWSER_VERSIONS = {
20820
- Chrome: 109,
20821
- Edge: 109,
20822
- Safari: 17.4,
20823
- Samsung: 21
20824
- // Samsung Internet 21+ is based on Chromium 109+
20825
- };
20826
- var MIN_IOS_VERSION = 17.4;
20827
- function checkPrfCompatibility() {
20828
- const platform = detectPlatform2();
20829
- const browser = detectBrowser();
20830
- const { browser: browserName, version: browserVersion } = getBrowserVersion();
20831
- const baseResult = {
20832
- platform,
20833
- browser,
20834
- browserVersion
20835
- };
20836
- if (isInAppBrowser()) {
20837
- return {
20838
- ...baseResult,
20839
- supported: false,
20840
- reason: "inapp-browser",
20841
- messageKey: "passkey.compatibility.inAppBrowser",
20842
- action: "use-external-browser"
20843
- };
20844
- }
20845
- if (browserName === "Firefox") {
20846
- return {
20847
- ...baseResult,
20848
- supported: false,
20849
- reason: "unsupported-browser",
20850
- messageKey: "passkey.compatibility.firefoxNotSupported",
20851
- action: "use-chrome"
20852
- };
20853
- }
20854
- if (browser === "Whale") {
20855
- return {
20856
- ...baseResult,
20857
- supported: false,
20858
- reason: "unsupported-browser",
20859
- messageKey: "passkey.compatibility.whaleNotSupported",
20860
- action: "use-chrome"
20861
- };
20862
- }
20863
- if (browserName === "Chrome" && browserVersion < MIN_BROWSER_VERSIONS.Chrome) {
20864
- return {
20865
- ...baseResult,
20866
- supported: false,
20867
- reason: "outdated-browser",
20868
- messageKey: "passkey.compatibility.outdatedChrome",
20869
- action: "update-browser"
20870
- };
20871
- }
20872
- if (browserName === "Edge" && browserVersion < MIN_BROWSER_VERSIONS.Edge) {
20873
- return {
20874
- ...baseResult,
20875
- supported: false,
20876
- reason: "outdated-browser",
20877
- messageKey: "passkey.compatibility.outdatedEdge",
20878
- action: "update-browser"
20879
- };
20880
- }
20881
- if (browserName === "Safari" && browserVersion < MIN_BROWSER_VERSIONS.Safari) {
20882
- return {
20883
- ...baseResult,
20884
- supported: false,
20885
- reason: "outdated-browser",
20886
- messageKey: "passkey.compatibility.outdatedSafari",
20887
- action: "update-browser"
20888
- };
20889
- }
20890
- if (browserName === "Samsung" && browserVersion < MIN_BROWSER_VERSIONS.Samsung) {
20891
- return {
20892
- ...baseResult,
20893
- supported: false,
20894
- reason: "outdated-browser",
20895
- messageKey: "passkey.compatibility.outdatedSamsung",
20896
- action: "update-browser"
20897
- };
20898
- }
20899
- if (platform === "iOS") {
20900
- const iosVersion = getIOSVersion();
20901
- if (iosVersion && iosVersion < MIN_IOS_VERSION) {
20902
- return {
20903
- ...baseResult,
20904
- supported: false,
20905
- reason: "outdated-os",
20906
- messageKey: "passkey.compatibility.outdatedIOS",
20907
- action: "update-os"
20908
- };
20909
- }
20910
- }
20911
- if (browserName === "Unknown") {
20912
- return {
20913
- ...baseResult,
20914
- supported: true,
20915
- messageKey: "passkey.compatibility.unknownBrowser"
20916
- };
20917
- }
20918
- return {
20919
- ...baseResult,
20920
- supported: true
20921
- };
20922
- }
20923
- function getPlatformHint(platform) {
20924
- switch (platform) {
20925
- case "macOS":
20926
- return {
20927
- hintKey: "passkey.hint.macOS",
20928
- noteKey: "passkey.hint.note"
20929
- };
20930
- case "iOS":
20931
- return {
20932
- hintKey: "passkey.hint.iOS",
20933
- noteKey: "passkey.hint.note"
20934
- };
20935
- case "Android":
20936
- return {
20937
- hintKey: "passkey.hint.android",
20938
- noteKey: "passkey.hint.note"
20939
- };
20940
- case "Windows":
20941
- return {
20942
- hintKey: "passkey.hint.windows",
20943
- noteKey: "passkey.hint.windowsNote"
20944
- };
20945
- case "Linux":
20946
- return {
20947
- hintKey: "passkey.hint.linux",
20948
- noteKey: "passkey.hint.windowsNote"
20949
- };
20950
- default:
20951
- return {
20952
- hintKey: "passkey.hint.default",
20953
- noteKey: "passkey.hint.note"
20954
- };
20955
- }
20956
- }
20957
20988
  function blobToBase642(blob) {
20958
20989
  return new Promise((resolve, reject) => {
20959
20990
  const reader = new FileReader();
@@ -21139,7 +21170,7 @@ async function completeMigration(params) {
21139
21170
  credentialId: tempCredentialId
21140
21171
  };
21141
21172
  const prfSalt = sdkCore.deriveWrapKey(tempPrfInput);
21142
- const authenticatorSelection = getAuthenticatorSelection();
21173
+ const authenticatorSelection = getAuthenticatorSelection({ allowPlatform: true });
21143
21174
  const hints = getWebAuthnHints();
21144
21175
  const publicKeyCredentialCreationOptions = {
21145
21176
  challenge: challenge2,
@@ -21363,6 +21394,7 @@ Object.defineProperty(exports, "uploadBlob", {
21363
21394
  });
21364
21395
  exports.DEFAULT_EXPIRES_IN_SEC = DEFAULT_EXPIRES_IN_SEC;
21365
21396
  exports.DEFAULT_MODE = DEFAULT_MODE;
21397
+ exports.InAppBrowserNotSupportedError = InAppBrowserNotSupportedError;
21366
21398
  exports.PasskeyNotFoundError = PasskeyNotFoundError;
21367
21399
  exports.PrfNotSupportedError = PrfNotSupportedError;
21368
21400
  exports.UserCancelledError = UserCancelledError;
@@ -21393,6 +21425,7 @@ exports.getUserCredentials = getUserCredentials;
21393
21425
  exports.getWalletState = getWalletState;
21394
21426
  exports.isEIP7702Delegated = isEIP7702Delegated;
21395
21427
  exports.isInAppBrowser = isInAppBrowser;
21428
+ exports.isInAppBrowserNotSupportedError = isInAppBrowserNotSupportedError;
21396
21429
  exports.isUserCancelledError = isUserCancelledError;
21397
21430
  exports.isWebAuthnBusyError = isWebAuthnBusyError;
21398
21431
  exports.listenForSeedRequests = listenForSeedRequests;