@explorins/pers-sdk-react-native 1.3.2 → 1.5.2

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 (94) hide show
  1. package/README.md +276 -123
  2. package/dist/hooks/index.d.ts +10 -0
  3. package/dist/hooks/index.d.ts.map +1 -1
  4. package/dist/hooks/index.js +8 -0
  5. package/dist/hooks/useAnalytics.d.ts +96 -0
  6. package/dist/hooks/useAnalytics.d.ts.map +1 -0
  7. package/dist/hooks/useAnalytics.js +73 -0
  8. package/dist/hooks/useAuth.d.ts +52 -7
  9. package/dist/hooks/useAuth.d.ts.map +1 -1
  10. package/dist/hooks/useAuth.js +250 -3
  11. package/dist/hooks/useBusiness.d.ts +45 -3
  12. package/dist/hooks/useBusiness.d.ts.map +1 -1
  13. package/dist/hooks/useBusiness.js +182 -28
  14. package/dist/hooks/useCampaigns.d.ts +11 -4
  15. package/dist/hooks/useCampaigns.d.ts.map +1 -1
  16. package/dist/hooks/useCampaigns.js +101 -39
  17. package/dist/hooks/useDonations.d.ts +33 -0
  18. package/dist/hooks/useDonations.d.ts.map +1 -0
  19. package/dist/hooks/useDonations.js +62 -0
  20. package/dist/hooks/useFiles.d.ts +50 -0
  21. package/dist/hooks/useFiles.d.ts.map +1 -0
  22. package/dist/hooks/useFiles.js +140 -0
  23. package/dist/hooks/usePurchases.d.ts +9 -0
  24. package/dist/hooks/usePurchases.d.ts.map +1 -0
  25. package/dist/hooks/usePurchases.js +56 -0
  26. package/dist/hooks/useRedemptions.d.ts +10 -5
  27. package/dist/hooks/useRedemptions.d.ts.map +1 -1
  28. package/dist/hooks/useRedemptions.js +118 -66
  29. package/dist/hooks/useTenants.d.ts +10 -0
  30. package/dist/hooks/useTenants.d.ts.map +1 -0
  31. package/dist/hooks/useTenants.js +68 -0
  32. package/dist/hooks/useTokens.d.ts +36 -2
  33. package/dist/hooks/useTokens.d.ts.map +1 -1
  34. package/dist/hooks/useTokens.js +180 -19
  35. package/dist/hooks/useTransactionSigner.d.ts +73 -0
  36. package/dist/hooks/useTransactionSigner.d.ts.map +1 -0
  37. package/dist/hooks/useTransactionSigner.js +216 -0
  38. package/dist/hooks/useTransactions.d.ts +45 -3
  39. package/dist/hooks/useTransactions.d.ts.map +1 -1
  40. package/dist/hooks/useTransactions.js +149 -39
  41. package/dist/hooks/useUserStatus.d.ts +9 -0
  42. package/dist/hooks/useUserStatus.d.ts.map +1 -0
  43. package/dist/hooks/useUserStatus.js +57 -0
  44. package/dist/hooks/useUsers.d.ts +17 -0
  45. package/dist/hooks/useUsers.d.ts.map +1 -0
  46. package/dist/hooks/useUsers.js +120 -0
  47. package/dist/hooks/useWeb3.d.ts +69 -6
  48. package/dist/hooks/useWeb3.d.ts.map +1 -1
  49. package/dist/hooks/useWeb3.js +177 -17
  50. package/dist/index.d.ts +6 -4
  51. package/dist/index.d.ts.map +1 -1
  52. package/dist/index.js +31540 -794
  53. package/dist/index.js.map +1 -1
  54. package/dist/polyfills/index.d.ts +1 -1
  55. package/dist/polyfills/index.d.ts.map +1 -1
  56. package/dist/polyfills/index.js +155 -9
  57. package/dist/polyfills/web3-polyfills.d.ts +7 -0
  58. package/dist/polyfills/web3-polyfills.d.ts.map +1 -0
  59. package/dist/polyfills/web3-polyfills.js +85 -0
  60. package/dist/providers/PersSDKProvider.d.ts +28 -18
  61. package/dist/providers/PersSDKProvider.d.ts.map +1 -1
  62. package/dist/providers/PersSDKProvider.js +63 -129
  63. package/dist/providers/react-native-auth-provider.d.ts +19 -64
  64. package/dist/providers/react-native-auth-provider.d.ts.map +1 -1
  65. package/dist/providers/react-native-auth-provider.js +57 -175
  66. package/package.json +177 -157
  67. package/src/hooks/index.ts +13 -1
  68. package/src/hooks/useAnalytics.ts +150 -0
  69. package/src/hooks/useAuth.ts +286 -27
  70. package/src/hooks/useBusiness.ts +193 -30
  71. package/src/hooks/useCampaigns.ts +121 -43
  72. package/src/hooks/useDonations.ts +68 -0
  73. package/src/hooks/useFiles.ts +160 -0
  74. package/src/hooks/usePurchases.ts +69 -0
  75. package/src/hooks/useRedemptions.ts +135 -68
  76. package/src/hooks/useTenants.ts +77 -0
  77. package/src/hooks/useTokens.ts +189 -21
  78. package/src/hooks/useTransactionSigner.ts +287 -0
  79. package/src/hooks/useTransactions.ts +163 -41
  80. package/src/hooks/useUserStatus.ts +65 -0
  81. package/src/hooks/useUsers.ts +133 -0
  82. package/src/hooks/useWeb3.ts +201 -21
  83. package/src/index.ts +22 -17
  84. package/src/polyfills/index.ts +163 -10
  85. package/src/polyfills/web3-polyfills.ts +98 -0
  86. package/src/providers/PersSDKProvider.tsx +114 -178
  87. package/src/providers/react-native-auth-provider.ts +65 -208
  88. package/dist/index.esm.js +0 -1057
  89. package/dist/index.esm.js.map +0 -1
  90. package/dist/polyfills/index.simple.d.ts +0 -2
  91. package/dist/polyfills/index.simple.d.ts.map +0 -1
  92. package/dist/polyfills/index.simple.js +0 -17
  93. package/src/polyfills/index.simple.ts +0 -22
  94. package/src/types/external-modules.d.ts +0 -13
@@ -0,0 +1,133 @@
1
+ import { useCallback } from 'react';
2
+ import { usePersSDK } from '../providers/PersSDKProvider';
3
+ import type { UserDTO, UserCreateRequestDTO } from '@explorins/pers-shared';
4
+ import type { UserPublicProfileDTO } from '@explorins/pers-sdk/user';
5
+
6
+ export const useUsers = () => {
7
+ const { sdk, isInitialized, isAuthenticated } = usePersSDK();
8
+
9
+ const getCurrentUser = useCallback(async (): Promise<UserDTO> => {
10
+ if (!isInitialized || !sdk) {
11
+ throw new Error('SDK not initialized. Call initialize() first.');
12
+ }
13
+ if (!isAuthenticated) {
14
+ throw new Error('SDK not authenticated. getCurrentUser requires authentication.');
15
+ }
16
+
17
+ try {
18
+ const result = await sdk.users.getCurrentUser();
19
+ console.log('Current user fetched successfully:', result);
20
+ return result;
21
+ } catch (error) {
22
+ console.error('Failed to fetch current user:', error);
23
+ throw error;
24
+ }
25
+ }, [sdk, isInitialized, isAuthenticated]);
26
+
27
+ const updateCurrentUser = useCallback(async (userData: UserCreateRequestDTO): Promise<UserDTO> => {
28
+ if (!isInitialized || !sdk) {
29
+ throw new Error('SDK not initialized. Call initialize() first.');
30
+ }
31
+ if (!isAuthenticated) {
32
+ throw new Error('SDK not authenticated. updateCurrentUser requires authentication.');
33
+ }
34
+
35
+ try {
36
+ const result = await sdk.users.updateCurrentUser(userData);
37
+ console.log('Current user updated successfully:', result);
38
+ return result;
39
+ } catch (error) {
40
+ console.error('Failed to update current user:', error);
41
+ throw error;
42
+ }
43
+ }, [sdk, isInitialized, isAuthenticated]);
44
+
45
+ const getUserById = useCallback(async (userId: string): Promise<UserDTO> => {
46
+ if (!isInitialized || !sdk) {
47
+ throw new Error('SDK not initialized. Call initialize() first.');
48
+ }
49
+
50
+ try {
51
+ const result = await sdk.users.getUserById(userId);
52
+ console.log('User fetched successfully:', result);
53
+ return result;
54
+ } catch (error) {
55
+ console.error('Failed to fetch user:', error);
56
+ throw error;
57
+ }
58
+ }, [sdk, isInitialized]);
59
+
60
+ const getAllUsersPublic = useCallback(async (filter?: { key: string; value: string }): Promise<UserPublicProfileDTO[]> => {
61
+ if (!isInitialized || !sdk) {
62
+ throw new Error('SDK not initialized. Call initialize() first.');
63
+ }
64
+
65
+ try {
66
+ const result = await sdk.users.getAllUsersPublic(filter);
67
+ console.log('Public users fetched successfully:', result);
68
+ return result;
69
+ } catch (error) {
70
+ console.error('Failed to fetch public users:', error);
71
+ throw error;
72
+ }
73
+ }, [sdk, isInitialized]);
74
+
75
+ // Admin methods
76
+ const getAllUsers = useCallback(async (): Promise<UserDTO[]> => {
77
+ if (!isInitialized || !sdk) {
78
+ throw new Error('SDK not initialized. Call initialize() first.');
79
+ }
80
+
81
+ try {
82
+ const result = await sdk.users.getAllUsers();
83
+ console.log('All users fetched successfully:', result);
84
+ return result;
85
+ } catch (error) {
86
+ console.error('Failed to fetch all users:', error);
87
+ throw error;
88
+ }
89
+ }, [sdk, isInitialized]);
90
+
91
+ const updateUser = useCallback(async (userId: string, userData: UserCreateRequestDTO): Promise<UserDTO> => {
92
+ if (!isInitialized || !sdk) {
93
+ throw new Error('SDK not initialized. Call initialize() first.');
94
+ }
95
+
96
+ try {
97
+ const result = await sdk.users.updateUser(userId, userData);
98
+ console.log('User updated successfully:', result);
99
+ return result;
100
+ } catch (error) {
101
+ console.error('Failed to update user:', error);
102
+ throw error;
103
+ }
104
+ }, [sdk, isInitialized]);
105
+
106
+ const toggleUserStatus = useCallback(async (user: UserDTO): Promise<UserDTO> => {
107
+ if (!isInitialized || !sdk) {
108
+ throw new Error('SDK not initialized. Call initialize() first.');
109
+ }
110
+
111
+ try {
112
+ const result = await sdk.users.toggleUserStatus(user);
113
+ console.log('User status toggled successfully:', result);
114
+ return result;
115
+ } catch (error) {
116
+ console.error('Failed to toggle user status:', error);
117
+ throw error;
118
+ }
119
+ }, [sdk, isInitialized]);
120
+
121
+ return {
122
+ getCurrentUser,
123
+ updateCurrentUser,
124
+ getUserById,
125
+ getAllUsersPublic,
126
+ getAllUsers,
127
+ updateUser,
128
+ toggleUserStatus,
129
+ isAvailable: isInitialized && !!sdk?.users,
130
+ };
131
+ };
132
+
133
+ export type UserHook = ReturnType<typeof useUsers>;
@@ -1,51 +1,224 @@
1
1
  import { useCallback } from 'react';
2
2
  import { usePersSDK } from '../providers/PersSDKProvider';
3
+ import type {
4
+ TokenBalance,
5
+ TokenBalanceRequest,
6
+ TokenCollectionRequest,
7
+ TokenCollection,
8
+ TokenMetadata
9
+ } from '@explorins/pers-sdk/web3';
10
+ import type { ChainData } from '@explorins/pers-sdk/web3-chain';
3
11
 
12
+ interface WalletInfo {
13
+ address: string | null;
14
+ isConnected: boolean;
15
+ }
16
+
17
+ /**
18
+ * React hook for Web3 operations in the PERS SDK
19
+ *
20
+ * Provides comprehensive Web3 functionality including token balance queries,
21
+ * metadata retrieval, collection management, IPFS resolution, and blockchain
22
+ * explorer integration. Supports multi-chain operations and wallet management.
23
+ *
24
+ * @returns Web3 hook with methods for blockchain operations
25
+ *
26
+ * @example
27
+ * ```typescript
28
+ * function Web3Component() {
29
+ * const {
30
+ * getTokenBalance,
31
+ * getTokenMetadata,
32
+ * getWalletInfo,
33
+ * accountAddress
34
+ * } = useWeb3();
35
+ *
36
+ * const loadTokenData = async () => {
37
+ * try {
38
+ * if (!accountAddress) {
39
+ * console.log('No wallet connected');
40
+ * return;
41
+ * }
42
+ *
43
+ * const balance = await getTokenBalance({
44
+ * walletAddress: accountAddress,
45
+ * contractAddress: '0x123...',
46
+ * chainId: 1
47
+ * });
48
+ *
49
+ * console.log('Token balance:', balance);
50
+ * } catch (error) {
51
+ * console.error('Failed to load token data:', error);
52
+ * }
53
+ * };
54
+ *
55
+ * return (
56
+ * <div>
57
+ * {accountAddress ? (
58
+ * <div>
59
+ * <p>Wallet: {accountAddress}</p>
60
+ * <button onClick={loadTokenData}>Load Tokens</button>
61
+ * </div>
62
+ * ) : (
63
+ * <p>No wallet connected</p>
64
+ * )}
65
+ * </div>
66
+ * );
67
+ * }
68
+ * ```
69
+ */
4
70
  export const useWeb3 = () => {
5
- const { web3, isInitialized, isAuthenticated, accountAddress } = usePersSDK();
71
+ const { sdk, isInitialized, isAuthenticated, accountAddress } = usePersSDK();
6
72
 
7
73
  if (!isAuthenticated && isInitialized) {
8
74
  console.warn('SDK not authenticated. Some web3 operations may fail.');
9
75
  }
10
76
 
11
- const getTokenBalance = useCallback(async (request: any) => {
12
- if (!isInitialized) {
77
+ /**
78
+ * Retrieves token balance for a specific wallet and contract
79
+ *
80
+ * @param request - Token balance request containing wallet address, contract, and chain info
81
+ * @returns Promise resolving to token balance data
82
+ * @throws Error if SDK is not initialized
83
+ *
84
+ * @example
85
+ * ```typescript
86
+ * const { getTokenBalance } = useWeb3();
87
+ * const balance = await getTokenBalance({
88
+ * walletAddress: '0x123...',
89
+ * contractAddress: '0x456...',
90
+ * chainId: 1,
91
+ * tokenId: '1' // For NFTs
92
+ * });
93
+ * console.log('Balance:', balance.balance);
94
+ * ```
95
+ */
96
+ const getTokenBalance = useCallback(async (request: TokenBalanceRequest): Promise<TokenBalance> => {
97
+ console.log('[useWeb3] getTokenBalance called with request:', request);
98
+ if (!isInitialized || !sdk) {
13
99
  throw new Error('SDK not initialized. Call initialize() first.');
14
100
  }
15
- if (!web3?.getTokenBalance) {
16
- throw new Error('getTokenBalance method not available');
101
+
102
+ try {
103
+ const result = await sdk.web3.getTokenBalance(request);
104
+ console.log('Token balance fetched successfully:', result);
105
+ return result;
106
+ } catch (error) {
107
+ console.error('Failed to fetch token balance:', error);
108
+ throw error;
109
+ }
110
+ }, [sdk, isInitialized]);
111
+
112
+ /**
113
+ * Retrieves metadata for a specific token (useful for NFTs)
114
+ *
115
+ * @param request - Token balance request containing contract and token info
116
+ * @returns Promise resolving to token metadata or null if not available
117
+ * @throws Error if SDK is not initialized
118
+ *
119
+ * @example
120
+ * ```typescript
121
+ * const { getTokenMetadata } = useWeb3();
122
+ * const metadata = await getTokenMetadata({
123
+ * contractAddress: '0x123...',
124
+ * tokenId: '1',
125
+ * chainId: 1
126
+ * });
127
+ * console.log('NFT name:', metadata?.name);
128
+ * console.log('NFT image:', metadata?.image);
129
+ * ```
130
+ */
131
+ const getTokenMetadata = useCallback(async (request: TokenBalanceRequest): Promise<TokenMetadata | null> => {
132
+ if (!isInitialized || !sdk) {
133
+ throw new Error('SDK not initialized. Call initialize() first.');
17
134
  }
18
135
 
19
136
  try {
20
- const result = await web3.getTokenBalance(request);
21
- console.log('Token balance fetched successfully:', result);
137
+ const result = await sdk.web3.getTokenMetadata(request);
138
+ console.log('Token metadata fetched successfully:', result);
22
139
  return result;
23
140
  } catch (error) {
24
- console.error('Failed to fetch token balance:', error);
141
+ console.error('Failed to fetch token metadata:', error);
25
142
  throw error;
26
143
  }
27
- }, [web3]);
144
+ }, [sdk, isInitialized]);
28
145
 
29
- const getTokenCollection = useCallback(async (request: any) => {
30
- if (!isInitialized) {
146
+ const getTokenCollection = useCallback(async (request: TokenCollectionRequest): Promise<TokenCollection> => {
147
+ if (!isInitialized || !sdk) {
31
148
  throw new Error('SDK not initialized. Call initialize() first.');
32
149
  }
33
- if (!web3?.getTokenCollection) {
34
- console.warn('getTokenCollection method not available');
35
- return [];
150
+
151
+ try {
152
+ const result = await sdk.web3.getTokenCollection(request);
153
+ console.log('Token collection fetched successfully:', result);
154
+ return result;
155
+ } catch (error) {
156
+ console.error('Failed to fetch token collection:', error);
157
+ throw error;
158
+ }
159
+ }, [sdk, isInitialized]);
160
+
161
+ const resolveIPFSUrl = useCallback(async (url: string, chainId: number): Promise<string> => {
162
+ if (!isInitialized || !sdk) {
163
+ throw new Error('SDK not initialized. Call initialize() first.');
36
164
  }
37
165
 
38
166
  try {
39
- const result = await web3.getTokenCollection(request);
40
- console.log(' Token collection fetched successfully:', result);
167
+ const result = await sdk.web3.resolveIPFSUrl(url, chainId);
168
+ console.log('IPFS URL resolved successfully:', result);
41
169
  return result;
42
170
  } catch (error) {
43
- console.error('Failed to fetch token collection:', error);
171
+ console.error('Failed to resolve IPFS URL:', error);
44
172
  throw error;
45
173
  }
46
- }, [web3]);
174
+ }, [sdk, isInitialized]);
47
175
 
48
- const getWalletInfo = useCallback(async () => {
176
+ const fetchAndProcessMetadata = useCallback(async (tokenUri: string, chainId: number): Promise<TokenMetadata | null> => {
177
+ if (!isInitialized || !sdk) {
178
+ throw new Error('SDK not initialized. Call initialize() first.');
179
+ }
180
+
181
+ try {
182
+ const result = await sdk.web3.fetchAndProcessMetadata(tokenUri, chainId);
183
+ console.log('Metadata fetched and processed successfully:', result);
184
+ return result;
185
+ } catch (error) {
186
+ console.error('Failed to fetch and process metadata:', error);
187
+ throw error;
188
+ }
189
+ }, [sdk, isInitialized]);
190
+
191
+ const getChainDataById = useCallback(async (chainId: number): Promise<ChainData | null> => {
192
+ if (!isInitialized || !sdk) {
193
+ throw new Error('SDK not initialized. Call initialize() first.');
194
+ }
195
+
196
+ try {
197
+ const result = await sdk.web3.getChainDataById(chainId);
198
+ console.log('Chain data fetched successfully:', result);
199
+ return result;
200
+ } catch (error) {
201
+ console.error('Failed to fetch chain data:', error);
202
+ throw error;
203
+ }
204
+ }, [sdk, isInitialized]);
205
+
206
+ const getExplorerUrl = useCallback(async (chainId: number, address: string, type: 'address' | 'tx'): Promise<string> => {
207
+ if (!isInitialized || !sdk) {
208
+ throw new Error('SDK not initialized. Call initialize() first.');
209
+ }
210
+
211
+ try {
212
+ const result = await sdk.web3.getExplorerUrl(chainId, address, type);
213
+ console.log('Explorer URL generated successfully:', result);
214
+ return result;
215
+ } catch (error) {
216
+ console.error('Failed to generate explorer URL:', error);
217
+ throw error;
218
+ }
219
+ }, [sdk, isInitialized]);
220
+
221
+ const getWalletInfo = useCallback(async (): Promise<WalletInfo | null> => {
49
222
  if (!isInitialized) {
50
223
  throw new Error('SDK not initialized. Call initialize() first.');
51
224
  }
@@ -62,9 +235,16 @@ export const useWeb3 = () => {
62
235
 
63
236
  return {
64
237
  getTokenBalance,
238
+ getTokenMetadata,
65
239
  getTokenCollection,
240
+ resolveIPFSUrl,
241
+ fetchAndProcessMetadata,
242
+ getChainDataById,
243
+ getExplorerUrl,
66
244
  getWalletInfo,
67
245
  accountAddress: isInitialized ? accountAddress : null,
68
- isAvailable: isInitialized && !!web3,
246
+ isAvailable: isInitialized && !!sdk?.web3,
69
247
  };
70
- };
248
+ };
249
+
250
+ export type Web3Hook = ReturnType<typeof useWeb3>;
package/src/index.ts CHANGED
@@ -1,25 +1,17 @@
1
1
  // Initialize React Native polyfills automatically
2
2
  import './polyfills';
3
3
 
4
- // TEMPORARY: Minimal exports to isolate the .from() error
5
- console.log('🔍 [DEBUG] Loading React Native SDK...');
6
-
7
4
  // Export React Native specific providers (FIRST - break circular dependency)
8
5
  export {
9
- BaseReactNativeAuthProvider,
10
6
  ReactNativeAuthProvider,
11
- SecureReactNativeAuthProvider,
12
- StorageStrategy,
13
7
  type ReactNativeAuthConfig
14
8
  } from './providers/react-native-auth-provider';
15
9
 
16
- console.log('🔍 [DEBUG] Auth providers loaded successfully');
17
-
18
10
  // Export Provider and Context directly (avoid circular import through hooks)
19
11
  export {
20
12
  PersSDKProvider,
21
13
  usePersSDK,
22
- type PersSDKConfig,
14
+ type PersConfig,
23
15
  type PersSDKContext
24
16
  } from './providers/PersSDKProvider';
25
17
 
@@ -28,24 +20,37 @@ export {
28
20
  useAuth,
29
21
  useTokens,
30
22
  useTransactions,
23
+ useTransactionSigner,
31
24
  useBusiness,
32
25
  useCampaigns,
33
26
  useRedemptions,
34
- useWeb3
27
+ useWeb3,
28
+ usePurchases,
29
+ useTenants,
30
+ useUsers,
31
+ useUserStatus,
32
+ useFiles,
33
+ useAnalytics,
34
+ useDonations
35
35
  } from './hooks';
36
36
 
37
- console.log('🔍 [DEBUG] React Native SDK loaded with full exports including useWeb3');
38
-
39
37
  export {
40
38
  ReactNativeHttpClient
41
39
  } from './providers/react-native-http-client';
42
40
 
43
41
  // Export polyfill utilities for advanced usage
44
42
  export {
45
- initializeReactNativePolyfills,
46
- isReactNative
43
+ initializeReactNativePolyfills
47
44
  } from './polyfills';
48
45
 
49
- // Note: For types and DTOs, import directly from @explorins/pers-shared
50
- // This maintains clean separation and avoids circular dependencies
51
- // Example: import { TokenDTO, BusinessDTO } from '@explorins/pers-shared';
46
+ // Re-export all types and utilities from @explorins/pers-shared
47
+ export * from '@explorins/pers-shared';
48
+
49
+ // Re-export Web3 types from base SDK
50
+ export type {
51
+ TokenBalanceRequest,
52
+ TokenBalance,
53
+ TokenMetadata,
54
+ TokenCollection,
55
+ TokenCollectionRequest
56
+ } from '@explorins/pers-sdk/web3';
@@ -1,16 +1,169 @@
1
- // Minimal React Native environment setup
2
- // No polyfills needed - modules are disabled at Metro level
1
+ // React Native polyfills for crypto and Web3 functionality
2
+ // Consolidated "batteries included" approach for React Native SDK
3
3
 
4
- // Simple initialization function for compatibility
4
+ import { Buffer } from 'buffer';
5
+ import { setupWeb3InstanceofPolyfill } from './web3-polyfills';
6
+
7
+ // Initialize React Native polyfills
5
8
  export const initializeReactNativePolyfills = (): boolean => {
6
- console.log('✅ [PERS SDK] React Native environment ready (no polyfills needed)');
7
- return true;
9
+ try {
10
+ // Set up basic global environment
11
+ (global as any).global = global;
12
+ (global as any).Buffer = Buffer;
13
+
14
+ // Add process if missing
15
+ if (typeof global !== 'undefined' && !global.process) {
16
+ global.process = {
17
+ env: {},
18
+ version: '16.0.0',
19
+ nextTick: (callback: () => void) => setTimeout(callback, 0)
20
+ } as any;
21
+ }
22
+
23
+ // Initialize crypto polyfills (CRITICAL for Web3)
24
+ require('react-native-get-random-values');
25
+
26
+ // Crypto polyfill for better Web3 compatibility
27
+ if (typeof global !== 'undefined' && !(global as any).crypto) {
28
+ (global as any).crypto = {
29
+ getRandomValues: (arr: any) => {
30
+ require('react-native-get-random-values');
31
+ return (global as any).crypto.getRandomValues(arr);
32
+ },
33
+ randomUUID: () => {
34
+ const hex = '0123456789abcdef';
35
+ let result = '';
36
+ for (let i = 0; i < 32; i++) {
37
+ result += hex[Math.floor(Math.random() * 16)];
38
+ if (i === 7 || i === 11 || i === 15 || i === 19) result += '-';
39
+ }
40
+ return result;
41
+ }
42
+ };
43
+ }
44
+
45
+ // Add URL polyfill for Web3 compatibility
46
+ if (typeof global !== 'undefined' && !(global as any).URL) {
47
+ try {
48
+ // Try to use react-native-url-polyfill if available
49
+ require('react-native-url-polyfill/auto');
50
+ } catch {
51
+ // Fallback to basic URL implementation
52
+ (global as any).URL = class URL {
53
+ constructor(public href: string) {}
54
+ toString() { return this.href; }
55
+ } as any;
56
+ }
57
+ }
58
+
59
+ // Add btoa/atob polyfills for Web3 compatibility
60
+ if (typeof global !== 'undefined') {
61
+ if (!(global as any).btoa) {
62
+ (global as any).btoa = (str: string) => Buffer.from(str, 'binary').toString('base64');
63
+ }
64
+ if (!(global as any).atob) {
65
+ (global as any).atob = (str: string) => Buffer.from(str, 'base64').toString('binary');
66
+ }
67
+ }
68
+
69
+ // EventTarget polyfill for Web3 providers
70
+ if (typeof global !== 'undefined' && !(global as any).EventTarget) {
71
+ (global as any).EventTarget = class EventTarget {
72
+ private listeners: { [key: string]: ((...args: any[]) => void)[] } = {};
73
+
74
+ addEventListener(type: string, listener: (...args: any[]) => void) {
75
+ if (!this.listeners[type]) {
76
+ this.listeners[type] = [];
77
+ }
78
+ this.listeners[type].push(listener);
79
+ }
80
+
81
+ removeEventListener(type: string, listener: (...args: any[]) => void) {
82
+ if (this.listeners[type]) {
83
+ const index = this.listeners[type].indexOf(listener);
84
+ if (index > -1) {
85
+ this.listeners[type].splice(index, 1);
86
+ }
87
+ }
88
+ }
89
+
90
+ dispatchEvent(event: any) {
91
+ if (this.listeners[event.type]) {
92
+ this.listeners[event.type].forEach(listener => {
93
+ listener(event);
94
+ });
95
+ }
96
+ return true;
97
+ }
98
+ };
99
+ }
100
+
101
+ // Performance polyfill
102
+ if (typeof global !== 'undefined' && !(global as any).performance) {
103
+ (global as any).performance = {
104
+ now: () => Date.now(),
105
+ timeOrigin: Date.now()
106
+ };
107
+ }
108
+
109
+ // Stream polyfill (minimal)
110
+ if (typeof global !== 'undefined' && !(global as any).stream) {
111
+ (global as any).stream = {
112
+ Readable: class {},
113
+ Writable: class {},
114
+ Transform: class {}
115
+ };
116
+ }
117
+
118
+ // Web3 specific polyfills for instanceof issues
119
+ setupWeb3Polyfills();
120
+ setupWeb3InstanceofPolyfill();
121
+
122
+ return true;
123
+ } catch (error) {
124
+ console.warn('[PERS SDK] Failed to initialize some polyfills:', error);
125
+ return true;
126
+ }
8
127
  };
9
128
 
10
- // Platform detection
11
- export const isReactNative = (): boolean => {
12
- return typeof navigator !== 'undefined' && navigator.product === 'ReactNative';
129
+ // Web3 specific polyfills to fix instanceof issues
130
+ const setupWeb3Polyfills = () => {
131
+ try {
132
+ // Ensure Symbol polyfill for constructor comparison
133
+ if (typeof global !== 'undefined' && !(global as any).Symbol) {
134
+ (global as any).Symbol = {
135
+ for: (key: string) => `Symbol(${key})`,
136
+ iterator: '@@iterator',
137
+ toStringTag: '@@toStringTag'
138
+ };
139
+ }
140
+
141
+ // Add constructor.name polyfill for better class detection
142
+ if (typeof global !== 'undefined' && typeof Function !== 'undefined') {
143
+ const originalToString = Function.prototype.toString;
144
+ if (!Function.prototype.name) {
145
+ Object.defineProperty(Function.prototype, 'name', {
146
+ get: function() {
147
+ const match = originalToString.call(this).match(/function\s*([^(]*)/);
148
+ return match ? match[1] : '';
149
+ }
150
+ });
151
+ }
152
+ }
153
+
154
+ // Module resolution enhancement for Web3
155
+ if (typeof global !== 'undefined') {
156
+ // Store reference to help with instanceof checks
157
+ (global as any).__PERS_SDK_WEB3_POLYFILLS__ = true;
158
+ }
159
+
160
+ } catch (error) {
161
+ console.warn('[PERS SDK] Web3 polyfills setup failed:', error);
162
+ }
13
163
  };
14
164
 
15
- // Auto-initialize
16
- initializeReactNativePolyfills();
165
+ // Auto-initialize polyfills when SDK is imported
166
+ initializeReactNativePolyfills();
167
+
168
+ // Export utilities for advanced usage
169
+ export { createSafeWeb3Check } from './web3-polyfills';