@rango-dev/widget-embedded 0.1.10-next.99 → 0.1.10

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 (99) hide show
  1. package/dist/App.d.ts.map +1 -1
  2. package/dist/QueueManager.d.ts.map +1 -1
  3. package/dist/components/AppRouter.d.ts +6 -1
  4. package/dist/components/AppRouter.d.ts.map +1 -1
  5. package/dist/components/AppRoutes.d.ts.map +1 -1
  6. package/dist/components/HeaderButtons.d.ts +4 -1
  7. package/dist/components/HeaderButtons.d.ts.map +1 -1
  8. package/dist/components/Layout.d.ts.map +1 -1
  9. package/dist/components/SwapDetailsPlaceholder.d.ts +9 -0
  10. package/dist/components/SwapDetailsPlaceholder.d.ts.map +1 -0
  11. package/dist/components/TokenPreview.d.ts +1 -1
  12. package/dist/components/TokenPreview.d.ts.map +1 -1
  13. package/dist/components/UpdateUrl.d.ts.map +1 -1
  14. package/dist/components/warnings/BalanceWarnings.d.ts.map +1 -1
  15. package/dist/components/warnings/MinRequiredSlippage.d.ts +1 -1
  16. package/dist/components/warnings/MinRequiredSlippage.d.ts.map +1 -1
  17. package/dist/constants/navigationRoutes.d.ts +0 -1
  18. package/dist/constants/navigationRoutes.d.ts.map +1 -1
  19. package/dist/globalStyles.d.ts.map +1 -1
  20. package/dist/hooks/useConfirmSwap.d.ts.map +1 -1
  21. package/dist/lib.d.ts.map +1 -1
  22. package/dist/pages/ConfirmSwapPage.d.ts.map +1 -1
  23. package/dist/pages/HistoryPage.d.ts.map +1 -1
  24. package/dist/pages/Home.d.ts.map +1 -1
  25. package/dist/pages/LiquiditySourcesPage.d.ts.map +1 -1
  26. package/dist/pages/SelectTokenPage.d.ts.map +1 -1
  27. package/dist/pages/SettingsPage.d.ts.map +1 -1
  28. package/dist/pages/SwapDetailsPage.d.ts.map +1 -1
  29. package/dist/pages/WalletsPage.d.ts +1 -0
  30. package/dist/pages/WalletsPage.d.ts.map +1 -1
  31. package/dist/store/bestRoute.d.ts +2 -0
  32. package/dist/store/bestRoute.d.ts.map +1 -1
  33. package/dist/store/ui.d.ts.map +1 -1
  34. package/dist/store/wallets.d.ts +14 -0
  35. package/dist/store/wallets.d.ts.map +1 -1
  36. package/dist/types/routing.d.ts +1 -1
  37. package/dist/types/swap.d.ts +6 -0
  38. package/dist/types/swap.d.ts.map +1 -1
  39. package/dist/utils/common.d.ts +1 -0
  40. package/dist/utils/common.d.ts.map +1 -1
  41. package/dist/utils/date.d.ts +3 -0
  42. package/dist/utils/date.d.ts.map +1 -0
  43. package/dist/utils/routing.d.ts +1 -0
  44. package/dist/utils/routing.d.ts.map +1 -1
  45. package/dist/utils/swap.d.ts +16 -5
  46. package/dist/utils/swap.d.ts.map +1 -1
  47. package/dist/utils/time.d.ts +4 -0
  48. package/dist/utils/time.d.ts.map +1 -0
  49. package/dist/utils/wallets.d.ts +1 -1
  50. package/dist/utils/wallets.d.ts.map +1 -1
  51. package/dist/widget-embedded.cjs.development.js +1048 -705
  52. package/dist/widget-embedded.cjs.development.js.map +1 -1
  53. package/dist/widget-embedded.cjs.production.min.js +1048 -705
  54. package/dist/widget-embedded.cjs.production.min.js.map +1 -1
  55. package/dist/widget-embedded.esm.js +1057 -714
  56. package/dist/widget-embedded.esm.js.map +1 -1
  57. package/package.json +12 -11
  58. package/readme.md +1 -2
  59. package/src/App.tsx +30 -5
  60. package/src/QueueManager.tsx +5 -2
  61. package/src/components/AppRouter.tsx +24 -13
  62. package/src/components/AppRoutes.tsx +15 -12
  63. package/src/components/HeaderButtons.tsx +9 -2
  64. package/src/components/Layout.tsx +37 -5
  65. package/src/components/SwapDetailsPlaceholder.tsx +32 -0
  66. package/src/components/TokenPreview.tsx +7 -4
  67. package/src/components/UpdateUrl.tsx +1 -3
  68. package/src/components/warnings/BalanceWarnings.tsx +1 -0
  69. package/src/components/warnings/MinRequiredSlippage.tsx +9 -4
  70. package/src/constants/navigationRoutes.ts +0 -1
  71. package/src/globalStyles.ts +2 -1
  72. package/src/hooks/useConfirmSwap.ts +2 -1
  73. package/src/hooks/useNavigateBack.ts +3 -3
  74. package/src/lib.tsx +25 -3
  75. package/src/pages/ConfirmSwapPage.tsx +128 -20
  76. package/src/pages/HistoryPage.tsx +4 -4
  77. package/src/pages/Home.tsx +19 -8
  78. package/src/pages/LiquiditySourcesPage.tsx +2 -0
  79. package/src/pages/SelectTokenPage.tsx +3 -1
  80. package/src/pages/SettingsPage.tsx +3 -0
  81. package/src/pages/SwapDetailsPage.tsx +142 -6
  82. package/src/pages/WalletsPage.tsx +47 -11
  83. package/src/store/bestRoute.ts +110 -12
  84. package/src/store/ui.ts +4 -0
  85. package/src/store/wallets.ts +4 -1
  86. package/src/types/routing.ts +1 -1
  87. package/src/types/swap.ts +7 -0
  88. package/src/utils/common.ts +14 -0
  89. package/src/utils/date.ts +62 -0
  90. package/src/utils/routing.ts +23 -13
  91. package/src/utils/swap.ts +101 -10
  92. package/src/utils/time.ts +52 -0
  93. package/src/utils/wallets.ts +13 -4
  94. package/dist/components/Header.d.ts +0 -10
  95. package/dist/components/Header.d.ts.map +0 -1
  96. package/dist/pages/ConfirmWalletsPage.d.ts +0 -3
  97. package/dist/pages/ConfirmWalletsPage.d.ts.map +0 -1
  98. package/src/components/Header.tsx +0 -37
  99. package/src/pages/ConfirmWalletsPage.tsx +0 -127
@@ -4,8 +4,9 @@ import {
4
4
  styled,
5
5
  Wallet,
6
6
  WalletState,
7
+ WalletInfo,
7
8
  } from '@rango-dev/ui';
8
- import React, { useEffect, useState } from 'react';
9
+ import React, { useEffect, useRef, useState } from 'react';
9
10
  import { getlistWallet, sortWalletsBasedOnState } from '../utils/wallets';
10
11
  import { WalletType, detectMobileScreens } from '@rango-dev/wallets-shared';
11
12
  import { useWallets } from '@rango-dev/wallets-core';
@@ -14,6 +15,9 @@ import { useUiStore } from '../store/ui';
14
15
  import { useNavigateBack } from '../hooks/useNavigateBack';
15
16
  import { navigationRoutes } from '../constants/navigationRoutes';
16
17
  import { useTranslation } from 'react-i18next';
18
+ import { useMetaStore } from '../store/meta';
19
+ import { Spinner } from '@rango-dev/ui';
20
+ import { LoadingFailedAlert } from '@rango-dev/ui';
17
21
 
18
22
  interface PropTypes {
19
23
  supportedWallets: 'all' | WalletType[];
@@ -24,9 +28,17 @@ const ListContainer = styled('div', {
24
28
  display: 'grid',
25
29
  gap: '.5rem',
26
30
  gridTemplateColumns: ' repeat(2, minmax(0, 1fr))',
27
- height: '450px',
28
31
  alignContent: 'baseline',
29
32
  padding: '0.5rem',
33
+ overflowY: 'auto',
34
+ });
35
+
36
+ export const LoaderContainer = styled('div', {
37
+ display: 'flex',
38
+ justifyContent: 'center',
39
+ width: '100%',
40
+ position: 'absolute',
41
+ top: '50%',
30
42
  });
31
43
 
32
44
  const AlertContainer = styled('div', {
@@ -40,6 +52,7 @@ export function WalletsPage({ supportedWallets, multiWallets }: PropTypes) {
40
52
  getWalletInfo,
41
53
  supportedWallets === 'all' ? Object.values(WalletType) : supportedWallets
42
54
  );
55
+ const walletsRef = useRef<WalletInfo[]>();
43
56
 
44
57
  let sortedWallets = detectMobileScreens()
45
58
  ? wallets.filter((wallet) => wallet.showOnMobile)
@@ -48,6 +61,7 @@ export function WalletsPage({ supportedWallets, multiWallets }: PropTypes) {
48
61
  const [walletErrorMessage, setWalletErrorMessage] = useState('');
49
62
  const toggleConnectWalletsButton =
50
63
  useUiStore.use.toggleConnectWalletsButton();
64
+ const loadingMetaStatus = useMetaStore.use.loadingStatus();
51
65
  const { t } = useTranslation();
52
66
 
53
67
  const onSelectWallet = async (type: WalletType) => {
@@ -69,12 +83,27 @@ export function WalletsPage({ supportedWallets, multiWallets }: PropTypes) {
69
83
  setWalletErrorMessage('Error: ' + (e as any)?.message);
70
84
  }
71
85
  };
72
-
86
+ const disconnectConnectingWallets = () => {
87
+ const connectingWallets =
88
+ walletsRef.current?.filter(
89
+ (wallet) => wallet.state === WalletState.CONNECTING
90
+ ) || [];
91
+ for (const wallet of connectingWallets) {
92
+ disconnect(wallet.type);
93
+ }
94
+ };
73
95
  useEffect(() => {
74
96
  toggleConnectWalletsButton();
75
- return () => toggleConnectWalletsButton();
97
+ return () => {
98
+ disconnectConnectingWallets();
99
+ toggleConnectWalletsButton();
100
+ };
76
101
  }, []);
77
102
 
103
+ useEffect(() => {
104
+ walletsRef.current = wallets;
105
+ }, [wallets]);
106
+
78
107
  return (
79
108
  <SecondaryPage
80
109
  title={t('Select Wallet') || ''}
@@ -87,14 +116,21 @@ export function WalletsPage({ supportedWallets, multiWallets }: PropTypes) {
87
116
  <Alert type="error">{walletErrorMessage}</Alert>
88
117
  </AlertContainer>
89
118
  )}
119
+ {loadingMetaStatus === 'loading' && (
120
+ <LoaderContainer className="loader">
121
+ <Spinner size={24} />
122
+ </LoaderContainer>
123
+ )}
124
+ {loadingMetaStatus === 'failed' && <LoadingFailedAlert />}
90
125
  <ListContainer>
91
- {sortedWallets.map((wallet, index) => (
92
- <Wallet
93
- {...wallet}
94
- key={`${index}-${wallet.type}`}
95
- onClick={onSelectWallet}
96
- />
97
- ))}
126
+ {loadingMetaStatus === 'success' &&
127
+ sortedWallets.map((wallet, index) => (
128
+ <Wallet
129
+ {...wallet}
130
+ key={`${index}-${wallet.type}`}
131
+ onClick={onSelectWallet}
132
+ />
133
+ ))}
98
134
  </ListContainer>
99
135
  </>
100
136
  </SecondaryPage>
@@ -13,10 +13,15 @@ import { httpService } from '../services/httpService';
13
13
  import { useSettingsStore } from './settings';
14
14
  import { calcOutputUsdValue, createBestRouteRequestBody } from '../utils/swap';
15
15
  import { useMetaStore } from './meta';
16
- import { getDefaultToken, getSortedTokens } from '../utils/wallets';
16
+ import {
17
+ getDefaultToken,
18
+ getSortedTokens,
19
+ tokensAreEqual,
20
+ } from '../utils/wallets';
17
21
  import { useWalletsStore } from './wallets';
18
22
  import { TokenWithBalance } from '../pages/SelectTokenPage';
19
-
23
+ import { PendingSwap } from '@rango-dev/queue-manager-rango-preset/dist/shared';
24
+ import { debounce } from '../utils/common';
20
25
  const getUsdValue = (token: Token | null, amount: string) =>
21
26
  new BigNumber(amount || ZERO).multipliedBy(token?.usdPrice || 0);
22
27
 
@@ -43,6 +48,7 @@ export interface RouteState {
43
48
  setInputAmount: (amount: string) => void;
44
49
  bestRoute: BestRouteResponse | null;
45
50
  setBestRoute: (bestRoute: BestRouteResponse | null) => void;
51
+ retry: (pendingSwap: PendingSwap) => void;
46
52
  }
47
53
 
48
54
  export const useBestRouteStore = createSelectors(
@@ -65,6 +71,7 @@ export const useBestRouteStore = createSelectors(
65
71
  set((state) => {
66
72
  let outputAmount: BigNumber | null = null;
67
73
  let outputUsdValue: BigNumber = ZERO;
74
+ if (!state.inputAmount || state.inputAmount === '0') return {};
68
75
  if (!!bestRoute) {
69
76
  outputAmount = !!bestRoute.result?.outputAmount
70
77
  ? new BigNumber(bestRoute.result?.outputAmount)
@@ -139,6 +146,7 @@ export const useBestRouteStore = createSelectors(
139
146
  toToken: token,
140
147
  })),
141
148
  setInputAmount: (amount) => {
149
+ console.log(amount, typeof amount);
142
150
  set((state) => ({
143
151
  inputAmount: amount,
144
152
  ...(!amount && {
@@ -151,6 +159,71 @@ export const useBestRouteStore = createSelectors(
151
159
  }),
152
160
  }));
153
161
  },
162
+ retry: (pendingSwap) => {
163
+ const { tokens, blockchains } = useMetaStore.getState().meta;
164
+ const balances = useWalletsStore.getState().balances;
165
+ const failedIndex =
166
+ pendingSwap.status === 'failed'
167
+ ? pendingSwap.steps.findIndex((s) => s.status === 'failed')
168
+ : null;
169
+
170
+ if (failedIndex === null || failedIndex < 0) return;
171
+
172
+ const firstStep = pendingSwap.steps[0];
173
+ const lastStep = pendingSwap.steps[pendingSwap.steps.length - 1];
174
+ const fromChain =
175
+ blockchains.find(
176
+ (blockchain) => blockchain.name === firstStep.fromBlockchain
177
+ ) || null;
178
+ const toChain =
179
+ blockchains.find(
180
+ (blockchain) => blockchain.name === lastStep.toBlockchain
181
+ ) || null;
182
+
183
+ const fromToken = tokens.find((token) =>
184
+ tokensAreEqual(token, {
185
+ blockchain: firstStep.fromBlockchain,
186
+ symbol: firstStep.fromSymbol,
187
+ address: firstStep.fromSymbolAddress,
188
+ })
189
+ );
190
+
191
+ const toToken = tokens.find((token) =>
192
+ tokensAreEqual(token, {
193
+ blockchain: lastStep.toBlockchain,
194
+ symbol: lastStep.toSymbol,
195
+ address: lastStep.toSymbolAddress,
196
+ })
197
+ );
198
+ const sortedSourceTokens = getSortedTokens(
199
+ fromChain,
200
+ tokens,
201
+ balances,
202
+ []
203
+ );
204
+ const sortedDestinationTokens = getSortedTokens(
205
+ toChain,
206
+ tokens,
207
+ balances,
208
+ []
209
+ );
210
+ const inputAmount = pendingSwap.inputAmount;
211
+ set({
212
+ fromChain,
213
+ fromToken,
214
+ inputAmount,
215
+ outputAmount: null,
216
+ inputUsdValue: getUsdValue(fromToken || null, inputAmount),
217
+ outputUsdValue: new BigNumber(0),
218
+ toChain,
219
+ toToken,
220
+ bestRoute: null,
221
+ loading: false,
222
+ error: '',
223
+ sourceTokens: sortedSourceTokens,
224
+ destinationTokens: sortedDestinationTokens,
225
+ });
226
+ },
154
227
  }))
155
228
  )
156
229
  );
@@ -164,7 +237,7 @@ const bestRoute = (
164
237
  const { fromToken, toToken, inputAmount } = bestRouteStore.getState();
165
238
  const { slippage, customSlippage, disabledLiquiditySources } =
166
239
  settingsStore.getState();
167
- if (!fromToken || !toToken || !inputAmount) return;
240
+ if (!fromToken || !toToken || !inputAmount || inputAmount === '0') return;
168
241
  abortController?.abort();
169
242
  abortController = new AbortController();
170
243
  const userSlippage = !!customSlippage ? customSlippage : slippage;
@@ -178,12 +251,13 @@ const bestRoute = (
178
251
  userSlippage,
179
252
  false
180
253
  );
181
- bestRouteStore.setState({
182
- loading: true,
183
- bestRoute: null,
184
- outputAmount: null,
185
- outputUsdValue: new BigNumber(0),
186
- });
254
+ if (!bestRouteStore.getState().loading)
255
+ bestRouteStore.setState({
256
+ loading: true,
257
+ bestRoute: null,
258
+ outputAmount: null,
259
+ outputUsdValue: new BigNumber(0),
260
+ });
187
261
  httpService
188
262
  .getBestRoute(requestBody, {
189
263
  signal: abortController.signal,
@@ -203,6 +277,31 @@ const bestRoute = (
203
277
  });
204
278
  };
205
279
 
280
+ const debouncedFetchBestRoute = debounce(fetchBestRoute, 600);
281
+
282
+ const bestRouteParamsListener = () => {
283
+ const { fromToken, toToken, inputAmount, inputUsdValue } =
284
+ useBestRouteStore.getState();
285
+ if (!inputAmount || inputAmount === '0') return;
286
+
287
+ if (tokensAreEqual(fromToken, toToken))
288
+ return bestRouteStore.setState({
289
+ loading: false,
290
+ bestRoute: null,
291
+ outputAmount: new BigNumber(inputAmount),
292
+ outputUsdValue: inputUsdValue,
293
+ });
294
+
295
+ if (!bestRouteStore.getState().loading)
296
+ bestRouteStore.setState({
297
+ loading: true,
298
+ bestRoute: null,
299
+ outputAmount: null,
300
+ outputUsdValue: new BigNumber(0),
301
+ });
302
+ debouncedFetchBestRoute();
303
+ };
304
+
206
305
  useBestRouteStore.subscribe(
207
306
  (state) => ({
208
307
  fromChain: state.fromChain,
@@ -211,8 +310,7 @@ const bestRoute = (
211
310
  toToken: state.toToken,
212
311
  inputAmount: state.inputAmount,
213
312
  }),
214
-
215
- fetchBestRoute.bind(null),
313
+ bestRouteParamsListener,
216
314
  {
217
315
  equalityFn: (prevState, state) => {
218
316
  if (isRouteParametersChanged(prevState, state)) return false;
@@ -227,7 +325,7 @@ const bestRoute = (
227
325
  customSlippage: state.customSlippage,
228
326
  disabledLiquiditySources: state.disabledLiquiditySources,
229
327
  }),
230
- fetchBestRoute.bind(null),
328
+ bestRouteParamsListener,
231
329
  {
232
330
  equalityFn: (prevState, state) => {
233
331
  if (isRouteParametersChanged(prevState, state)) return false;
package/src/store/ui.ts CHANGED
@@ -4,18 +4,22 @@ import createSelectors from './selectors';
4
4
  interface UiState {
5
5
  connectWalletsButtonDisabled: boolean;
6
6
  selectedSwapRequestId: string | null;
7
+ currentPage: string;
7
8
  toggleConnectWalletsButton: () => void;
8
9
  setSelectedSwap: (requestId: string | null) => void;
10
+ setCurrentPage: (path: string) => void;
9
11
  }
10
12
 
11
13
  export const useUiStore = createSelectors(
12
14
  create<UiState>()((set) => ({
13
15
  connectWalletsButtonDisabled: false,
14
16
  selectedSwapRequestId: null,
17
+ currentPage: '',
15
18
  toggleConnectWalletsButton: () =>
16
19
  set((state) => ({
17
20
  connectWalletsButtonDisabled: !state.connectWalletsButtonDisabled,
18
21
  })),
19
22
  setSelectedSwap: (requestId) => set({ selectedSwapRequestId: requestId }),
23
+ setCurrentPage: (path) => set({ currentPage: path }),
20
24
  }))
21
25
  );
@@ -142,7 +142,7 @@ export const useWalletsStore = createSelectors(
142
142
  }
143
143
  });
144
144
  return {
145
- selectedWallets: state.selectedWallets.concat(selectedWallets),
145
+ selectedWallets: selectedWallets,
146
146
  };
147
147
  }),
148
148
  setSelectedWallet: (wallet) =>
@@ -188,3 +188,6 @@ useWalletsStore.subscribe(
188
188
  equalityFn: shallow,
189
189
  }
190
190
  );
191
+
192
+ export const fetchingBalanceSelector = (state: WalletsStore) =>
193
+ !!state.balances.find((wallet) => wallet.loading);
@@ -26,7 +26,7 @@ export type ConfirmSwapError =
26
26
  }
27
27
  | {
28
28
  type: ConfirmSwapErrorTypes.INSUFFICIENT_SLIPPAGE;
29
- minRequiredSlippage: number | null;
29
+ minRequiredSlippage: string | null;
30
30
  }
31
31
  | {
32
32
  type: Exclude<
package/src/types/swap.ts CHANGED
@@ -11,3 +11,10 @@ export type SwapButtonState = (
11
11
  ) & {
12
12
  title: string;
13
13
  };
14
+
15
+ export type ConvertedToken = {
16
+ symbol: string;
17
+ address: string | null;
18
+ blockchain: string;
19
+ outputAmount: string | null;
20
+ } | null;
@@ -33,3 +33,17 @@ export function shadeColor(color: string, percent: number) {
33
33
 
34
34
  return '#' + RR + GG + BB;
35
35
  }
36
+
37
+ export function debounce(fn: Function, time: number) {
38
+ let timeoutId: ReturnType<typeof setTimeout> | null;
39
+ return wrapper;
40
+ function wrapper(...args: any) {
41
+ if (timeoutId) {
42
+ clearTimeout(timeoutId);
43
+ }
44
+ timeoutId = setTimeout(() => {
45
+ timeoutId = null;
46
+ fn(...args);
47
+ }, time);
48
+ }
49
+ }
@@ -0,0 +1,62 @@
1
+ import { PendingSwap } from '@rango-dev/queue-manager-rango-preset';
2
+ import dayjs from 'dayjs';
3
+ import { GroupBy } from '@rango-dev/ui';
4
+
5
+ export const groupSwapsByDate: GroupBy = swaps => {
6
+ const output: Map<
7
+ string,
8
+ {
9
+ title: string;
10
+ swaps: PendingSwap[];
11
+ }
12
+ > = new Map([
13
+ [
14
+ 'today',
15
+ {
16
+ title: 'Today',
17
+ swaps: [],
18
+ },
19
+ ],
20
+ [
21
+ 'week',
22
+ {
23
+ title: 'This week',
24
+ swaps: [],
25
+ },
26
+ ],
27
+ [
28
+ 'month',
29
+ {
30
+ title: 'This month',
31
+ swaps: [],
32
+ },
33
+ ],
34
+ [
35
+ 'year',
36
+ {
37
+ title: 'This year',
38
+ swaps: [],
39
+ },
40
+ ],
41
+ [
42
+ 'history',
43
+ {
44
+ title: 'History',
45
+ swaps: [],
46
+ },
47
+ ],
48
+ ]);
49
+
50
+ const now = dayjs();
51
+ swaps.forEach(swap => {
52
+ const swapDate = dayjs(Number(swap.creationTime));
53
+ if (now.isSame(swapDate, 'day')) output.get('today')?.swaps.push(swap);
54
+ else if (now.isSame(swapDate, 'week')) output.get('week')?.swaps.push(swap);
55
+ else if (now.isSame(swapDate, 'month'))
56
+ output.get('month')?.swaps.push(swap);
57
+ else if (now.isSame(swapDate, 'year')) output.get('year')?.swaps.push(swap);
58
+ else output.get('history')?.swaps.push(swap);
59
+ });
60
+
61
+ return Array.from(output.values());
62
+ };
@@ -117,19 +117,22 @@ export function isRouteParametersChanged(
117
117
  currentParams: BestRouteParams
118
118
  ) {
119
119
  return (
120
- prevParams.fromChain?.name !== currentParams.fromChain?.name ||
121
- prevParams.toChain?.name !== currentParams.toChain?.name ||
122
- prevParams.fromToken?.symbol !== currentParams.fromToken?.symbol ||
123
- prevParams.toToken?.symbol !== currentParams.toToken?.symbol ||
124
- prevParams.fromToken?.blockchain !== currentParams.fromToken?.blockchain ||
125
- prevParams.toToken?.blockchain !== currentParams.toToken?.blockchain ||
126
- prevParams.fromToken?.address !== currentParams.fromToken?.address ||
127
- prevParams.toToken?.address !== currentParams.toToken?.address ||
128
- prevParams.inputAmount !== currentParams.inputAmount ||
129
- prevParams.slippage !== currentParams.slippage ||
130
- prevParams.customSlippage !== currentParams.customSlippage ||
131
- prevParams.disabledLiquiditySources?.length !==
132
- currentParams.disabledLiquiditySources?.length
120
+ !!currentParams.fromToken &&
121
+ !!currentParams.toToken &&
122
+ (prevParams.fromChain?.name !== currentParams.fromChain?.name ||
123
+ prevParams.toChain?.name !== currentParams.toChain?.name ||
124
+ prevParams.fromToken?.symbol !== currentParams.fromToken?.symbol ||
125
+ prevParams.toToken?.symbol !== currentParams.toToken?.symbol ||
126
+ prevParams.fromToken?.blockchain !==
127
+ currentParams.fromToken?.blockchain ||
128
+ prevParams.toToken?.blockchain !== currentParams.toToken?.blockchain ||
129
+ prevParams.fromToken?.address !== currentParams.fromToken?.address ||
130
+ prevParams.toToken?.address !== currentParams.toToken?.address ||
131
+ prevParams.inputAmount !== currentParams.inputAmount ||
132
+ prevParams.slippage !== currentParams.slippage ||
133
+ prevParams.customSlippage !== currentParams.customSlippage ||
134
+ prevParams.disabledLiquiditySources?.length !==
135
+ currentParams.disabledLiquiditySources?.length)
133
136
  );
134
137
  }
135
138
 
@@ -148,3 +151,10 @@ export function getBestRouteWithCalculatedFees(
148
151
  result: { ...bestRoute.result, swaps: swapsWithFee },
149
152
  };
150
153
  }
154
+
155
+ //todo: refactor bestRoute store and add loadingStatus
156
+ export const getBestRouteStatus = (loading: boolean, error: boolean) => {
157
+ if (loading) return 'loading';
158
+ if (error) return 'failed';
159
+ else return 'success';
160
+ };
package/src/utils/swap.ts CHANGED
@@ -1,4 +1,3 @@
1
- import { PendingSwap } from '@rango-dev/ui/dist/containers/History/types';
2
1
  import {
3
2
  WalletTypeAndAddress,
4
3
  SwapSavedSettings,
@@ -19,7 +18,12 @@ import { WalletType } from '@rango-dev/wallets-shared';
19
18
  import { getRequiredBalanceOfWallet } from './routing';
20
19
  import { getRequiredChains, SelectedWallet } from './wallets';
21
20
  import { LoadingStatus } from '../store/meta';
22
- import { SwapButtonState } from '../types';
21
+ import { ConvertedToken, SwapButtonState } from '../types';
22
+ import {
23
+ PendingSwapNetworkStatus,
24
+ PendingSwapStep,
25
+ } from '@rango-dev/queue-manager-rango-preset';
26
+ import { PendingSwap } from '@rango-dev/queue-manager-rango-preset';
23
27
 
24
28
  export function getOutputRatio(
25
29
  inputUsdValue: BigNumber,
@@ -187,6 +191,7 @@ export function calculatePendingSwap(
187
191
  finishTime: null,
188
192
  requestId: bestRoute.requestId || '',
189
193
  inputAmount: inputAmount,
194
+ //@ts-ignore
190
195
  wallets,
191
196
  status: 'running',
192
197
  isPaused: false,
@@ -201,6 +206,7 @@ export function calculatePendingSwap(
201
206
  settings: settings,
202
207
  simulationResult: simulationResult,
203
208
  validateBalanceOrFee,
209
+ //@ts-ignore
204
210
  steps:
205
211
  bestRoute.result?.swaps?.map((swap, index) => {
206
212
  const swapper = meta.swappers.find(
@@ -339,25 +345,24 @@ export function hasSlippageError(
339
345
 
340
346
  export function getMinRequiredSlippage(
341
347
  route: BestRouteResponse
342
- ): number | null {
348
+ ): string | null {
343
349
  const slippages = route.result?.swaps.map(
344
350
  (slippage) => slippage.recommendedSlippage
345
351
  );
346
352
  return (
347
353
  slippages
348
- ?.map((s) => parseFloat(s?.slippage || '0'))
349
- ?.filter((s) => s > 0)
350
- ?.sort((a, b) => b - a)
354
+ ?.map((s) => s?.slippage || '0')
355
+ ?.filter((s) => parseFloat(s) > 0)
356
+ ?.sort((a, b) => parseFloat(b) - parseFloat(a))
351
357
  ?.find(() => true) || null
352
358
  );
353
359
  }
354
360
 
355
361
  export function hasProperSlippage(
356
362
  userSlippage: string,
357
- minRequiredSlippage: number | null
363
+ minRequiredSlippage: string | null
358
364
  ) {
359
365
  if (!minRequiredSlippage) return true;
360
- //@ts-ignore
361
366
  return parseFloat(userSlippage) >= parseFloat(minRequiredSlippage);
362
367
  }
363
368
 
@@ -386,7 +391,7 @@ export function hasEnoughBalanceAndProperSlippage(
386
391
  route: BestRouteResponse,
387
392
  selectedWallets: SelectedWallet[],
388
393
  userSlippage: string,
389
- minRequiredSlippage: number | null
394
+ minRequiredSlippage: string | null
390
395
  ): boolean {
391
396
  return (
392
397
  hasEnoughBalance(route, selectedWallets) &&
@@ -429,6 +434,8 @@ export function createBestRouteRequestBody(
429
434
  });
430
435
  });
431
436
 
437
+ const filteredBlockchains = selectedWallets.map((wallet) => wallet.chain);
438
+
432
439
  const requestBody: BestRouteRequest = {
433
440
  amount: inputAmount.toString(),
434
441
  checkPrerequisites,
@@ -446,8 +453,8 @@ export function createBestRouteRequestBody(
446
453
  selectedWallets: selectedWalletsMap,
447
454
  swapperGroups: disabledLiquiditySources,
448
455
  swappersGroupsExclude: true,
449
- //@ts-ignore
450
456
  slippage: slippage.toString(),
457
+ ...(checkPrerequisites && { blockchains: filteredBlockchains }),
451
458
  };
452
459
 
453
460
  return requestBody;
@@ -550,3 +557,87 @@ export function calcOutputUsdValue(
550
557
 
551
558
  return amount.multipliedBy(tokenPrice || 0);
552
559
  }
560
+
561
+ export function isNetworkStatusInWarningState(
562
+ pendingSwapStep: PendingSwapStep | null
563
+ ): boolean {
564
+ return (
565
+ !!pendingSwapStep &&
566
+ pendingSwapStep.networkStatus !== null &&
567
+ pendingSwapStep.networkStatus !== PendingSwapNetworkStatus.NetworkChanged
568
+ );
569
+ }
570
+
571
+ export function getSwapMessages(
572
+ pendingSwap: PendingSwap,
573
+ currentStep: PendingSwapStep | null
574
+ ): {
575
+ shortMessage: string;
576
+ detailedMessage: { content: string; long: boolean };
577
+ } {
578
+ const textForRemove = 'bellow button or';
579
+ let message = pendingSwap.extraMessage;
580
+ let detailedMessage = pendingSwap.extraMessageDetail;
581
+
582
+ if (pendingSwap.networkStatusExtraMessageDetail?.includes(textForRemove)) {
583
+ pendingSwap.networkStatusExtraMessageDetail =
584
+ pendingSwap.networkStatusExtraMessageDetail.replace(textForRemove, '');
585
+ }
586
+
587
+ const networkWarningState = isNetworkStatusInWarningState(currentStep);
588
+
589
+ if (networkWarningState) {
590
+ message = pendingSwap.networkStatusExtraMessage || '';
591
+ detailedMessage = pendingSwap.networkStatusExtraMessageDetail || '';
592
+ switch (currentStep?.networkStatus) {
593
+ case PendingSwapNetworkStatus.WaitingForConnectingWallet:
594
+ message = message || 'Waiting for connecting wallet';
595
+ break;
596
+ case PendingSwapNetworkStatus.WaitingForQueue:
597
+ message = message || 'Waiting for other running tasks to be finished';
598
+ break;
599
+ case PendingSwapNetworkStatus.WaitingForNetworkChange:
600
+ message = message || 'Waiting for changing wallet network';
601
+ break;
602
+ }
603
+ }
604
+ detailedMessage = detailedMessage || '';
605
+ message = message || '';
606
+ const isRpc =
607
+ message?.indexOf('code') !== -1 && message?.indexOf('reason') !== -1;
608
+
609
+ return {
610
+ shortMessage: message,
611
+ detailedMessage: { content: detailedMessage, long: isRpc },
612
+ };
613
+ }
614
+
615
+ export function getLastConvertedTokenInFailedSwap(
616
+ pendingSwap: PendingSwap
617
+ ): ConvertedToken {
618
+ let resultToken: ConvertedToken = null;
619
+ if (pendingSwap.status === 'failed') {
620
+ const lastSuccessStep = pendingSwap.steps
621
+ .slice()
622
+ .reverse()
623
+ .filter((step) => step.status === 'success')[0];
624
+
625
+ if (lastSuccessStep) {
626
+ resultToken = {
627
+ blockchain: lastSuccessStep.toBlockchain,
628
+ symbol: lastSuccessStep.toSymbol,
629
+ outputAmount: lastSuccessStep.outputAmount,
630
+ address: lastSuccessStep.toSymbolAddress,
631
+ };
632
+ }
633
+ }
634
+ return resultToken;
635
+ }
636
+
637
+ export function shouldRetrySwap(pendingSwap: PendingSwap) {
638
+ return (
639
+ pendingSwap.status === 'failed' &&
640
+ !!pendingSwap.finishTime &&
641
+ new Date().getTime() - parseInt(pendingSwap.finishTime) < 4 * 3600 * 1000
642
+ );
643
+ }