@silentswap/react 0.0.41

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 (86) hide show
  1. package/README.md +48 -0
  2. package/dist/contexts/AssetsContext.d.ts +24 -0
  3. package/dist/contexts/AssetsContext.js +83 -0
  4. package/dist/contexts/BalancesContext.d.ts +28 -0
  5. package/dist/contexts/BalancesContext.js +533 -0
  6. package/dist/contexts/OrdersContext.d.ts +53 -0
  7. package/dist/contexts/OrdersContext.js +240 -0
  8. package/dist/contexts/PricesContext.d.ts +12 -0
  9. package/dist/contexts/PricesContext.js +109 -0
  10. package/dist/contexts/SilentSwapContext.d.ts +58 -0
  11. package/dist/contexts/SilentSwapContext.js +205 -0
  12. package/dist/hooks/silent/orderTrackingWebSocketManager.d.ts +48 -0
  13. package/dist/hooks/silent/orderTrackingWebSocketManager.js +284 -0
  14. package/dist/hooks/silent/solana-transaction.d.ts +60 -0
  15. package/dist/hooks/silent/solana-transaction.js +236 -0
  16. package/dist/hooks/silent/useAuth.d.ts +90 -0
  17. package/dist/hooks/silent/useAuth.js +269 -0
  18. package/dist/hooks/silent/useBridgeExecution.d.ts +39 -0
  19. package/dist/hooks/silent/useBridgeExecution.js +877 -0
  20. package/dist/hooks/silent/useOrderSigning.d.ts +34 -0
  21. package/dist/hooks/silent/useOrderSigning.js +133 -0
  22. package/dist/hooks/silent/useOrderTracking.d.ts +174 -0
  23. package/dist/hooks/silent/useOrderTracking.js +524 -0
  24. package/dist/hooks/silent/useQuoteCalculation.d.ts +50 -0
  25. package/dist/hooks/silent/useQuoteCalculation.js +331 -0
  26. package/dist/hooks/silent/useQuoteFetching.d.ts +18 -0
  27. package/dist/hooks/silent/useQuoteFetching.js +54 -0
  28. package/dist/hooks/silent/useRefund.d.ts +26 -0
  29. package/dist/hooks/silent/useRefund.js +134 -0
  30. package/dist/hooks/silent/useSilentClient.d.ts +16 -0
  31. package/dist/hooks/silent/useSilentClient.js +32 -0
  32. package/dist/hooks/silent/useSilentOrders.d.ts +174 -0
  33. package/dist/hooks/silent/useSilentOrders.js +73 -0
  34. package/dist/hooks/silent/useSilentQuote.d.ts +88 -0
  35. package/dist/hooks/silent/useSilentQuote.js +381 -0
  36. package/dist/hooks/silent/useWallet.d.ts +76 -0
  37. package/dist/hooks/silent/useWallet.js +203 -0
  38. package/dist/hooks/useAssetPrice.d.ts +8 -0
  39. package/dist/hooks/useAssetPrice.js +47 -0
  40. package/dist/hooks/useContacts.d.ts +52 -0
  41. package/dist/hooks/useContacts.js +259 -0
  42. package/dist/hooks/useEgressEstimates.d.ts +32 -0
  43. package/dist/hooks/useEgressEstimates.js +230 -0
  44. package/dist/hooks/useHiddenSwapFees.d.ts +22 -0
  45. package/dist/hooks/useHiddenSwapFees.js +81 -0
  46. package/dist/hooks/useOrderEstimates.d.ts +37 -0
  47. package/dist/hooks/useOrderEstimates.js +393 -0
  48. package/dist/hooks/useOutputAssetInfo.d.ts +12 -0
  49. package/dist/hooks/useOutputAssetInfo.js +38 -0
  50. package/dist/hooks/usePrices.d.ts +60 -0
  51. package/dist/hooks/usePrices.js +188 -0
  52. package/dist/hooks/useQuote.d.ts +73 -0
  53. package/dist/hooks/useQuote.js +507 -0
  54. package/dist/hooks/useResetSwapForm.d.ts +16 -0
  55. package/dist/hooks/useResetSwapForm.js +68 -0
  56. package/dist/hooks/useSlippageUsd.d.ts +11 -0
  57. package/dist/hooks/useSlippageUsd.js +19 -0
  58. package/dist/hooks/useSolanaAdapter.d.ts +15 -0
  59. package/dist/hooks/useSolanaAdapter.js +55 -0
  60. package/dist/hooks/useStatus.d.ts +25 -0
  61. package/dist/hooks/useStatus.js +60 -0
  62. package/dist/hooks/useSwap.d.ts +67 -0
  63. package/dist/hooks/useSwap.js +285 -0
  64. package/dist/hooks/useTransaction.d.ts +119 -0
  65. package/dist/hooks/useTransaction.js +353 -0
  66. package/dist/hooks/useTransactionAddress.d.ts +11 -0
  67. package/dist/hooks/useTransactionAddress.js +26 -0
  68. package/dist/hooks/useUsdValue.d.ts +7 -0
  69. package/dist/hooks/useUsdValue.js +19 -0
  70. package/dist/index.d.ts +54 -0
  71. package/dist/index.js +41 -0
  72. package/dist/stories/SilentSwapOverview.stories.d.ts +10 -0
  73. package/dist/stories/SilentSwapOverview.stories.js +364 -0
  74. package/dist/stories/useAuth.stories.d.ts +6 -0
  75. package/dist/stories/useAuth.stories.js +55 -0
  76. package/dist/stories/useSilentClient.stories.d.ts +9 -0
  77. package/dist/stories/useSilentClient.stories.js +39 -0
  78. package/dist/stories/useSilentOrders.stories.d.ts +1 -0
  79. package/dist/stories/useSilentOrders.stories.js +1 -0
  80. package/dist/stories/useSilentQuote.stories.d.ts +6 -0
  81. package/dist/stories/useSilentQuote.stories.js +267 -0
  82. package/dist/stories/useTransaction.stories.d.ts +6 -0
  83. package/dist/stories/useTransaction.stories.js +121 -0
  84. package/dist/utils/formatters.d.ts +33 -0
  85. package/dist/utils/formatters.js +82 -0
  86. package/package.json +67 -0
@@ -0,0 +1,269 @@
1
+ import { useCallback, useState, useEffect, useRef } from 'react';
2
+ import { createSignInMessage, createEip712DocForOrder, createEip712DocForWalletGeneration, loadCachedAuth, saveAuth, clearAuth, normalizeAddress, } from '@silentswap/sdk';
3
+ /**
4
+ * React hook for SilentSwap authentication with full SIWE flow
5
+ *
6
+ * This hook provides:
7
+ * - SIWE authentication with nonce management
8
+ * - Automatic auth caching and restoration
9
+ * - Sign-in message creation and signing
10
+ * - Auth state management
11
+ * - Auto-authentication when dependencies are available
12
+ *
13
+ * @param options - Configuration options for authentication
14
+ * @returns Object with authentication state and methods
15
+ *
16
+ * @example
17
+ * ```typescript
18
+ * import { useAuth, useSilentClient } from '@silentswap/react';
19
+ * import { useWalletClient, useAccount } from 'wagmi';
20
+ *
21
+ * function MyComponent() {
22
+ * const { address } = useAccount();
23
+ * const { data: walletClient } = useWalletClient();
24
+ * const client = useSilentClient({ config: { /* ... *\/ } }).client;
25
+ *
26
+ * const {
27
+ * auth,
28
+ * isAuthenticated,
29
+ * signIn,
30
+ * signOut,
31
+ * isLoading,
32
+ * error
33
+ * } = useAuth({
34
+ * client,
35
+ * address,
36
+ * walletClient: walletClient as any,
37
+ * autoAuthenticate: true,
38
+ * });
39
+ *
40
+ * return (
41
+ * <div>
42
+ * {isLoading && <div>Authenticating...</div>}
43
+ * {error && <div>Error: {error.message}</div>}
44
+ *
45
+ * {isAuthenticated() ? (
46
+ * <div>
47
+ * <p>Authenticated as {auth?.address}</p>
48
+ * <button onClick={signOut}>Sign Out</button>
49
+ * </div>
50
+ * ) : (
51
+ * <button onClick={signIn} disabled={isLoading}>
52
+ * Sign In with Ethereum
53
+ * </button>
54
+ * )}
55
+ * </div>
56
+ * );
57
+ * }
58
+ * ```
59
+ */
60
+ export function useAuth({ client, address, walletClient, domain = typeof window !== 'undefined' ? window.location.host : undefined, autoAuthenticate = false, } = {}) {
61
+ const [auth, setAuth] = useState(null);
62
+ const [nonce, setNonce] = useState(null);
63
+ const [isLoading, setIsLoading] = useState(false);
64
+ const [isAutoAuthenticating, setIsAutoAuthenticating] = useState(false);
65
+ const [error, setError] = useState(null);
66
+ // Track if auto-authentication has been attempted to prevent duplicate calls
67
+ const hasAutoAuthenticatedRef = useRef(false);
68
+ // Normalize address
69
+ const normalizedAddress = address ? normalizeAddress(address) : null;
70
+ /**
71
+ * Load cached authentication
72
+ */
73
+ const loadCachedAuthCallback = useCallback(() => {
74
+ if (!normalizedAddress)
75
+ return null;
76
+ return loadCachedAuth(normalizedAddress);
77
+ }, [normalizedAddress]);
78
+ /**
79
+ * Save authentication to cache
80
+ */
81
+ const saveAuthCallback = useCallback((authData) => {
82
+ if (!normalizedAddress)
83
+ return;
84
+ saveAuth(normalizedAddress, authData);
85
+ }, [normalizedAddress]);
86
+ /**
87
+ * Create SIWE sign-in message
88
+ */
89
+ const createSignInMessageCallback = useCallback((address, nonce, domain) => {
90
+ return createSignInMessage(address, nonce, domain);
91
+ }, []);
92
+ /**
93
+ * Create EIP-712 document for order
94
+ */
95
+ const createEip712DocForOrderCallback = useCallback((quoteResponse) => {
96
+ return createEip712DocForOrder(quoteResponse);
97
+ }, []);
98
+ /**
99
+ * Create EIP-712 document for wallet generation
100
+ */
101
+ const createEip712DocForWalletGenerationCallback = useCallback((scope, token) => {
102
+ return createEip712DocForWalletGeneration(scope, token);
103
+ }, []);
104
+ /**
105
+ * Get nonce from server
106
+ */
107
+ const getNonce = useCallback(async () => {
108
+ if (!client) {
109
+ throw new Error('Client required for nonce request');
110
+ }
111
+ if (!normalizedAddress) {
112
+ throw new Error('Address required for nonce request');
113
+ }
114
+ setError(null);
115
+ try {
116
+ const [error, response] = await client.nonce(normalizedAddress);
117
+ if (error) {
118
+ throw new Error(`Failed to get nonce: ${error.error}`);
119
+ }
120
+ const nonceValue = response.nonce;
121
+ setNonce(nonceValue);
122
+ return nonceValue;
123
+ }
124
+ catch (err) {
125
+ const error = err instanceof Error ? err : new Error('Failed to fetch nonce');
126
+ setError(error);
127
+ throw error;
128
+ }
129
+ }, [client, normalizedAddress]);
130
+ /**
131
+ * Perform SIWE authentication
132
+ */
133
+ const authenticate = useCallback(async () => {
134
+ if (!client) {
135
+ throw new Error('Client required for authentication');
136
+ }
137
+ if (!normalizedAddress) {
138
+ throw new Error('Address required for authentication');
139
+ }
140
+ if (!walletClient) {
141
+ throw new Error('Wallet client required for authentication');
142
+ }
143
+ setIsLoading(true);
144
+ setError(null);
145
+ try {
146
+ // Get nonce if we don't have one
147
+ let nonceValue = nonce;
148
+ if (!nonceValue) {
149
+ nonceValue = await getNonce();
150
+ }
151
+ // Create SIWE message
152
+ const siweMessage = createSignInMessageCallback(normalizedAddress, nonceValue, domain);
153
+ // Sign the message
154
+ const signature = await walletClient.signMessage({
155
+ account: normalizedAddress,
156
+ message: siweMessage.message,
157
+ });
158
+ // Authenticate with server
159
+ const [authError, authResponse] = await client.authenticate({
160
+ siwe: {
161
+ message: siweMessage.message,
162
+ signature: signature,
163
+ },
164
+ });
165
+ if (authError || !authResponse) {
166
+ throw new Error(`Authentication failed: ${authError?.error}`);
167
+ }
168
+ // Cache the auth response
169
+ saveAuthCallback(authResponse);
170
+ // Update state
171
+ setAuth(authResponse);
172
+ return authResponse;
173
+ }
174
+ catch (err) {
175
+ const error = err instanceof Error ? err : new Error('Authentication failed');
176
+ setError(error);
177
+ return null;
178
+ }
179
+ finally {
180
+ setIsLoading(false);
181
+ }
182
+ }, [client, normalizedAddress, walletClient, nonce, getNonce, createSignInMessageCallback, domain, saveAuthCallback]);
183
+ /**
184
+ * Sign in (alias for authenticate for convenience)
185
+ */
186
+ const signIn = useCallback(async () => {
187
+ return authenticate();
188
+ }, [authenticate]);
189
+ /**
190
+ * Sign out and clear auth
191
+ */
192
+ const signOut = useCallback(() => {
193
+ if (!normalizedAddress)
194
+ return;
195
+ clearAuth(normalizedAddress);
196
+ setAuth(null);
197
+ setNonce(null);
198
+ setError(null);
199
+ setIsAutoAuthenticating(false);
200
+ // Reset auto-authentication flag
201
+ hasAutoAuthenticatedRef.current = false;
202
+ }, [normalizedAddress]);
203
+ /**
204
+ * Check if user is authenticated
205
+ */
206
+ const isAuthenticated = useCallback(() => {
207
+ return auth !== null && auth.authExpires > Date.now();
208
+ }, [auth]);
209
+ // Load cached auth on mount
210
+ useEffect(() => {
211
+ if (normalizedAddress && !auth && !isLoading) {
212
+ const cachedAuth = loadCachedAuthCallback();
213
+ if (cachedAuth) {
214
+ setAuth(cachedAuth);
215
+ }
216
+ }
217
+ }, [normalizedAddress, auth, isLoading, loadCachedAuthCallback]);
218
+ // Auto-authenticate when dependencies are available
219
+ useEffect(() => {
220
+ // Skip if already authenticated, loading, has error, or already attempted
221
+ if (!autoAuthenticate ||
222
+ !normalizedAddress ||
223
+ !walletClient ||
224
+ auth ||
225
+ isLoading ||
226
+ isAutoAuthenticating ||
227
+ error ||
228
+ hasAutoAuthenticatedRef.current) {
229
+ return;
230
+ }
231
+ // Check if cached auth exists and is valid
232
+ const cachedAuth = loadCachedAuthCallback();
233
+ if (cachedAuth && cachedAuth.authExpires > Date.now()) {
234
+ setAuth(cachedAuth);
235
+ hasAutoAuthenticatedRef.current = true;
236
+ return;
237
+ }
238
+ // Mark as in progress and attempt authentication
239
+ setIsAutoAuthenticating(true);
240
+ authenticate()
241
+ .then(() => {
242
+ hasAutoAuthenticatedRef.current = true;
243
+ })
244
+ .catch((err) => {
245
+ console.error('Auto-authentication failed:', err);
246
+ })
247
+ .finally(() => {
248
+ setIsAutoAuthenticating(false);
249
+ });
250
+ }, [autoAuthenticate, normalizedAddress, walletClient, auth, isLoading, isAutoAuthenticating, error, authenticate, loadCachedAuthCallback]);
251
+ return {
252
+ // State
253
+ auth,
254
+ nonce,
255
+ isLoading: isLoading || isAutoAuthenticating,
256
+ error,
257
+ // Sign-in message creation
258
+ createSignInMessage: createSignInMessageCallback,
259
+ // EIP-712 document creation
260
+ createEip712DocForOrder: createEip712DocForOrderCallback,
261
+ createEip712DocForWalletGeneration: createEip712DocForWalletGenerationCallback,
262
+ // Authentication methods
263
+ getNonce,
264
+ authenticate,
265
+ signIn,
266
+ signOut,
267
+ isAuthenticated,
268
+ };
269
+ }
@@ -0,0 +1,39 @@
1
+ import type { Hex, WalletClient } from 'viem';
2
+ import type { Connector } from 'wagmi';
3
+ import type { DepositParams } from '@silentswap/sdk';
4
+ import type { SolanaWalletConnector, SolanaConnection } from './solana-transaction.js';
5
+ /**
6
+ * Result from executing a bridge transaction
7
+ */
8
+ export interface BridgeExecutionResult {
9
+ /** Transaction hash of the deposit on Avalanche */
10
+ depositTxHash: Hex;
11
+ /** Selected bridge provider */
12
+ provider: 'relay' | 'debridge';
13
+ }
14
+ /**
15
+ * Hook for executing bridge transactions (Solana → Avalanche or EVM → Avalanche)
16
+ *
17
+ * This hook handles the complete bridge execution flow:
18
+ * - Solving for optimal USDC amount (if not provided)
19
+ * - Fetching quotes from both relay.link and deBridge
20
+ * - Selecting the best provider based on rates
21
+ * - Executing bridge transactions (Solana or EVM)
22
+ * - Monitoring bridge status until deposit arrives
23
+ *
24
+ * Supports both Solana and EVM source chains, automatically selecting
25
+ * the best bridge provider (relay.link or deBridge) based on rates.
26
+ *
27
+ * @param walletClient - Wallet client for EVM transactions
28
+ * @param connector - Wagmi connector for chain switching
29
+ * @param solanaConnector - Solana wallet connector (required for Solana swaps)
30
+ * @param solanaConnection - Solana RPC connection (required for Solana swaps)
31
+ * @param solanaRpcUrl - Optional Solana RPC URL
32
+ * @param setCurrentStep - Callback to set current step message
33
+ * @param onStatus - Optional status update callback
34
+ * @returns Functions for executing bridge transactions
35
+ */
36
+ export declare function useBridgeExecution(walletClient: WalletClient | undefined, connector: Connector | undefined, solanaConnector: SolanaWalletConnector | undefined, solanaConnection: SolanaConnection | undefined, solanaRpcUrl: string | undefined, setCurrentStep: (step: string) => void, depositorAddress: Hex, onStatus?: (status: string) => void): {
37
+ executeSolanaBridge: (sourceAsset: string, sourceAmount: string, usdcAmount: string | undefined, solanaSenderAddress: string, evmSignerAddress: `0x${string}`, depositParams?: DepositParams<`${bigint}`>) => Promise<BridgeExecutionResult>;
38
+ executeEvmBridge: (sourceChainId: number, sourceTokenAddress: string, sourceAmount: string, usdcAmount: string | undefined, depositParams: DepositParams<`${bigint}`>, evmSignerAddress: `0x${string}`, evmSenderAddress?: `0x${string}`, provider?: "relay" | "debridge") => Promise<BridgeExecutionResult>;
39
+ };