@pooflabs/web 0.0.80 → 0.0.81-rc2

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 (82) hide show
  1. package/dist/auth/providers/phantom-wallet-provider.d.ts +20 -0
  2. package/dist/index-Bdcc5821.js +2375 -0
  3. package/dist/index-Bdcc5821.js.map +1 -0
  4. package/dist/{index-BhfNMrC0.js → index-BjlCinic.js} +25 -883
  5. package/dist/index-BjlCinic.js.map +1 -0
  6. package/dist/{index-Db0NqU8R.esm.js → index-Bx_lLXRT.esm.js} +342 -277
  7. package/dist/index-Bx_lLXRT.esm.js.map +1 -0
  8. package/dist/{index-COIUWugk.esm.js → index-CHqM9n4K.esm.js} +24 -881
  9. package/dist/index-CHqM9n4K.esm.js.map +1 -0
  10. package/dist/{index-BVi7fTm2.js → index-CL4JIAAR.js} +24 -882
  11. package/dist/index-CL4JIAAR.js.map +1 -0
  12. package/dist/index-CrOVJFX9.esm.js +2373 -0
  13. package/dist/index-CrOVJFX9.esm.js.map +1 -0
  14. package/dist/{index-BbtYb8sE.esm.js → index-DCo85UGg.esm.js} +23 -882
  15. package/dist/index-DCo85UGg.esm.js.map +1 -0
  16. package/dist/{index-BNyxZ82q.js → index-DHm4usay.js} +342 -276
  17. package/dist/index-DHm4usay.js.map +1 -0
  18. package/dist/{index.browser-BuHl80dp.esm.js → index.browser-7dDfRU5G.esm.js} +1367 -1697
  19. package/dist/index.browser-7dDfRU5G.esm.js.map +1 -0
  20. package/dist/index.browser-Bg_-PAgT.esm.js +1250 -0
  21. package/dist/index.browser-Bg_-PAgT.esm.js.map +1 -0
  22. package/dist/index.browser-C-_FEr5M.esm.js +1134 -0
  23. package/dist/index.browser-C-_FEr5M.esm.js.map +1 -0
  24. package/dist/{index.browser-8hyi2LOX.js → index.browser-CmlqbyPr.js} +1367 -1697
  25. package/dist/index.browser-CmlqbyPr.js.map +1 -0
  26. package/dist/index.browser-CxXQ2RhF.js +122 -0
  27. package/dist/index.browser-CxXQ2RhF.js.map +1 -0
  28. package/dist/index.browser-DjEZSiqI.js +1137 -0
  29. package/dist/index.browser-DjEZSiqI.js.map +1 -0
  30. package/dist/index.browser-DuVkpEzB.js +1253 -0
  31. package/dist/index.browser-DuVkpEzB.js.map +1 -0
  32. package/dist/index.browser-xJkO73vw.esm.js +119 -0
  33. package/dist/index.browser-xJkO73vw.esm.js.map +1 -0
  34. package/dist/index.esm.js +1 -1
  35. package/dist/index.js +1 -1
  36. package/dist/{index.native-DUnE51Mx.js → index.native-DJA9_K3i.js} +186 -2669
  37. package/dist/index.native-DJA9_K3i.js.map +1 -0
  38. package/dist/{index.native-DuKhZcus.esm.js → index.native-TLhfXfe6.esm.js} +187 -2669
  39. package/dist/index.native-TLhfXfe6.esm.js.map +1 -0
  40. package/dist/index.native.esm.js +1 -1
  41. package/dist/index.native.js +1 -1
  42. package/dist/{phantom-wallet-provider-Cg-srwP4.js → phantom-wallet-provider-BegJFoWW.js} +141 -12
  43. package/dist/{phantom-wallet-provider-Cg-srwP4.js.map → phantom-wallet-provider-BegJFoWW.js.map} +1 -1
  44. package/dist/{phantom-wallet-provider--BJjVUA1.esm.js → phantom-wallet-provider-DzUAMhbm.esm.js} +141 -12
  45. package/dist/{phantom-wallet-provider--BJjVUA1.esm.js.map → phantom-wallet-provider-DzUAMhbm.esm.js.map} +1 -1
  46. package/dist/{privy-wallet-provider-BLcur3Ue.esm.js → privy-wallet-provider-BspbiyOr.esm.js} +3 -3
  47. package/dist/privy-wallet-provider-BspbiyOr.esm.js.map +1 -0
  48. package/dist/{privy-wallet-provider-DpNVyaXa.js → privy-wallet-provider-Du-QHaaG.js} +3 -3
  49. package/dist/privy-wallet-provider-Du-QHaaG.js.map +1 -0
  50. package/dist/{solana-mobile-wallet-provider-CFaubssb.esm.js → solana-mobile-wallet-provider-Bh7SBFpQ.esm.js} +53 -4
  51. package/dist/{solana-mobile-wallet-provider-CFaubssb.esm.js.map → solana-mobile-wallet-provider-Bh7SBFpQ.esm.js.map} +1 -1
  52. package/dist/{solana-mobile-wallet-provider-zXAk2tfS.js → solana-mobile-wallet-provider-DPp4SYem.js} +53 -4
  53. package/dist/{solana-mobile-wallet-provider-zXAk2tfS.js.map → solana-mobile-wallet-provider-DPp4SYem.js.map} +1 -1
  54. package/package.json +1 -1
  55. package/dist/index-BNyxZ82q.js.map +0 -1
  56. package/dist/index-BVi7fTm2.js.map +0 -1
  57. package/dist/index-BbtYb8sE.esm.js.map +0 -1
  58. package/dist/index-BhfNMrC0.js.map +0 -1
  59. package/dist/index-CKIoDkjJ.esm.js +0 -6
  60. package/dist/index-CKIoDkjJ.esm.js.map +0 -1
  61. package/dist/index-COIUWugk.esm.js.map +0 -1
  62. package/dist/index-CSraUgD6.js +0 -8
  63. package/dist/index-CSraUgD6.js.map +0 -1
  64. package/dist/index-Db0NqU8R.esm.js.map +0 -1
  65. package/dist/index.browser-8hyi2LOX.js.map +0 -1
  66. package/dist/index.browser-B4zXnffD.esm.js +0 -225
  67. package/dist/index.browser-B4zXnffD.esm.js.map +0 -1
  68. package/dist/index.browser-BJ_TdUVA.js +0 -228
  69. package/dist/index.browser-BJ_TdUVA.js.map +0 -1
  70. package/dist/index.browser-BkNaRRVe.js +0 -1222
  71. package/dist/index.browser-BkNaRRVe.js.map +0 -1
  72. package/dist/index.browser-BuHl80dp.esm.js.map +0 -1
  73. package/dist/index.browser-CnbxBj3-.esm.js +0 -1219
  74. package/dist/index.browser-CnbxBj3-.esm.js.map +0 -1
  75. package/dist/index.browser-OvGNsMPu.esm.js +0 -1002
  76. package/dist/index.browser-OvGNsMPu.esm.js.map +0 -1
  77. package/dist/index.browser-vuTr40so.js +0 -1008
  78. package/dist/index.browser-vuTr40so.js.map +0 -1
  79. package/dist/index.native-DUnE51Mx.js.map +0 -1
  80. package/dist/index.native-DuKhZcus.esm.js.map +0 -1
  81. package/dist/privy-wallet-provider-BLcur3Ue.esm.js.map +0 -1
  82. package/dist/privy-wallet-provider-DpNVyaXa.js.map +0 -1
@@ -1,4 +1,4 @@
1
- export { X as DEFAULT_TEST_ADDRESS, _ as InsufficientBalanceError, V as MockAuthProvider, Y as OffchainAuthProvider, Z as PrivyExpoProvider, $ as ReactNativeSessionManager, a0 as ServerSessionManager, W as WebSessionManager, O as aggregate, b as buildSetDocumentsTransaction, a1 as clearCache, a2 as closeAllSubscriptions, c as convertRemainingAccounts, N as count, f as createSessionWithPrivy, o as createSessionWithSignature, R as deserializeTransaction, m as genAuthNonce, n as genSolanaMessage, B as get, w as getAuthLoading, A as getAuthProvider, a3 as getCachedData, z as getConfig, t as getCurrentUser, F as getFiles, T as getIdToken, a4 as getMany, g as getPlatform, q as init, x as login, y as logout, v as onAuthLoadingChanged, u as onAuthStateChanged, a5 as reconnectWithNewAuth, a6 as refreshSession, I as runExpression, J as runExpressionMany, G as runQuery, H as runQueryMany, C as set, E as setFile, D as setMany, U as setPlatform, M as signAndSubmitTransaction, K as signMessage, a7 as signSessionCreateMessage, L as signTransaction, P as subscribe, Q as useAuth } from './index.native-DuKhZcus.esm.js';
1
+ export { U as DEFAULT_TEST_ADDRESS, Y as InsufficientBalanceError, T as MockAuthProvider, V as OffchainAuthProvider, X as PrivyExpoProvider, Z as ReactNativeSessionManager, _ as ServerSessionManager, W as WebSessionManager, M as aggregate, b as buildSetDocumentsTransaction, $ as clearCache, a0 as closeAllSubscriptions, c as convertRemainingAccounts, L as count, f as createSessionWithPrivy, n as createSessionWithSignature, P as deserializeTransaction, l as genAuthNonce, m as genSolanaMessage, z as get, u as getAuthLoading, y as getAuthProvider, a1 as getCachedData, x as getConfig, q as getCurrentUser, D as getFiles, Q as getIdToken, a2 as getMany, g as getPlatform, p as init, v as login, w as logout, t as onAuthLoadingChanged, r as onAuthStateChanged, a3 as reconnectWithNewAuth, a4 as refreshSession, G as runExpression, H as runExpressionMany, E as runQuery, F as runQueryMany, A as set, C as setFile, B as setMany, R as setPlatform, K as signAndSubmitTransaction, I as signMessage, a5 as signSessionCreateMessage, J as signTransaction, N as subscribe, O as useAuth } from './index.native-TLhfXfe6.esm.js';
2
2
  import 'axios';
3
3
  import '@solana/web3.js';
4
4
  import '@coral-xyz/anchor';
@@ -1,6 +1,6 @@
1
1
  'use strict';
2
2
 
3
- var index_native = require('./index.native-DUnE51Mx.js');
3
+ var index_native = require('./index.native-DJA9_K3i.js');
4
4
  require('axios');
5
5
  require('@solana/web3.js');
6
6
  require('@coral-xyz/anchor');
@@ -1,7 +1,7 @@
1
1
  'use strict';
2
2
 
3
- var index = require('./index-CSraUgD6.js');
4
- var index_native = require('./index.native-DUnE51Mx.js');
3
+ var index = require('./index-Bdcc5821.js');
4
+ var index_native = require('./index.native-DJA9_K3i.js');
5
5
  var web3_js = require('@solana/web3.js');
6
6
  var anchor = require('@coral-xyz/anchor');
7
7
  require('axios');
@@ -73,7 +73,7 @@ async function loadDependencies() {
73
73
  const [reactModule, reactDomModule, phantomModule] = await Promise.all([
74
74
  import('react'),
75
75
  import('react-dom/client'),
76
- Promise.resolve().then(function () { return require('./index-BhfNMrC0.js'); })
76
+ Promise.resolve().then(function () { return require('./index-BjlCinic.js'); })
77
77
  ]);
78
78
  // Extract default export from ESM module namespace
79
79
  // Dynamic import() returns { default: Module, ...exports }, not the module directly
@@ -116,8 +116,13 @@ class PhantomWalletProvider {
116
116
  async initializeAsync() {
117
117
  // Lazy load dependencies only when actually instantiating
118
118
  await loadDependencies();
119
- // Initialize React component
120
- this.initialize();
119
+ // Initialize React component eagerly only when there's a real reason to
120
+ // (URL callback to consume, prior session to restore, in-page wallet,
121
+ // or non-Android). Otherwise defer until ensureReady() is reached from
122
+ // a user-gesture flow. See shouldMountEagerly() for the rationale.
123
+ if (this.shouldMountEagerly()) {
124
+ this.initialize();
125
+ }
121
126
  }
122
127
  /**
123
128
  * Check if social login providers are configured (non-injected providers).
@@ -125,6 +130,69 @@ class PhantomWalletProvider {
125
130
  hasSocialProviders() {
126
131
  return this.resolvedProviders.some(p => p !== 'injected');
127
132
  }
133
+ /**
134
+ * Decide whether to mount the @phantom/react-sdk <PhantomProvider> tree
135
+ * eagerly during init() or defer until the first user-triggered call
136
+ * (login / sign / etc.) reaches ensureReady().
137
+ *
138
+ * Mounting the React tree synchronously constructs BrowserSDK, which runs
139
+ * wallet-standard discovery in its constructor and fires sdk.autoConnect()
140
+ * in a useEffect on mount. On Solana Seeker (Android Chrome PWA), both
141
+ * pathways probe the Android intent surface to discover the Phantom mobile
142
+ * app, which surfaces Chrome's system "wants to access other apps and
143
+ * services" permission dialog *before* the PWA activity has window focus.
144
+ * The dialog renders with grayed-out buttons until the user backgrounds
145
+ * and resumes the app.
146
+ *
147
+ * Returns true when eager mount is needed (callback to handle, prior
148
+ * session, in-page wallet present, or non-Android). Otherwise returns
149
+ * false — the React tree is mounted lazily inside ensureReady() once a
150
+ * user gesture brings us there.
151
+ */
152
+ shouldMountEagerly() {
153
+ if (typeof window === 'undefined')
154
+ return false;
155
+ // Preserve desktop behavior: always mount eagerly.
156
+ if (!index_native.detectAndroid())
157
+ return true;
158
+ // In-page wallet present (Phantom in-app browser / desktop extension on
159
+ // a desktop-mode Android UA): no Android intent probe needed, mount free.
160
+ // Tighten beyond truthy `window.phantom` since arbitrary stubs can land
161
+ // on that key — require a wallet-shaped surface.
162
+ const ph = window.phantom;
163
+ if (ph && (ph.solana || ph.ethereum || ph.app))
164
+ return true;
165
+ // Returning from a Phantom redirect (OAuth or deeplink hop). SDK must
166
+ // be live to read these URL params via urlParamsAccessor.
167
+ const callbackKeys = ['session_id', 'wallet_id', 'selected_account_index', 'error', 'error_description'];
168
+ try {
169
+ const params = new URLSearchParams(window.location.search);
170
+ if (callbackKeys.some(k => params.has(k)))
171
+ return true;
172
+ }
173
+ catch (_a) {
174
+ return true; // conservative on URL access failure
175
+ }
176
+ // Returning user with a stored Phantom session. They've already
177
+ // approved the Android intent permission for this origin on first
178
+ // login, so the dialog is typically pre-granted by Chrome — eager
179
+ // mount lets autoConnect silently restore the wallet handshake.
180
+ // Require BOTH the marker AND a session storage entry so a stale
181
+ // orphaned marker doesn't keep eager-mounting forever. Note
182
+ // isAuthenticated() is a raw key-existence check, not a validity
183
+ // check — restoreSession() above clears the marker on the next load
184
+ // if the session is unusable, so the bug self-corrects after at
185
+ // most one further cold start.
186
+ try {
187
+ const stored = index_native.getPlatform().storage.getItem('tarobase_last_auth_method');
188
+ if (stored === 'phantom' && index_native.WebSessionManager.isAuthenticated())
189
+ return true;
190
+ }
191
+ catch (_b) {
192
+ return true;
193
+ }
194
+ return false;
195
+ }
128
196
  static getInstance(networkUrl, config) {
129
197
  if (!PhantomWalletProvider.instance) {
130
198
  new PhantomWalletProvider(networkUrl, config);
@@ -485,11 +553,20 @@ class PhantomWalletProvider {
485
553
  const handleMobileWalletClick = async () => {
486
554
  that.loginInProgress = false;
487
555
  walletClickedRef.current = true;
488
- setShowWalletModal(false);
556
+ // Don't close the wallet modal yet. On Android Chrome PWA,
557
+ // closing the modal here triggers a React commit and a focus
558
+ // transition that races MWA's transact() opening a localhost
559
+ // WebSocket. Chrome's "Apps on Device" / Local Network Access
560
+ // permission dialog spawns inheriting the activity's focus
561
+ // state at that moment — and the in-transit focus produces a
562
+ // dialog with grayed-out Allow/Block buttons. Keep the modal
563
+ // mounted through MWA login so focus is stable when the
564
+ // system dialog spawns; close it after login resolves.
489
565
  if (that.onSwitchToMWA) {
490
566
  try {
491
567
  const mwaProvider = await that.onSwitchToMWA();
492
568
  const user = await mwaProvider.login();
569
+ setShowWalletModal(false);
493
570
  if (that.pendingLogin && user) {
494
571
  that.pendingLogin.resolve(user);
495
572
  that.pendingLogin = null;
@@ -500,12 +577,16 @@ class PhantomWalletProvider {
500
577
  }
501
578
  }
502
579
  catch (error) {
580
+ setShowWalletModal(false);
503
581
  if (that.pendingLogin) {
504
582
  that.pendingLogin.reject(error);
505
583
  that.pendingLogin = null;
506
584
  }
507
585
  }
508
586
  }
587
+ else {
588
+ setShowWalletModal(false);
589
+ }
509
590
  };
510
591
  const handleCloseModal = () => {
511
592
  setShowWalletModal(false);
@@ -801,6 +882,13 @@ class PhantomWalletProvider {
801
882
  if (this.initPromise) {
802
883
  await this.initPromise;
803
884
  }
885
+ // Lazy-mount path: if initializeAsync deferred the React mount (e.g.
886
+ // first-time visitor on Android Chrome PWA), do it now. We're being
887
+ // called from a user-gesture flow like login(), so any Android intent
888
+ // dialog that surfaces will appear with the activity already focused.
889
+ if (!this.containerElement) {
890
+ this.initialize();
891
+ }
804
892
  // Wait for SDK to be ready
805
893
  await new Promise((resolve) => {
806
894
  const check = () => {
@@ -910,12 +998,53 @@ class PhantomWalletProvider {
910
998
  });
911
999
  }
912
1000
  async restoreSession() {
913
- await this.ensureReady();
914
- const session = await index_native.WebSessionManager.getSession();
915
- if (session) {
916
- return { provider: this, address: session.address };
1001
+ // Read from storage directly. Do NOT ensureReady() here — that would
1002
+ // mount @phantom/react-sdk's <PhantomProvider> during init(), which
1003
+ // synchronously constructs BrowserSDK (running wallet-standard discovery)
1004
+ // and fires sdk.autoConnect() both probing the Android intent surface
1005
+ // before the PWA activity has window focus on Solana Seeker. The
1006
+ // resulting "access other apps and services" system dialog renders
1007
+ // with grayed-out buttons.
1008
+ //
1009
+ // Wrap getSession() in try/catch: WebSessionManager.getSession() runs
1010
+ // JSON.parse on the stored session *outside* its internal try/catch,
1011
+ // so genuinely malformed JSON in localStorage would propagate through
1012
+ // restoreSession() and break init() entirely. Treat any throw as
1013
+ // "no session" and fall through to the cleanup path so corrupted
1014
+ // storage is recoverable on next load.
1015
+ let session;
1016
+ try {
1017
+ session = await index_native.WebSessionManager.getSession();
1018
+ }
1019
+ catch (_a) {
1020
+ session = null;
1021
+ }
1022
+ if (!session) {
1023
+ // Tidy up storage so we don't leave junk behind:
1024
+ // (a) clearSession() removes any stale or unparseable session
1025
+ // storage entry. WebSessionManager.getSession() can't reach
1026
+ // its own clearSession() if JSON.parse threw. Idempotent —
1027
+ // safe to call unconditionally here.
1028
+ // (b) Drop the auth-method marker if it's stale.
1029
+ // WebSessionManager.clearSession() only removes the session
1030
+ // storage key, not the marker — so without this cleanup
1031
+ // shouldMountEagerly() would keep eager-mounting on every
1032
+ // future cold start.
1033
+ try {
1034
+ index_native.WebSessionManager.clearSession();
1035
+ }
1036
+ catch ( /* best-effort */_b) { /* best-effort */ }
1037
+ try {
1038
+ if (index_native.getPlatform().storage.getItem('tarobase_last_auth_method') === 'phantom') {
1039
+ index_native.getPlatform().storage.removeItem('tarobase_last_auth_method');
1040
+ }
1041
+ }
1042
+ catch (_c) {
1043
+ // storage unavailable — best-effort cleanup
1044
+ }
1045
+ return null;
917
1046
  }
918
- return null;
1047
+ return { provider: this, address: session.address };
919
1048
  }
920
1049
  async address() {
921
1050
  var _a, _b, _c, _d;
@@ -1372,4 +1501,4 @@ class PhantomWalletProvider {
1372
1501
  PhantomWalletProvider.instance = null;
1373
1502
 
1374
1503
  exports.PhantomWalletProvider = PhantomWalletProvider;
1375
- //# sourceMappingURL=phantom-wallet-provider-Cg-srwP4.js.map
1504
+ //# sourceMappingURL=phantom-wallet-provider-BegJFoWW.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"phantom-wallet-provider-Cg-srwP4.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
1
+ {"version":3,"file":"phantom-wallet-provider-BegJFoWW.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -1,5 +1,5 @@
1
- import { b as bufferExports } from './index-CKIoDkjJ.esm.js';
2
- import { W as WebSessionManager, c as convertRemainingAccounts, b as buildSetDocumentsTransaction, e as confirmAndCheckTransaction, s as setCurrentUser, a as SOLANA_DEVNET_RPC_URL, S as SOLANA_MAINNET_RPC_URL, h as SURFNET_RPC_URL, j as detectMobile, k as detectAndroid, l as setAuthLoading, m as genAuthNonce, n as genSolanaMessage, o as createSessionWithSignature, g as getPlatform } from './index.native-DuKhZcus.esm.js';
1
+ import { b as bufferExports } from './index-CrOVJFX9.esm.js';
2
+ import { h as detectAndroid, g as getPlatform, W as WebSessionManager, c as convertRemainingAccounts, b as buildSetDocumentsTransaction, e as confirmAndCheckTransaction, s as setCurrentUser, a as SOLANA_DEVNET_RPC_URL, S as SOLANA_MAINNET_RPC_URL, i as SURFNET_RPC_URL, j as detectMobile, k as setAuthLoading, l as genAuthNonce, m as genSolanaMessage, n as createSessionWithSignature } from './index.native-TLhfXfe6.esm.js';
3
3
  import { Connection, PublicKey, VersionedTransaction } from '@solana/web3.js';
4
4
  import * as anchor from '@coral-xyz/anchor';
5
5
  import 'axios';
@@ -52,7 +52,7 @@ async function loadDependencies() {
52
52
  const [reactModule, reactDomModule, phantomModule] = await Promise.all([
53
53
  import('react'),
54
54
  import('react-dom/client'),
55
- import('./index-BbtYb8sE.esm.js')
55
+ import('./index-CHqM9n4K.esm.js')
56
56
  ]);
57
57
  // Extract default export from ESM module namespace
58
58
  // Dynamic import() returns { default: Module, ...exports }, not the module directly
@@ -95,8 +95,13 @@ class PhantomWalletProvider {
95
95
  async initializeAsync() {
96
96
  // Lazy load dependencies only when actually instantiating
97
97
  await loadDependencies();
98
- // Initialize React component
99
- this.initialize();
98
+ // Initialize React component eagerly only when there's a real reason to
99
+ // (URL callback to consume, prior session to restore, in-page wallet,
100
+ // or non-Android). Otherwise defer until ensureReady() is reached from
101
+ // a user-gesture flow. See shouldMountEagerly() for the rationale.
102
+ if (this.shouldMountEagerly()) {
103
+ this.initialize();
104
+ }
100
105
  }
101
106
  /**
102
107
  * Check if social login providers are configured (non-injected providers).
@@ -104,6 +109,69 @@ class PhantomWalletProvider {
104
109
  hasSocialProviders() {
105
110
  return this.resolvedProviders.some(p => p !== 'injected');
106
111
  }
112
+ /**
113
+ * Decide whether to mount the @phantom/react-sdk <PhantomProvider> tree
114
+ * eagerly during init() or defer until the first user-triggered call
115
+ * (login / sign / etc.) reaches ensureReady().
116
+ *
117
+ * Mounting the React tree synchronously constructs BrowserSDK, which runs
118
+ * wallet-standard discovery in its constructor and fires sdk.autoConnect()
119
+ * in a useEffect on mount. On Solana Seeker (Android Chrome PWA), both
120
+ * pathways probe the Android intent surface to discover the Phantom mobile
121
+ * app, which surfaces Chrome's system "wants to access other apps and
122
+ * services" permission dialog *before* the PWA activity has window focus.
123
+ * The dialog renders with grayed-out buttons until the user backgrounds
124
+ * and resumes the app.
125
+ *
126
+ * Returns true when eager mount is needed (callback to handle, prior
127
+ * session, in-page wallet present, or non-Android). Otherwise returns
128
+ * false — the React tree is mounted lazily inside ensureReady() once a
129
+ * user gesture brings us there.
130
+ */
131
+ shouldMountEagerly() {
132
+ if (typeof window === 'undefined')
133
+ return false;
134
+ // Preserve desktop behavior: always mount eagerly.
135
+ if (!detectAndroid())
136
+ return true;
137
+ // In-page wallet present (Phantom in-app browser / desktop extension on
138
+ // a desktop-mode Android UA): no Android intent probe needed, mount free.
139
+ // Tighten beyond truthy `window.phantom` since arbitrary stubs can land
140
+ // on that key — require a wallet-shaped surface.
141
+ const ph = window.phantom;
142
+ if (ph && (ph.solana || ph.ethereum || ph.app))
143
+ return true;
144
+ // Returning from a Phantom redirect (OAuth or deeplink hop). SDK must
145
+ // be live to read these URL params via urlParamsAccessor.
146
+ const callbackKeys = ['session_id', 'wallet_id', 'selected_account_index', 'error', 'error_description'];
147
+ try {
148
+ const params = new URLSearchParams(window.location.search);
149
+ if (callbackKeys.some(k => params.has(k)))
150
+ return true;
151
+ }
152
+ catch (_a) {
153
+ return true; // conservative on URL access failure
154
+ }
155
+ // Returning user with a stored Phantom session. They've already
156
+ // approved the Android intent permission for this origin on first
157
+ // login, so the dialog is typically pre-granted by Chrome — eager
158
+ // mount lets autoConnect silently restore the wallet handshake.
159
+ // Require BOTH the marker AND a session storage entry so a stale
160
+ // orphaned marker doesn't keep eager-mounting forever. Note
161
+ // isAuthenticated() is a raw key-existence check, not a validity
162
+ // check — restoreSession() above clears the marker on the next load
163
+ // if the session is unusable, so the bug self-corrects after at
164
+ // most one further cold start.
165
+ try {
166
+ const stored = getPlatform().storage.getItem('tarobase_last_auth_method');
167
+ if (stored === 'phantom' && WebSessionManager.isAuthenticated())
168
+ return true;
169
+ }
170
+ catch (_b) {
171
+ return true;
172
+ }
173
+ return false;
174
+ }
107
175
  static getInstance(networkUrl, config) {
108
176
  if (!PhantomWalletProvider.instance) {
109
177
  new PhantomWalletProvider(networkUrl, config);
@@ -464,11 +532,20 @@ class PhantomWalletProvider {
464
532
  const handleMobileWalletClick = async () => {
465
533
  that.loginInProgress = false;
466
534
  walletClickedRef.current = true;
467
- setShowWalletModal(false);
535
+ // Don't close the wallet modal yet. On Android Chrome PWA,
536
+ // closing the modal here triggers a React commit and a focus
537
+ // transition that races MWA's transact() opening a localhost
538
+ // WebSocket. Chrome's "Apps on Device" / Local Network Access
539
+ // permission dialog spawns inheriting the activity's focus
540
+ // state at that moment — and the in-transit focus produces a
541
+ // dialog with grayed-out Allow/Block buttons. Keep the modal
542
+ // mounted through MWA login so focus is stable when the
543
+ // system dialog spawns; close it after login resolves.
468
544
  if (that.onSwitchToMWA) {
469
545
  try {
470
546
  const mwaProvider = await that.onSwitchToMWA();
471
547
  const user = await mwaProvider.login();
548
+ setShowWalletModal(false);
472
549
  if (that.pendingLogin && user) {
473
550
  that.pendingLogin.resolve(user);
474
551
  that.pendingLogin = null;
@@ -479,12 +556,16 @@ class PhantomWalletProvider {
479
556
  }
480
557
  }
481
558
  catch (error) {
559
+ setShowWalletModal(false);
482
560
  if (that.pendingLogin) {
483
561
  that.pendingLogin.reject(error);
484
562
  that.pendingLogin = null;
485
563
  }
486
564
  }
487
565
  }
566
+ else {
567
+ setShowWalletModal(false);
568
+ }
488
569
  };
489
570
  const handleCloseModal = () => {
490
571
  setShowWalletModal(false);
@@ -780,6 +861,13 @@ class PhantomWalletProvider {
780
861
  if (this.initPromise) {
781
862
  await this.initPromise;
782
863
  }
864
+ // Lazy-mount path: if initializeAsync deferred the React mount (e.g.
865
+ // first-time visitor on Android Chrome PWA), do it now. We're being
866
+ // called from a user-gesture flow like login(), so any Android intent
867
+ // dialog that surfaces will appear with the activity already focused.
868
+ if (!this.containerElement) {
869
+ this.initialize();
870
+ }
783
871
  // Wait for SDK to be ready
784
872
  await new Promise((resolve) => {
785
873
  const check = () => {
@@ -889,12 +977,53 @@ class PhantomWalletProvider {
889
977
  });
890
978
  }
891
979
  async restoreSession() {
892
- await this.ensureReady();
893
- const session = await WebSessionManager.getSession();
894
- if (session) {
895
- return { provider: this, address: session.address };
980
+ // Read from storage directly. Do NOT ensureReady() here — that would
981
+ // mount @phantom/react-sdk's <PhantomProvider> during init(), which
982
+ // synchronously constructs BrowserSDK (running wallet-standard discovery)
983
+ // and fires sdk.autoConnect() both probing the Android intent surface
984
+ // before the PWA activity has window focus on Solana Seeker. The
985
+ // resulting "access other apps and services" system dialog renders
986
+ // with grayed-out buttons.
987
+ //
988
+ // Wrap getSession() in try/catch: WebSessionManager.getSession() runs
989
+ // JSON.parse on the stored session *outside* its internal try/catch,
990
+ // so genuinely malformed JSON in localStorage would propagate through
991
+ // restoreSession() and break init() entirely. Treat any throw as
992
+ // "no session" and fall through to the cleanup path so corrupted
993
+ // storage is recoverable on next load.
994
+ let session;
995
+ try {
996
+ session = await WebSessionManager.getSession();
997
+ }
998
+ catch (_a) {
999
+ session = null;
1000
+ }
1001
+ if (!session) {
1002
+ // Tidy up storage so we don't leave junk behind:
1003
+ // (a) clearSession() removes any stale or unparseable session
1004
+ // storage entry. WebSessionManager.getSession() can't reach
1005
+ // its own clearSession() if JSON.parse threw. Idempotent —
1006
+ // safe to call unconditionally here.
1007
+ // (b) Drop the auth-method marker if it's stale.
1008
+ // WebSessionManager.clearSession() only removes the session
1009
+ // storage key, not the marker — so without this cleanup
1010
+ // shouldMountEagerly() would keep eager-mounting on every
1011
+ // future cold start.
1012
+ try {
1013
+ WebSessionManager.clearSession();
1014
+ }
1015
+ catch ( /* best-effort */_b) { /* best-effort */ }
1016
+ try {
1017
+ if (getPlatform().storage.getItem('tarobase_last_auth_method') === 'phantom') {
1018
+ getPlatform().storage.removeItem('tarobase_last_auth_method');
1019
+ }
1020
+ }
1021
+ catch (_c) {
1022
+ // storage unavailable — best-effort cleanup
1023
+ }
1024
+ return null;
896
1025
  }
897
- return null;
1026
+ return { provider: this, address: session.address };
898
1027
  }
899
1028
  async address() {
900
1029
  var _a, _b, _c, _d;
@@ -1351,4 +1480,4 @@ class PhantomWalletProvider {
1351
1480
  PhantomWalletProvider.instance = null;
1352
1481
 
1353
1482
  export { PhantomWalletProvider };
1354
- //# sourceMappingURL=phantom-wallet-provider--BJjVUA1.esm.js.map
1483
+ //# sourceMappingURL=phantom-wallet-provider-DzUAMhbm.esm.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"phantom-wallet-provider--BJjVUA1.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
1
+ {"version":3,"file":"phantom-wallet-provider-DzUAMhbm.esm.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;"}
@@ -1,4 +1,4 @@
1
- import { S as SOLANA_MAINNET_RPC_URL, a as SOLANA_DEVNET_RPC_URL, W as WebSessionManager, c as convertRemainingAccounts, b as buildSetDocumentsTransaction, d as bs58, e as confirmAndCheckTransaction, s as setCurrentUser, g as getPlatform, f as createSessionWithPrivy } from './index.native-DuKhZcus.esm.js';
1
+ import { S as SOLANA_MAINNET_RPC_URL, a as SOLANA_DEVNET_RPC_URL, W as WebSessionManager, c as convertRemainingAccounts, b as buildSetDocumentsTransaction, d as bs58, e as confirmAndCheckTransaction, s as setCurrentUser, g as getPlatform, f as createSessionWithPrivy } from './index.native-TLhfXfe6.esm.js';
2
2
  import { Connection, VersionedTransaction, PublicKey, Transaction } from '@solana/web3.js';
3
3
  import * as anchor from '@coral-xyz/anchor';
4
4
  import 'axios';
@@ -3848,7 +3848,7 @@ class PrivyWalletProvider {
3848
3848
  }));
3849
3849
  // The signature is returned as a Uint8Array, encode it as base58 (standard Solana format)
3850
3850
  const signatureBytes = (result === null || result === void 0 ? void 0 : result.signature) || result;
3851
- const bs58 = await import('./index.native-DuKhZcus.esm.js').then(function (n) { return n.i; });
3851
+ const bs58 = await import('./index.native-TLhfXfe6.esm.js').then(function (n) { return n.a6; });
3852
3852
  return bs58.default.encode(signatureBytes);
3853
3853
  }
3854
3854
  async restoreSession() {
@@ -3917,4 +3917,4 @@ class PrivyWalletProvider {
3917
3917
  PrivyWalletProvider.instance = null;
3918
3918
 
3919
3919
  export { PrivyWalletProvider };
3920
- //# sourceMappingURL=privy-wallet-provider-BLcur3Ue.esm.js.map
3920
+ //# sourceMappingURL=privy-wallet-provider-BspbiyOr.esm.js.map