@swype-org/react-sdk 0.1.155 → 0.1.157

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
@@ -3432,6 +3432,7 @@ function WalletPickerScreen({
3432
3432
  providers,
3433
3433
  pendingConnections,
3434
3434
  loading,
3435
+ onPrepareProvider,
3435
3436
  onSelectProvider,
3436
3437
  onContinueConnection,
3437
3438
  onBack
@@ -3440,6 +3441,27 @@ function WalletPickerScreen({
3440
3441
  const [hoveredId, setHoveredId] = react.useState(null);
3441
3442
  const [selectedProviderId, setSelectedProviderId] = react.useState(null);
3442
3443
  const [cryptoExpanded, setCryptoExpanded] = react.useState(false);
3444
+ const [connecting, setConnecting] = react.useState(false);
3445
+ const [preparedSession, setPreparedSession] = react.useState(null);
3446
+ const [preparing, setPreparing] = react.useState(false);
3447
+ const prepareIdRef = react.useRef(0);
3448
+ const handleCardClick = react.useCallback(async (providerId) => {
3449
+ setSelectedProviderId(providerId);
3450
+ setPreparedSession(null);
3451
+ setPreparing(true);
3452
+ const id = ++prepareIdRef.current;
3453
+ try {
3454
+ const session = await onPrepareProvider(providerId);
3455
+ if (prepareIdRef.current !== id) return;
3456
+ if (session) {
3457
+ setPreparedSession({ ...session, providerId });
3458
+ }
3459
+ } finally {
3460
+ if (prepareIdRef.current === id) {
3461
+ setPreparing(false);
3462
+ }
3463
+ }
3464
+ }, [onPrepareProvider]);
3443
3465
  const hasPending = pendingConnections != null && pendingConnections.length > 0;
3444
3466
  const displayProviders = providers.length > 0 ? providers : [
3445
3467
  { id: "metamask", name: "MetaMask" },
@@ -3458,11 +3480,23 @@ function WalletPickerScreen({
3458
3480
  ScreenLayout,
3459
3481
  {
3460
3482
  footer: /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
3461
- selectedProvider && /* @__PURE__ */ jsxRuntime.jsxs(PrimaryButton, { onClick: () => onSelectProvider(selectedProvider.id), children: [
3462
- "Open ",
3463
- selectedProvider.name,
3464
- " to Link"
3465
- ] }),
3483
+ selectedProvider && /* @__PURE__ */ jsxRuntime.jsx(
3484
+ PrimaryButton,
3485
+ {
3486
+ onClick: async () => {
3487
+ setConnecting(true);
3488
+ try {
3489
+ const session = preparedSession?.providerId === selectedProvider.id ? preparedSession : void 0;
3490
+ await onSelectProvider(selectedProvider.id, session);
3491
+ } finally {
3492
+ setConnecting(false);
3493
+ }
3494
+ },
3495
+ loading: connecting || preparing,
3496
+ disabled: preparing,
3497
+ children: preparing ? "Preparing..." : `Open ${selectedProvider.name} to Link`
3498
+ }
3499
+ ),
3466
3500
  /* @__PURE__ */ jsxRuntime.jsx(PoweredByFooter, {})
3467
3501
  ] }),
3468
3502
  children: [
@@ -3539,7 +3573,7 @@ function WalletPickerScreen({
3539
3573
  return /* @__PURE__ */ jsxRuntime.jsxs(
3540
3574
  "button",
3541
3575
  {
3542
- onClick: () => setSelectedProviderId(p.id),
3576
+ onClick: () => handleCardClick(p.id),
3543
3577
  onMouseEnter: () => setHoveredId(p.id),
3544
3578
  onMouseLeave: () => setHoveredId(null),
3545
3579
  style: cardStyle(tokens, isHovered, isSelected),
@@ -5560,6 +5594,7 @@ function StepRenderer({
5560
5594
  providers: state.providers,
5561
5595
  pendingConnections,
5562
5596
  loading: state.creatingTransfer,
5597
+ onPrepareProvider: handlers.onPrepareProvider,
5563
5598
  onSelectProvider: handlers.onSelectProvider,
5564
5599
  onContinueConnection: handlers.onContinueConnection,
5565
5600
  onBack: () => handlers.onNavigate(state.activeCredentialId ? "deposit" : "create-passkey")
@@ -6506,25 +6541,14 @@ function useProviderHandlers(deps) {
6506
6541
  reauthSessionIdRef,
6507
6542
  reauthTokenRef
6508
6543
  } = deps;
6509
- const handleSelectProvider = react.useCallback(async (providerId) => {
6510
- dispatch({ type: "SELECT_PROVIDER", providerId });
6544
+ const handlePrepareProvider = react.useCallback(async (providerId) => {
6511
6545
  if (!activeCredentialId) {
6512
6546
  dispatch({ type: "SET_ERROR", error: "Create or verify a passkey on this device before continuing." });
6513
6547
  dispatch({ type: "NAVIGATE", step: "create-passkey" });
6514
- return;
6548
+ return null;
6515
6549
  }
6516
6550
  const provider = providers.find((p) => p.id === providerId);
6517
6551
  const providerName = provider?.name ?? "Wallet";
6518
- const isMobile = !shouldUseWalletConnector({
6519
- useWalletConnector: useWalletConnectorProp,
6520
- userAgent: typeof navigator === "undefined" ? void 0 : navigator.userAgent
6521
- });
6522
- if (isMobile) {
6523
- dispatch({ type: "PAY_STARTED", isSetupRedirect: true });
6524
- } else {
6525
- dispatch({ type: "PAY_STARTED", isSetupRedirect: false });
6526
- dispatch({ type: "NAVIGATE", step: "setup-status" });
6527
- }
6528
6552
  try {
6529
6553
  const token = await getAccessToken();
6530
6554
  if (!token) throw new Error("Not authenticated");
@@ -6537,21 +6561,71 @@ function useProviderHandlers(deps) {
6537
6561
  });
6538
6562
  const session = account.authorizationSessions?.[0];
6539
6563
  if (!session) throw new Error("No authorization session returned.");
6564
+ return { accountId: account.id, sessionId: session.id, uri: session.uri };
6565
+ } catch (err) {
6566
+ captureException(err);
6567
+ const msg = err instanceof Error ? err.message : "Failed to set up wallet";
6568
+ dispatch({ type: "PAY_ERROR", error: msg, fallbackStep: "wallet-picker" });
6569
+ onError?.(msg);
6570
+ return null;
6571
+ }
6572
+ }, [activeCredentialId, providers, apiBaseUrl, getAccessToken, onError, dispatch]);
6573
+ const handleSelectProvider = react.useCallback(async (providerId, preparedSession) => {
6574
+ dispatch({ type: "SELECT_PROVIDER", providerId });
6575
+ if (!activeCredentialId) {
6576
+ dispatch({ type: "SET_ERROR", error: "Create or verify a passkey on this device before continuing." });
6577
+ dispatch({ type: "NAVIGATE", step: "create-passkey" });
6578
+ return;
6579
+ }
6580
+ const provider = providers.find((p) => p.id === providerId);
6581
+ const providerName = provider?.name ?? "Wallet";
6582
+ const isMobile = !shouldUseWalletConnector({
6583
+ useWalletConnector: useWalletConnectorProp,
6584
+ userAgent: typeof navigator === "undefined" ? void 0 : navigator.userAgent
6585
+ });
6586
+ if (!isMobile) {
6587
+ dispatch({ type: "PAY_STARTED", isSetupRedirect: false });
6588
+ dispatch({ type: "NAVIGATE", step: "setup-status" });
6589
+ }
6590
+ try {
6591
+ let accountId;
6592
+ let sessionId;
6593
+ let sessionUri;
6594
+ if (preparedSession) {
6595
+ accountId = preparedSession.accountId;
6596
+ sessionId = preparedSession.sessionId;
6597
+ sessionUri = preparedSession.uri;
6598
+ } else {
6599
+ const token = await getAccessToken();
6600
+ if (!token) throw new Error("Not authenticated");
6601
+ const newAccountId = crypto.randomUUID();
6602
+ const account = await createAccount(apiBaseUrl, token, {
6603
+ id: newAccountId,
6604
+ name: providerName,
6605
+ credentialId: activeCredentialId,
6606
+ providerId
6607
+ });
6608
+ const session = account.authorizationSessions?.[0];
6609
+ if (!session) throw new Error("No authorization session returned.");
6610
+ accountId = account.id;
6611
+ sessionId = session.id;
6612
+ sessionUri = session.uri;
6613
+ }
6540
6614
  if (isMobile) {
6541
6615
  handlingMobileReturnRef.current = false;
6542
6616
  mobileSetupFlowRef.current = true;
6543
- setupAccountIdRef.current = account.id;
6617
+ setupAccountIdRef.current = accountId;
6544
6618
  persistMobileFlowState({
6545
- accountId: account.id,
6546
- sessionId: session.id,
6547
- deeplinkUri: session.uri,
6619
+ accountId,
6620
+ sessionId,
6621
+ deeplinkUri: sessionUri,
6548
6622
  providerId,
6549
6623
  isSetup: true
6550
6624
  });
6551
- dispatch({ type: "MOBILE_DEEPLINK_READY", deeplinkUri: session.uri });
6552
- triggerDeeplink(session.uri);
6625
+ triggerDeeplink(sessionUri);
6626
+ dispatch({ type: "MOBILE_DEEPLINK_READY", deeplinkUri: sessionUri });
6553
6627
  } else {
6554
- await authExecutor.executeSessionById(session.id);
6628
+ await authExecutor.executeSessionById(sessionId);
6555
6629
  await reloadAccounts();
6556
6630
  dispatch({ type: "NAVIGATE", step: "deposit" });
6557
6631
  }
@@ -6561,7 +6635,9 @@ function useProviderHandlers(deps) {
6561
6635
  dispatch({ type: "PAY_ERROR", error: msg, fallbackStep: "wallet-picker" });
6562
6636
  onError?.(msg);
6563
6637
  } finally {
6564
- dispatch({ type: "PAY_ENDED" });
6638
+ if (!isMobile) {
6639
+ dispatch({ type: "PAY_ENDED" });
6640
+ }
6565
6641
  }
6566
6642
  }, [
6567
6643
  activeCredentialId,
@@ -6779,6 +6855,7 @@ function useProviderHandlers(deps) {
6779
6855
  reauthTokenRef
6780
6856
  ]);
6781
6857
  return {
6858
+ handlePrepareProvider,
6782
6859
  handleSelectProvider,
6783
6860
  handleContinueConnection,
6784
6861
  handleSelectAccount,
@@ -7637,6 +7714,7 @@ function SwypePaymentInner({
7637
7714
  onRegisterPasskey: passkey.handleRegisterPasskey,
7638
7715
  onCreatePasskeyViaPopup: passkey.handleCreatePasskeyViaPopup,
7639
7716
  onVerifyPasskeyViaPopup: passkey.handleVerifyPasskeyViaPopup,
7717
+ onPrepareProvider: provider.handlePrepareProvider,
7640
7718
  onSelectProvider: provider.handleSelectProvider,
7641
7719
  onContinueConnection: provider.handleContinueConnection,
7642
7720
  onSelectAccount: provider.handleSelectAccount,