@0xsquid/react-hooks 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.babelrc +7 -0
- package/.eslintignore +1 -0
- package/.eslintrc.json +44 -0
- package/dist/index.js +6 -0
- package/jest.config.ts +28 -0
- package/package.json +124 -0
- package/scripts/copyAssets.js +27 -0
- package/scripts/removeBuildTestFolder.js +28 -0
- package/scripts/replacePaths.js +37 -0
- package/src/assets/images/icons/wallets/binance.svg +4 -0
- package/src/assets/images/icons/wallets/bitget.svg +43 -0
- package/src/assets/images/icons/wallets/bitkeep.svg +9 -0
- package/src/assets/images/icons/wallets/blockchaindotcom.svg +11 -0
- package/src/assets/images/icons/wallets/brave.svg +18 -0
- package/src/assets/images/icons/wallets/c98.svg +3 -0
- package/src/assets/images/icons/wallets/coinbase.svg +5 -0
- package/src/assets/images/icons/wallets/cosmostation.svg +9 -0
- package/src/assets/images/icons/wallets/defiConnect.svg +25 -0
- package/src/assets/images/icons/wallets/exodus.svg +33 -0
- package/src/assets/images/icons/wallets/fetchai.svg +1 -0
- package/src/assets/images/icons/wallets/index.ts +43 -0
- package/src/assets/images/icons/wallets/keplr.svg +9 -0
- package/src/assets/images/icons/wallets/leap.svg +35 -0
- package/src/assets/images/icons/wallets/metamask.svg +48 -0
- package/src/assets/images/icons/wallets/okx.svg +1 -0
- package/src/assets/images/icons/wallets/rabby.svg +1 -0
- package/src/assets/images/icons/wallets/trustwallet.svg +11 -0
- package/src/assets/images/icons/wallets/walletConnect.svg +11 -0
- package/src/assets/images/icons/wallets/wallet_icon.svg +1 -0
- package/src/assets/images/icons/wallets/xdefi.svg +9 -0
- package/src/assets/images/icons/wallets/zerion.svg +11 -0
- package/src/connectors/ExodusConnector.ts +6 -0
- package/src/connectors/LedgerLiveConnector.ts +226 -0
- package/src/contracts/typechain/ERC20.d.ts +441 -0
- package/src/contracts/typechain/factories/ERC20__factory.d.ts +56 -0
- package/src/contracts/typechain/factories/ERC20__factory.ts +340 -0
- package/src/core/constants.ts +549 -0
- package/src/core/externalLinks.ts +26 -0
- package/src/core/index.ts +1 -0
- package/src/core/multicall3.ts +22 -0
- package/src/core/numbers.ts +44 -0
- package/src/core/providers/CosmosProvider.tsx +55 -0
- package/src/core/queries/queries-keys.ts +156 -0
- package/src/core/queries/react-query-config.ts +13 -0
- package/src/core/types/components.ts +16 -0
- package/src/core/types/config.ts +52 -0
- package/src/core/types/dex.ts +31 -0
- package/src/core/types/error.ts +52 -0
- package/src/core/types/event.ts +16 -0
- package/src/core/types/route.ts +21 -0
- package/src/core/types/swap.ts +8 -0
- package/src/core/types/tokens.ts +30 -0
- package/src/core/types/transaction.ts +84 -0
- package/src/core/types/types.ts +37 -0
- package/src/core/types/wallet.ts +83 -0
- package/src/hooks/chains/useSquidChains.ts +66 -0
- package/src/hooks/cosmos/useCosmos.ts +279 -0
- package/src/hooks/cosmos/useCosmosForChain.ts +33 -0
- package/src/hooks/index.ts +32 -0
- package/src/hooks/navigation/useKeyboardNavigation.ts +88 -0
- package/src/hooks/store/useSquidStore.ts +80 -0
- package/src/hooks/swap/useSwap.ts +359 -0
- package/src/hooks/tokens/useAllTokensWithBalance.ts +157 -0
- package/src/hooks/tokens/useBalance.ts +180 -0
- package/src/hooks/tokens/useMultiChainBalance.ts +59 -0
- package/src/hooks/tokens/usePrices.ts +52 -0
- package/src/hooks/tokens/useSingleTokenPrice.ts +45 -0
- package/src/hooks/tokens/useSquidTokens.ts +48 -0
- package/src/hooks/tokens/useTokensWithBalance.ts +169 -0
- package/src/hooks/transaction/useEstimate.ts +397 -0
- package/src/hooks/transaction/useEstimatePriceImpact.ts +39 -0
- package/src/hooks/transaction/useExecuteTransaction.ts +440 -0
- package/src/hooks/transaction/useExpress.ts +46 -0
- package/src/hooks/transaction/useGetRoute.ts +145 -0
- package/src/hooks/transaction/useSingleTransaction.ts +155 -0
- package/src/hooks/transaction/useTransaction.ts +734 -0
- package/src/hooks/user/useUserParams.ts +63 -0
- package/src/hooks/wallet/useAddToken.ts +53 -0
- package/src/hooks/wallet/useAutoConnect.ts +56 -0
- package/src/hooks/wallet/useGnosisContext.ts +84 -0
- package/src/hooks/wallet/useIntegratorContext.ts +44 -0
- package/src/hooks/wallet/useMultiChainWallet.ts +146 -0
- package/src/hooks/wallet/useWallet.ts +86 -0
- package/src/hooks/webapp-router/useSquidRouter.ts +42 -0
- package/src/index.ts +5 -0
- package/src/provider/index.tsx +105 -0
- package/src/react-app-env.d.ts +2 -0
- package/src/services/external/analyticsService.ts +46 -0
- package/src/services/external/coingeckoService.ts +35 -0
- package/src/services/external/rpcService.ts +196 -0
- package/src/services/external/secretService.ts +178 -0
- package/src/services/index.ts +1 -0
- package/src/services/internal/apiService.ts +6 -0
- package/src/services/internal/assetsService.ts +84 -0
- package/src/services/internal/configService.ts +261 -0
- package/src/services/internal/errorService.ts +124 -0
- package/src/services/internal/eventService.ts +93 -0
- package/src/services/internal/priceService.ts +10 -0
- package/src/services/internal/transactionService.ts +255 -0
- package/src/services/internal/transactionStatusService.ts +293 -0
- package/src/services/internal/walletService.ts +158 -0
- package/src/tests/assetsService.test.ts +176 -0
- package/src/tests/configService.test.ts +486 -0
- package/src/tests/fetchSquidData.ts +43 -0
- package/src/tests/jest-svg-transform.ts +19 -0
- package/src/tests/sample.json +0 -0
- package/src/tests/walletService.test.ts +178 -0
- package/tsconfig.json +30 -0
|
@@ -0,0 +1,261 @@
|
|
|
1
|
+
import { defaultValues } from "@/core/constants";
|
|
2
|
+
import type { AppConfig } from "@/core/types/config";
|
|
3
|
+
import type { ChainData, Token } from "@0xsquid/sdk/dist/types";
|
|
4
|
+
import { ChainType } from "@0xsquid/sdk/dist/types";
|
|
5
|
+
import get from "lodash/get";
|
|
6
|
+
import { shareSubgraphId } from "./assetsService";
|
|
7
|
+
|
|
8
|
+
export const getConfigWithDefaults = (
|
|
9
|
+
config: AppConfig | undefined
|
|
10
|
+
): AppConfig => {
|
|
11
|
+
return {
|
|
12
|
+
integratorId: get(
|
|
13
|
+
config,
|
|
14
|
+
"integratorId",
|
|
15
|
+
defaultValues.config.integratorId
|
|
16
|
+
),
|
|
17
|
+
companyName: get(config, "companyName", defaultValues.config.companyName),
|
|
18
|
+
slippage: get(config, "slippage", defaultValues.config.slippage),
|
|
19
|
+
advanced: get(config, "advanced", defaultValues.config.advanced),
|
|
20
|
+
internalSameChainSwapAllowed: get(
|
|
21
|
+
config,
|
|
22
|
+
"internalSameChainSwapAllowed",
|
|
23
|
+
defaultValues.config.internalSameChainSwapAllowed
|
|
24
|
+
),
|
|
25
|
+
hideAnimations: get(
|
|
26
|
+
config,
|
|
27
|
+
"hideAnimations",
|
|
28
|
+
defaultValues.config.hideAnimations
|
|
29
|
+
),
|
|
30
|
+
infiniteApproval: get(
|
|
31
|
+
config,
|
|
32
|
+
"infiniteApproval",
|
|
33
|
+
defaultValues.config.infiniteApproval
|
|
34
|
+
),
|
|
35
|
+
enableExpress: get(
|
|
36
|
+
config,
|
|
37
|
+
"enableExpress",
|
|
38
|
+
defaultValues.config.enableExpress
|
|
39
|
+
),
|
|
40
|
+
collectFees: get(config, "collectFees", defaultValues.config.collectFees),
|
|
41
|
+
enableGetGasOnDestination: get(
|
|
42
|
+
config,
|
|
43
|
+
"enableGetGasOnDestination",
|
|
44
|
+
defaultValues.config.enableGetGasOnDestination
|
|
45
|
+
),
|
|
46
|
+
apiUrl: get(config, "apiUrl", defaultValues.config.apiUrl),
|
|
47
|
+
showOnRampLink: get(
|
|
48
|
+
config,
|
|
49
|
+
"showOnRampLink",
|
|
50
|
+
defaultValues.config.showOnRampLink
|
|
51
|
+
),
|
|
52
|
+
priceImpactWarnings: get(
|
|
53
|
+
config,
|
|
54
|
+
"priceImpactWarnings",
|
|
55
|
+
defaultValues.config.priceImpactWarnings
|
|
56
|
+
),
|
|
57
|
+
initialAssets: get(
|
|
58
|
+
config,
|
|
59
|
+
"initialAssets",
|
|
60
|
+
defaultValues.config.initialAssets
|
|
61
|
+
),
|
|
62
|
+
defaultTokensPerChain: get(
|
|
63
|
+
config,
|
|
64
|
+
"defaultTokensPerChain",
|
|
65
|
+
defaultValues.config.defaultTokensPerChain
|
|
66
|
+
),
|
|
67
|
+
preferDex: get(config, "preferDex", defaultValues.config.preferDex),
|
|
68
|
+
favTokens: get(config, "favTokens", defaultValues.config.favTokens),
|
|
69
|
+
comingSoonChainIds: get(
|
|
70
|
+
config,
|
|
71
|
+
"comingSoonChainIds",
|
|
72
|
+
defaultValues.config.comingSoonChainIds
|
|
73
|
+
),
|
|
74
|
+
availableChains: get(
|
|
75
|
+
config,
|
|
76
|
+
"availableChains",
|
|
77
|
+
defaultValues.config.availableChains
|
|
78
|
+
),
|
|
79
|
+
onChainQuoting: get(
|
|
80
|
+
config,
|
|
81
|
+
"onChainQuoting",
|
|
82
|
+
defaultValues.config.onChainQuoting
|
|
83
|
+
),
|
|
84
|
+
disabledChains: get(
|
|
85
|
+
config,
|
|
86
|
+
"disabledChains",
|
|
87
|
+
defaultValues.config.disabledChains
|
|
88
|
+
),
|
|
89
|
+
};
|
|
90
|
+
};
|
|
91
|
+
|
|
92
|
+
export const randomIntFromInterval = (min: number, max: number) => {
|
|
93
|
+
return Math.floor(Math.random() * (max - min + 1) + min);
|
|
94
|
+
};
|
|
95
|
+
|
|
96
|
+
export const getTokensForChain = (
|
|
97
|
+
tokens: Token[],
|
|
98
|
+
chainId: number | string | undefined
|
|
99
|
+
) => {
|
|
100
|
+
return chainId ? tokens.filter((t) => t.chainId === chainId) : tokens;
|
|
101
|
+
};
|
|
102
|
+
|
|
103
|
+
export const getFirstAvailableChainId = (
|
|
104
|
+
config: AppConfig,
|
|
105
|
+
direction: "from" | "to",
|
|
106
|
+
chains: ChainData[] | undefined = []
|
|
107
|
+
) => {
|
|
108
|
+
// available chains are those that are not coming soon or disabled chains
|
|
109
|
+
const availableChains = chains.filter(
|
|
110
|
+
(c) =>
|
|
111
|
+
!config.comingSoonChainIds?.find((id) => id === c.chainId) &&
|
|
112
|
+
!config.disabledChains?.[
|
|
113
|
+
direction === "from" ? "source" : "destination"
|
|
114
|
+
]?.some((id) => id === c.chainId)
|
|
115
|
+
);
|
|
116
|
+
|
|
117
|
+
if (
|
|
118
|
+
direction === "from" &&
|
|
119
|
+
config.initialAssets?.from &&
|
|
120
|
+
availableChains.some(
|
|
121
|
+
(c) => c.chainId === String(config.initialAssets?.from?.chainId)
|
|
122
|
+
)
|
|
123
|
+
) {
|
|
124
|
+
return config.initialAssets.from.chainId;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
if (
|
|
128
|
+
direction === "to" &&
|
|
129
|
+
config.initialAssets?.to &&
|
|
130
|
+
availableChains.some(
|
|
131
|
+
(c) => c.chainId === String(config.initialAssets?.to?.chainId)
|
|
132
|
+
)
|
|
133
|
+
) {
|
|
134
|
+
return config.initialAssets.to.chainId;
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
return availableChains.length > 0 ? availableChains[0].chainId : undefined;
|
|
138
|
+
};
|
|
139
|
+
|
|
140
|
+
export const getDefaultTokenAddressForChain = (
|
|
141
|
+
tokens: Token[],
|
|
142
|
+
config: AppConfig,
|
|
143
|
+
chainId: number | string | undefined,
|
|
144
|
+
unavailableTokenAddress?: string
|
|
145
|
+
): string | undefined => {
|
|
146
|
+
const chainIdDefaultToken = config.defaultTokensPerChain?.find(
|
|
147
|
+
(token) => token.chainId == chainId
|
|
148
|
+
);
|
|
149
|
+
|
|
150
|
+
if (
|
|
151
|
+
chainIdDefaultToken &&
|
|
152
|
+
chainIdDefaultToken.address !== unavailableTokenAddress
|
|
153
|
+
) {
|
|
154
|
+
return chainIdDefaultToken.address;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
const filteredTokens = chainId
|
|
158
|
+
? tokens.filter(
|
|
159
|
+
(t) => t.chainId === chainId && t.address !== unavailableTokenAddress
|
|
160
|
+
)
|
|
161
|
+
: tokens;
|
|
162
|
+
|
|
163
|
+
return filteredTokens.length > 0 ? filteredTokens[0].address : undefined;
|
|
164
|
+
};
|
|
165
|
+
|
|
166
|
+
/**
|
|
167
|
+
* Retrieves the initial token address for a specific chain and direction.
|
|
168
|
+
* If no initial assets are set in config, returns the default token address for the chain.
|
|
169
|
+
*
|
|
170
|
+
* @param tokens - The list of tokens.
|
|
171
|
+
* @param config - The application configuration.
|
|
172
|
+
* @param chainId - The ID of the chain.
|
|
173
|
+
* @param direction - The direction ("from" or "to").
|
|
174
|
+
* @returns The initial token address if found; otherwise, the default token address.
|
|
175
|
+
*/
|
|
176
|
+
export const getInitialOrDefaultTokenAddressForChain = ({
|
|
177
|
+
chainId,
|
|
178
|
+
config,
|
|
179
|
+
direction,
|
|
180
|
+
tokens,
|
|
181
|
+
unavailableTokenAddress,
|
|
182
|
+
}: {
|
|
183
|
+
tokens: Token[];
|
|
184
|
+
config: AppConfig;
|
|
185
|
+
chainId: number | string | undefined;
|
|
186
|
+
direction: "from" | "to";
|
|
187
|
+
unavailableTokenAddress?: string;
|
|
188
|
+
}): string | undefined => {
|
|
189
|
+
if (
|
|
190
|
+
direction === "from" &&
|
|
191
|
+
config.initialAssets?.from &&
|
|
192
|
+
config.initialAssets.from.chainId === chainId
|
|
193
|
+
) {
|
|
194
|
+
return config.initialAssets.from.address;
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
if (
|
|
198
|
+
direction === "to" &&
|
|
199
|
+
config.initialAssets?.to &&
|
|
200
|
+
config.initialAssets.to.chainId === chainId
|
|
201
|
+
) {
|
|
202
|
+
return config.initialAssets.to.address;
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
return getDefaultTokenAddressForChain(
|
|
206
|
+
tokens,
|
|
207
|
+
config,
|
|
208
|
+
chainId,
|
|
209
|
+
unavailableTokenAddress
|
|
210
|
+
);
|
|
211
|
+
};
|
|
212
|
+
|
|
213
|
+
/**
|
|
214
|
+
* Filter tokens for destination chain
|
|
215
|
+
*
|
|
216
|
+
* Case 1: fromToken.bridgeOnly = true
|
|
217
|
+
* Destination token list shows only tokens with the same commonKey as fromToken
|
|
218
|
+
*
|
|
219
|
+
* Case 2: fromToken.bridgeOnly = false
|
|
220
|
+
* Destination token list shows all tokens with bridgeOnly = false
|
|
221
|
+
* OR Destination token list shows all tokens with the same commonKey as fromToken
|
|
222
|
+
* @param tokens
|
|
223
|
+
* @param selectedDestinationChain
|
|
224
|
+
* @param selectedSourceChainID
|
|
225
|
+
* @param selectedSourceToken
|
|
226
|
+
* @returns
|
|
227
|
+
*/
|
|
228
|
+
export const filterTokensForDestination = <T extends Token>(
|
|
229
|
+
tokens: T[],
|
|
230
|
+
selectedDestinationChain: ChainData | undefined,
|
|
231
|
+
selectedSourceToken: Token | undefined
|
|
232
|
+
): T[] => {
|
|
233
|
+
let filteredTokens = [];
|
|
234
|
+
|
|
235
|
+
if (selectedSourceToken?.subGraphOnly) {
|
|
236
|
+
filteredTokens = tokens.filter(
|
|
237
|
+
(t) =>
|
|
238
|
+
shareSubgraphId(t, selectedSourceToken) &&
|
|
239
|
+
t.chainId === selectedDestinationChain?.chainId
|
|
240
|
+
);
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
filteredTokens = tokens.filter(
|
|
244
|
+
(t) => !t.subGraphOnly || shareSubgraphId(t, selectedSourceToken as Token)
|
|
245
|
+
);
|
|
246
|
+
|
|
247
|
+
// We don't want to show the same source token & chain in the destination list
|
|
248
|
+
// except for Cosmos swaps
|
|
249
|
+
return filteredTokens.filter((t) => {
|
|
250
|
+
const areSameToken =
|
|
251
|
+
t.address === selectedSourceToken?.address &&
|
|
252
|
+
t.chainId === selectedSourceToken.chainId;
|
|
253
|
+
|
|
254
|
+
// only return tokens that are on the same chain as the destination chain
|
|
255
|
+
const isValidChain = t.chainId === selectedDestinationChain?.chainId;
|
|
256
|
+
const isCosmosSwap =
|
|
257
|
+
selectedDestinationChain?.chainType === ChainType.COSMOS;
|
|
258
|
+
|
|
259
|
+
return isValidChain && (isCosmosSwap || !areSameToken);
|
|
260
|
+
});
|
|
261
|
+
};
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
import type {
|
|
2
|
+
SquidRouteError,
|
|
3
|
+
SquidStatusError,
|
|
4
|
+
TransactionError,
|
|
5
|
+
TransactionErrorWithMessage,
|
|
6
|
+
} from "@/core/types/error";
|
|
7
|
+
import { TransactionErrorType } from "@/core/types/error";
|
|
8
|
+
|
|
9
|
+
export const transactionErrorCode: Record<string, TransactionErrorWithMessage> =
|
|
10
|
+
{
|
|
11
|
+
// Metamask
|
|
12
|
+
ACTION_REJECTED: {
|
|
13
|
+
type: TransactionErrorType.REJECTED_BY_USER,
|
|
14
|
+
message: "Return to the swap page and try again.",
|
|
15
|
+
},
|
|
16
|
+
// Keplr
|
|
17
|
+
"Request rejected": {
|
|
18
|
+
type: TransactionErrorType.REJECTED_BY_USER,
|
|
19
|
+
message: "Return to the swap page and try again.",
|
|
20
|
+
},
|
|
21
|
+
// Metamask
|
|
22
|
+
4001: {
|
|
23
|
+
type: TransactionErrorType.REJECTED_BY_USER,
|
|
24
|
+
message: "Return to the swap page and try again.",
|
|
25
|
+
},
|
|
26
|
+
CALL_EXCEPTION: {
|
|
27
|
+
type: TransactionErrorType.CALL_EXCEPTION,
|
|
28
|
+
message:
|
|
29
|
+
"Swap failed on the source chain. Please let us know by submitting a ticket here.",
|
|
30
|
+
},
|
|
31
|
+
UNKNOWN: {
|
|
32
|
+
type: TransactionErrorType.UNKNOWN,
|
|
33
|
+
message: "The transaction could not be initiated.",
|
|
34
|
+
},
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* Check if the error is an EVM transaction error
|
|
39
|
+
* Because Typescript supports casting but that's only for compilation time,
|
|
40
|
+
* We need it at runtime since we're getting the error object from the wallet
|
|
41
|
+
* @param error
|
|
42
|
+
* @returns boolean
|
|
43
|
+
*/
|
|
44
|
+
export const isTransactionError = (error: any): error is TransactionError => {
|
|
45
|
+
return (
|
|
46
|
+
error &&
|
|
47
|
+
(typeof error.code === "string" ||
|
|
48
|
+
typeof error.code === "number" ||
|
|
49
|
+
typeof error.message === "string" ||
|
|
50
|
+
typeof error.reason === "string" ||
|
|
51
|
+
typeof error.action === "string")
|
|
52
|
+
);
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Return the error from enum entry
|
|
57
|
+
* @param error
|
|
58
|
+
* @returns boolean
|
|
59
|
+
*/
|
|
60
|
+
export const getTransactionError = (
|
|
61
|
+
error: any
|
|
62
|
+
): TransactionErrorWithMessage => {
|
|
63
|
+
if (isTransactionError(error)) {
|
|
64
|
+
const castError = error as TransactionError;
|
|
65
|
+
if (castError.code) return transactionErrorCode[castError.code];
|
|
66
|
+
if (castError.message) return transactionErrorCode[castError.message];
|
|
67
|
+
return transactionErrorCode.UNKNOWN;
|
|
68
|
+
}
|
|
69
|
+
return transactionErrorCode.UNKNOWN;
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
// --------------------
|
|
73
|
+
// SQUID ROUTE ERRORS
|
|
74
|
+
// --------------------
|
|
75
|
+
// TODO: Components will be handled outside hooks lib
|
|
76
|
+
// const squidRouteErrorMapping: Record<
|
|
77
|
+
// SquidRouteErrorType,
|
|
78
|
+
// string | JSX.Element
|
|
79
|
+
// > = {
|
|
80
|
+
// Unknown: RouteDefaultErrorMsg(),
|
|
81
|
+
// UnknownError: RouteDefaultErrorMsg(),
|
|
82
|
+
// SquidServiceError: RouteDefaultErrorMsg(),
|
|
83
|
+
// };
|
|
84
|
+
|
|
85
|
+
/**
|
|
86
|
+
* Check if the error is an Squid route error
|
|
87
|
+
* Because Typescript supports casting but that's only for compilation time,
|
|
88
|
+
* We need it at runtime since we're getting the error object from the wallet
|
|
89
|
+
* @param error
|
|
90
|
+
* @returns boolean
|
|
91
|
+
*/
|
|
92
|
+
export const isSwapRouteError = (error: any): error is SquidRouteError => {
|
|
93
|
+
return (
|
|
94
|
+
error &&
|
|
95
|
+
(typeof error.code === "string" || typeof error.errorType === "string")
|
|
96
|
+
);
|
|
97
|
+
};
|
|
98
|
+
|
|
99
|
+
export const isStatusError = (error: any): error is SquidStatusError => {
|
|
100
|
+
return error && typeof error.errorType === "string";
|
|
101
|
+
};
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Tries to parse as SquidRouteError Type & Return the error from Record entries
|
|
105
|
+
* @param error
|
|
106
|
+
* @returns string error message
|
|
107
|
+
*/
|
|
108
|
+
// TODO: move this outside hooks
|
|
109
|
+
// export const getSquidRouteErrorMessage = (error: any): string | JSX.Element => {
|
|
110
|
+
// if (isSwapRouteError(error)) {
|
|
111
|
+
// // Try to get the error message from the error code
|
|
112
|
+
// const codeMsg =
|
|
113
|
+
// error.code || error.errorType
|
|
114
|
+
// ? squidRouteErrorMapping[
|
|
115
|
+
// (error.code ?? error.errorType) as SquidRouteErrorType
|
|
116
|
+
// ]
|
|
117
|
+
// : undefined;
|
|
118
|
+
|
|
119
|
+
// if (codeMsg) return codeMsg;
|
|
120
|
+
// // If there is no error code, try to get the error message from backend
|
|
121
|
+
// if (error.message) return error.message;
|
|
122
|
+
// }
|
|
123
|
+
// return squidRouteErrorMapping.Unknown;
|
|
124
|
+
// };
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
import type { EventListenerFunction, WidgetEventMap } from "@/core/types/event";
|
|
2
|
+
import type { RouteResponse } from "@0xsquid/sdk/dist/types";
|
|
3
|
+
|
|
4
|
+
export class WidgetEvents extends EventTarget {
|
|
5
|
+
private static instance: WidgetEvents;
|
|
6
|
+
|
|
7
|
+
private constructor() {
|
|
8
|
+
super();
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
// Singleton, because we need to access this service outside the widget
|
|
12
|
+
public static getInstance(): WidgetEvents {
|
|
13
|
+
if (!WidgetEvents.instance) {
|
|
14
|
+
WidgetEvents.instance = new WidgetEvents();
|
|
15
|
+
}
|
|
16
|
+
return WidgetEvents.instance;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Overriding the addEventListener method to make it easier to use with typescript
|
|
21
|
+
* @param type
|
|
22
|
+
* @param listener
|
|
23
|
+
* @param options
|
|
24
|
+
*/
|
|
25
|
+
listenToWidget<T extends keyof WidgetEventMap>(
|
|
26
|
+
type: T,
|
|
27
|
+
listener: EventListenerFunction<T>,
|
|
28
|
+
options?: boolean | AddEventListenerOptions
|
|
29
|
+
) {
|
|
30
|
+
super.addEventListener(type, listener as unknown as EventListener, options);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Overriding the removeEventListener method to make it easier to use with typescript
|
|
35
|
+
* @param type
|
|
36
|
+
* @param listener
|
|
37
|
+
* @param options
|
|
38
|
+
*/
|
|
39
|
+
removeWidgetListener<T extends keyof WidgetEventMap>(
|
|
40
|
+
type: T,
|
|
41
|
+
listener: EventListenerFunction<T>,
|
|
42
|
+
options?: boolean | EventListenerOptions
|
|
43
|
+
) {
|
|
44
|
+
super.removeEventListener(
|
|
45
|
+
type,
|
|
46
|
+
listener as unknown as EventListener,
|
|
47
|
+
options
|
|
48
|
+
);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* Dispatch an event of the widget
|
|
53
|
+
* To be listened from an integrator website
|
|
54
|
+
* For example to display a success message when transaction is done
|
|
55
|
+
* @param name
|
|
56
|
+
* @param data
|
|
57
|
+
*/
|
|
58
|
+
dispatch<T extends keyof WidgetEventMap>(name: T, data: WidgetEventMap[T]) {
|
|
59
|
+
this.dispatchEvent(new CustomEvent(name, { detail: data }));
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
/**
|
|
63
|
+
* Will dispatch the main axelar status of transaction
|
|
64
|
+
* This will be called every time the status is received by backend
|
|
65
|
+
* (Using interval to check status)
|
|
66
|
+
* @param status
|
|
67
|
+
*/
|
|
68
|
+
dispatchSwapStatus(status: string) {
|
|
69
|
+
this.dispatch("swapStatus", { status });
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
/**
|
|
73
|
+
* Dispatch event when user executes a swap
|
|
74
|
+
* Only when we have the tx hash received
|
|
75
|
+
* @param route
|
|
76
|
+
*/
|
|
77
|
+
dispatchSwapExecuteCall(route: RouteResponse["route"], txHash: string) {
|
|
78
|
+
this.dispatch("swap", { route, txHash });
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/**
|
|
82
|
+
* Dispatch event when user changes chain/token
|
|
83
|
+
* @param swapParams
|
|
84
|
+
*/
|
|
85
|
+
dispatchSwapParamsChanged(swapParams: {
|
|
86
|
+
fromChainId?: string;
|
|
87
|
+
toChainId?: string;
|
|
88
|
+
fromTokenAddress?: string;
|
|
89
|
+
toTokenAddress?: string;
|
|
90
|
+
}) {
|
|
91
|
+
this.dispatch("swapParamsChanged", { ...swapParams });
|
|
92
|
+
}
|
|
93
|
+
}
|