@lifi/sdk 2.0.0-beta.1 → 2.0.0-beta.11

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 (81) hide show
  1. package/dist/{Lifi.d.ts → LiFi.d.ts} +19 -63
  2. package/dist/{Lifi.js → LiFi.js} +19 -212
  3. package/dist/allowance/checkAllowance.d.ts +2 -2
  4. package/dist/allowance/checkAllowance.js +16 -2
  5. package/dist/allowance/utils.d.ts +2 -1
  6. package/dist/allowance/utils.js +7 -2
  7. package/dist/balance/checkBalance.d.ts +2 -2
  8. package/dist/balance/index.d.ts +1 -1
  9. package/dist/cjs/{Lifi.d.ts → LiFi.d.ts} +19 -63
  10. package/dist/cjs/{Lifi.js → LiFi.js} +22 -213
  11. package/dist/cjs/allowance/checkAllowance.d.ts +2 -2
  12. package/dist/cjs/allowance/checkAllowance.js +16 -2
  13. package/dist/cjs/allowance/utils.d.ts +2 -1
  14. package/dist/cjs/allowance/utils.js +7 -2
  15. package/dist/cjs/balance/checkBalance.d.ts +2 -2
  16. package/dist/cjs/balance/index.d.ts +1 -1
  17. package/dist/cjs/connectors.d.ts +1 -1
  18. package/dist/cjs/connectors.js +7 -9
  19. package/dist/cjs/execution/RouteExecutionManager.d.ts +65 -0
  20. package/dist/cjs/execution/RouteExecutionManager.js +220 -0
  21. package/dist/cjs/execution/StatusManager.d.ts +12 -12
  22. package/dist/cjs/execution/StatusManager.js +5 -5
  23. package/dist/cjs/execution/{ExecutionManager.d.ts → StepExecutionManager.d.ts} +1 -1
  24. package/dist/cjs/execution/{ExecutionManager.js → StepExecutionManager.js} +11 -3
  25. package/dist/cjs/execution/StepExecutor.d.ts +4 -4
  26. package/dist/cjs/execution/StepExecutor.js +17 -9
  27. package/dist/cjs/execution/stepComparison.d.ts +3 -3
  28. package/dist/cjs/execution/stepComparison.js +2 -5
  29. package/dist/cjs/execution/switchChain.d.ts +2 -2
  30. package/dist/cjs/execution/utils.d.ts +3 -3
  31. package/dist/cjs/helpers.d.ts +5 -7
  32. package/dist/cjs/helpers.js +10 -30
  33. package/dist/cjs/index.d.ts +1 -2
  34. package/dist/cjs/index.js +3 -6
  35. package/dist/cjs/request.d.ts +9 -0
  36. package/dist/cjs/request.js +60 -0
  37. package/dist/cjs/services/ApiService.d.ts +8 -7
  38. package/dist/cjs/services/ApiService.js +52 -31
  39. package/dist/cjs/services/ConfigService.js +6 -2
  40. package/dist/cjs/typeguards.d.ts +2 -2
  41. package/dist/cjs/types/internal.types.d.ts +54 -10
  42. package/dist/cjs/utils/errors.d.ts +20 -1
  43. package/dist/cjs/utils/errors.js +23 -1
  44. package/dist/cjs/utils/parseError.d.ts +4 -4
  45. package/dist/cjs/utils/parseError.js +29 -12
  46. package/dist/cjs/utils/utils.d.ts +3 -3
  47. package/dist/cjs/version.d.ts +1 -1
  48. package/dist/cjs/version.js +1 -1
  49. package/dist/connectors.d.ts +1 -1
  50. package/dist/connectors.js +7 -9
  51. package/dist/execution/RouteExecutionManager.d.ts +65 -0
  52. package/dist/execution/RouteExecutionManager.js +213 -0
  53. package/dist/execution/StatusManager.d.ts +12 -12
  54. package/dist/execution/StatusManager.js +5 -5
  55. package/dist/execution/{ExecutionManager.d.ts → StepExecutionManager.d.ts} +1 -1
  56. package/dist/execution/{ExecutionManager.js → StepExecutionManager.js} +9 -1
  57. package/dist/execution/StepExecutor.d.ts +4 -4
  58. package/dist/execution/StepExecutor.js +17 -9
  59. package/dist/execution/stepComparison.d.ts +3 -3
  60. package/dist/execution/stepComparison.js +2 -5
  61. package/dist/execution/switchChain.d.ts +2 -2
  62. package/dist/execution/utils.d.ts +3 -3
  63. package/dist/helpers.d.ts +5 -7
  64. package/dist/helpers.js +9 -29
  65. package/dist/index.d.ts +1 -2
  66. package/dist/index.js +1 -3
  67. package/dist/request.d.ts +9 -0
  68. package/dist/request.js +53 -0
  69. package/dist/services/ApiService.d.ts +8 -7
  70. package/dist/services/ApiService.js +43 -22
  71. package/dist/services/ConfigService.js +7 -2
  72. package/dist/typeguards.d.ts +2 -2
  73. package/dist/types/internal.types.d.ts +54 -10
  74. package/dist/utils/errors.d.ts +20 -1
  75. package/dist/utils/errors.js +22 -0
  76. package/dist/utils/parseError.d.ts +4 -4
  77. package/dist/utils/parseError.js +30 -13
  78. package/dist/utils/utils.d.ts +3 -3
  79. package/dist/version.d.ts +1 -1
  80. package/dist/version.js +1 -1
  81. package/package.json +15 -15
package/dist/helpers.js CHANGED
@@ -1,5 +1,5 @@
1
- import { HTTPError, ValidationError } from './utils/errors';
2
- import { sleep } from './utils/utils';
1
+ import { request } from './request';
2
+ import { ValidationError } from './utils/errors';
3
3
  import { name, version } from './version';
4
4
  const ethereumRequest = async (method, params) => {
5
5
  // If ethereum.request() exists, the provider is probably EIP-1193 compliant.
@@ -58,7 +58,7 @@ export const checkPackageUpdates = async (packageName, packageVersion, disableCh
58
58
  }
59
59
  try {
60
60
  const pkgName = packageName ?? name;
61
- const response = await request(`https://registry.npmjs.org/${pkgName}/latest`);
61
+ const response = await request(`https://registry.npmjs.org/${pkgName}/latest`, { skipTrackingHeaders: true });
62
62
  const latestVersion = response.version;
63
63
  const currentVersion = packageVersion ?? version;
64
64
  if (semverCompare(latestVersion, currentVersion)) {
@@ -73,7 +73,7 @@ export const checkPackageUpdates = async (packageName, packageVersion, disableCh
73
73
  };
74
74
  /**
75
75
  * Converts a quote to Route
76
- * @param {Step} step - Step returned from the quote endpoint.
76
+ * @param {LifiStep} step - Step returned from the quote endpoint.
77
77
  * @return {Route} - The route to be executed.
78
78
  * @throws {ValidationError} Throws a ValidationError if the step has missing values.
79
79
  */
@@ -84,11 +84,6 @@ export const convertQuoteToRoute = (step) => {
84
84
  if (!step.estimate.toAmountUSD) {
85
85
  throw new ValidationError("Missing 'toAmountUSD' in step estimate.");
86
86
  }
87
- const lifiStep = {
88
- ...step,
89
- type: 'lifi',
90
- includedSteps: [],
91
- };
92
87
  const route = {
93
88
  fromToken: step.action.fromToken,
94
89
  toToken: step.action.toToken,
@@ -99,28 +94,13 @@ export const convertQuoteToRoute = (step) => {
99
94
  toChainId: step.action.toToken.chainId,
100
95
  fromAmountUSD: step.estimate.fromAmountUSD,
101
96
  toAmountUSD: step.estimate.toAmountUSD,
102
- steps: [lifiStep],
97
+ steps: [step],
103
98
  toAmountMin: step.estimate.toAmountMin,
99
+ insurance: { state: 'NOT_INSURABLE', feeAmountUsd: '0' },
104
100
  };
105
101
  return route;
106
102
  };
107
- export const requestSettings = {
108
- retries: 1,
109
- };
110
- export const request = async (url, options, retries = requestSettings.retries) => {
111
- try {
112
- const response = await fetch(url, options);
113
- if (!response.ok) {
114
- throw new HTTPError(response);
115
- }
116
- const data = await response.json();
117
- return data;
118
- }
119
- catch (error) {
120
- if (retries > 0 && error?.status === 500) {
121
- await sleep(500);
122
- return request(url, options, retries - 1);
123
- }
124
- throw error;
125
- }
103
+ export const fetchTxErrorDetails = async (txHash, chainId) => {
104
+ const response = await request(`https://api.tenderly.co/api/v1/public-contract/${chainId}/tx/${txHash}`);
105
+ return response;
126
106
  };
package/dist/index.d.ts CHANGED
@@ -1,6 +1,5 @@
1
- import LIFI from './Lifi';
2
1
  export * from './execution';
3
2
  export * from './helpers';
3
+ export { LiFi } from './LiFi';
4
4
  export * from './types';
5
5
  export * from './utils/errors';
6
- export default LIFI;
package/dist/index.js CHANGED
@@ -1,8 +1,6 @@
1
1
  // expose types and helpers
2
- import LIFI from './Lifi';
3
2
  export * from './execution';
4
3
  export * from './helpers';
4
+ export { LiFi } from './LiFi';
5
5
  export * from './types';
6
6
  export * from './utils/errors';
7
- // expose sdk
8
- export default LIFI;
@@ -0,0 +1,9 @@
1
+ export declare const requestSettings: {
2
+ retries: number;
3
+ };
4
+ interface ExtendedRequestInit extends RequestInit {
5
+ retries?: number;
6
+ skipTrackingHeaders?: boolean;
7
+ }
8
+ export declare const request: <T = Response>(url: RequestInfo | URL, options?: ExtendedRequestInit) => Promise<T>;
9
+ export {};
@@ -0,0 +1,53 @@
1
+ import ConfigService from './services/ConfigService';
2
+ import { HTTPError } from './utils/errors';
3
+ import { sleep } from './utils/utils';
4
+ import { version } from './version';
5
+ export const requestSettings = {
6
+ retries: 1,
7
+ };
8
+ export const request = async (url, options = {
9
+ retries: requestSettings.retries,
10
+ }) => {
11
+ const { userId, integrator, widgetVersion } = ConfigService.getInstance().getConfig();
12
+ options.retries = options.retries ?? requestSettings.retries;
13
+ try {
14
+ if (!options.skipTrackingHeaders) {
15
+ if (userId) {
16
+ options.headers = {
17
+ ...options?.headers,
18
+ 'X-LIFI-UserId': userId,
19
+ };
20
+ }
21
+ if (widgetVersion) {
22
+ options.headers = {
23
+ ...options?.headers,
24
+ 'X-LIFI-Widget': widgetVersion,
25
+ };
26
+ }
27
+ if (version) {
28
+ options.headers = {
29
+ ...options?.headers,
30
+ 'X-LIFI-SDK': version,
31
+ };
32
+ }
33
+ // integrator is mandatory during SDK initialization
34
+ options.headers = {
35
+ ...options?.headers,
36
+ 'X-LIFI-Integrator': integrator,
37
+ };
38
+ }
39
+ const response = await fetch(url, options);
40
+ if (!response.ok) {
41
+ throw new HTTPError(response);
42
+ }
43
+ const data = await response.json();
44
+ return data;
45
+ }
46
+ catch (error) {
47
+ if (options.retries > 0 && error?.status === 500) {
48
+ await sleep(500);
49
+ return request(url, { ...options, retries: options.retries - 1 });
50
+ }
51
+ throw error;
52
+ }
53
+ };
@@ -1,16 +1,17 @@
1
- import { ContractCallQuoteRequest, GasRecommendationRequest, GasRecommendationResponse, GetStatusRequest, QuoteRequest, RequestOptions, TokensRequest, TokensResponse } from '@lifi/types';
2
- import { ChainId, ChainKey, ExtendedChain, PossibilitiesRequest, PossibilitiesResponse, RoutesRequest, RoutesResponse, StatusResponse, Step, Token, ToolsRequest, ToolsResponse } from '../types';
1
+ import { ConnectionsRequest, ConnectionsResponse, ContractCallQuoteRequest, GasRecommendationRequest, GasRecommendationResponse, GetStatusRequest, LifiStep, QuoteRequest, RequestOptions, TokensRequest, TokensResponse } from '@lifi/types';
2
+ import { ChainId, ChainKey, ExtendedChain, PossibilitiesRequest, PossibilitiesResponse, RoutesRequest, RoutesResponse, StatusResponse, Token, ToolsRequest, ToolsResponse } from '../types';
3
3
  declare const _default: {
4
4
  getChains: (options?: RequestOptions | undefined) => Promise<ExtendedChain[]>;
5
- getContractCallQuote: (requestConfig: ContractCallQuoteRequest, options?: RequestOptions | undefined) => Promise<Step>;
5
+ getContractCallQuote: (requestConfig: ContractCallQuoteRequest, options?: RequestOptions | undefined) => Promise<LifiStep>;
6
6
  getGasRecommendation: ({ chainId, fromChain, fromToken }: GasRecommendationRequest, options?: RequestOptions | undefined) => Promise<GasRecommendationResponse>;
7
7
  getPossibilities: (requestConfig?: PossibilitiesRequest | undefined, options?: RequestOptions | undefined) => Promise<PossibilitiesResponse>;
8
- getQuote: (requestConfig: QuoteRequest, options?: RequestOptions | undefined) => Promise<Step>;
8
+ getQuote: (requestConfig: QuoteRequest, options?: RequestOptions | undefined) => Promise<LifiStep>;
9
9
  getRoutes: (requestConfig: RoutesRequest, options?: RequestOptions | undefined) => Promise<RoutesResponse>;
10
- getStatus: ({ bridge, fromChain, toChain, txHash }: GetStatusRequest, options?: RequestOptions | undefined) => Promise<StatusResponse>;
11
- getStepTransaction: (step: Step, options?: RequestOptions | undefined) => Promise<Step>;
12
- getToken: (chain: ChainKey | ChainId, token: string, options?: RequestOptions | undefined) => Promise<Token>;
10
+ getStatus: (requestConfig: GetStatusRequest, options?: RequestOptions | undefined) => Promise<StatusResponse>;
11
+ getStepTransaction: (step: LifiStep, options?: RequestOptions | undefined) => Promise<LifiStep>;
12
+ getToken: (chain: ChainId | ChainKey, token: string, options?: RequestOptions | undefined) => Promise<Token>;
13
13
  getTokens: (requestConfig?: TokensRequest | undefined, options?: RequestOptions | undefined) => Promise<TokensResponse>;
14
14
  getTools: (requestConfig?: ToolsRequest | undefined, options?: RequestOptions | undefined) => Promise<ToolsResponse>;
15
+ getAvailableConnections: (connectionRequest: ConnectionsRequest) => Promise<ConnectionsResponse>;
15
16
  };
16
17
  export default _default;
@@ -1,4 +1,4 @@
1
- import { request } from '../helpers';
1
+ import { request } from '../request';
2
2
  import { isRoutesRequest, isStep } from '../typeguards';
3
3
  import { ValidationError } from '../utils/errors';
4
4
  import { parseBackendError } from '../utils/parseError';
@@ -161,27 +161,14 @@ const getContractCallQuote = async (requestConfig, options) => {
161
161
  throw await parseBackendError(e);
162
162
  }
163
163
  };
164
- const getStatus = async ({ bridge, fromChain, toChain, txHash }, options) => {
165
- if (fromChain !== toChain && !bridge) {
166
- throw new ValidationError('Parameter "bridge" is required for cross chain transfers.');
167
- }
168
- if (!fromChain) {
169
- throw new ValidationError('Required parameter "fromChain" is missing.');
170
- }
171
- if (!toChain) {
172
- throw new ValidationError('Required parameter "toChain" is missing.');
173
- }
174
- if (!txHash) {
164
+ const getStatus = async (requestConfig, options) => {
165
+ if (!requestConfig.txHash) {
175
166
  throw new ValidationError('Required parameter "txHash" is missing.');
176
167
  }
177
168
  const config = ConfigService.getInstance().getConfig();
169
+ const queryParams = new URLSearchParams(requestConfig);
178
170
  try {
179
- const response = await request(`${config.apiUrl}/status?${new URLSearchParams({
180
- bridge,
181
- fromChain,
182
- toChain,
183
- txHash,
184
- })}`, {
171
+ const response = await request(`${config.apiUrl}/status?${queryParams}`, {
185
172
  signal: options?.signal,
186
173
  });
187
174
  return response;
@@ -277,11 +264,15 @@ const getGasRecommendation = async ({ chainId, fromChain, fromToken }, options)
277
264
  if (!chainId) {
278
265
  throw new ValidationError('Required parameter "chainId" is missing.');
279
266
  }
267
+ const url = new URL(`${config.apiUrl}/gas/suggestion/${chainId}`);
268
+ if (fromChain) {
269
+ url.searchParams.append('fromChain', fromChain);
270
+ }
271
+ if (fromToken) {
272
+ url.searchParams.append('fromToken', fromToken);
273
+ }
280
274
  try {
281
- const response = await request(`${config.apiUrl}/gas/suggestion/${chainId}?${new URLSearchParams({
282
- fromChain,
283
- fromToken,
284
- })}`, {
275
+ const response = await request(url, {
285
276
  signal: options?.signal,
286
277
  });
287
278
  return response;
@@ -290,6 +281,35 @@ const getGasRecommendation = async ({ chainId, fromChain, fromToken }, options)
290
281
  throw await parseBackendError(e);
291
282
  }
292
283
  };
284
+ const getAvailableConnections = async (connectionRequest) => {
285
+ const config = ConfigService.getInstance().getConfig();
286
+ const url = new URL(`${config.apiUrl}/connections`);
287
+ const { fromChain, fromToken, toChain, toToken, allowBridges } = connectionRequest;
288
+ if (fromChain) {
289
+ url.searchParams.append('fromChain', fromChain);
290
+ }
291
+ if (fromToken) {
292
+ url.searchParams.append('fromToken', fromToken);
293
+ }
294
+ if (toChain) {
295
+ url.searchParams.append('fromToken', toChain);
296
+ }
297
+ if (toToken) {
298
+ url.searchParams.append('fromToken', toToken);
299
+ }
300
+ if (allowBridges?.length) {
301
+ allowBridges.forEach((bridge) => {
302
+ url.searchParams.append('allowBridges', bridge);
303
+ });
304
+ }
305
+ try {
306
+ const response = await request(url);
307
+ return response;
308
+ }
309
+ catch (e) {
310
+ throw await parseBackendError(e);
311
+ }
312
+ };
293
313
  export default {
294
314
  getChains,
295
315
  getContractCallQuote,
@@ -302,4 +322,5 @@ export default {
302
322
  getToken,
303
323
  getTokens,
304
324
  getTools,
325
+ getAvailableConnections,
305
326
  };
@@ -3,12 +3,11 @@ const DefaultExecutionSettings = {
3
3
  /* eslint-disable-next-line @typescript-eslint/no-empty-function */
4
4
  updateCallback: () => { },
5
5
  switchChainHook: () => Promise.resolve(undefined),
6
- acceptSlippageUpdateHook: () => Promise.resolve(undefined),
7
6
  acceptExchangeRateUpdateHook: () => Promise.resolve(undefined),
8
7
  infiniteApproval: false,
9
8
  executeInBackground: false,
10
9
  };
11
- export default class ConfigService {
10
+ class ConfigService {
12
11
  constructor() {
13
12
  this.resolveSetupPromise = undefined;
14
13
  /**
@@ -37,6 +36,10 @@ export default class ConfigService {
37
36
  this.config.defaultExecutionSettings = Object.assign(this.config.defaultExecutionSettings, configUpdate.defaultExecutionSettings);
38
37
  // OPTIONS
39
38
  this.config.defaultRouteOptions = Object.assign(this.config.defaultRouteOptions, configUpdate.defaultRouteOptions);
39
+ this.config.userId = configUpdate.userId || this.config.userId;
40
+ this.config.integrator = configUpdate.integrator || this.config.integrator;
41
+ this.config.widgetVersion =
42
+ configUpdate.widgetVersion || this.config.widgetVersion;
40
43
  return this.config;
41
44
  };
42
45
  this.updateChains = (chains) => {
@@ -85,5 +88,7 @@ ConfigService.getDefaultConfig = () => {
85
88
  defaultRouteOptions: {
86
89
  integrator: 'lifi-sdk',
87
90
  },
91
+ integrator: 'lifi-sdk',
88
92
  };
89
93
  };
94
+ export default ConfigService;
@@ -1,4 +1,4 @@
1
- import { RoutesRequest, Step, Token } from './types';
1
+ import { LifiStep, RoutesRequest, Token } from './types';
2
2
  export declare const isRoutesRequest: (routesRequest: RoutesRequest) => routesRequest is RoutesRequest;
3
- export declare const isStep: (step: Step) => step is Step;
3
+ export declare const isStep: (step: LifiStep) => step is LifiStep;
4
4
  export declare const isToken: (token: Token) => token is Token;
@@ -1,4 +1,5 @@
1
- import { Route, RouteOptions, Step, Token } from '@lifi/types';
1
+ import { TransactionRequest } from '@ethersproject/abstract-provider';
2
+ import { LifiStep, Route, RouteOptions, Token } from '@lifi/types';
2
3
  import BigNumber from 'bignumber.js';
3
4
  import { Signer } from 'ethers';
4
5
  import { ChainId } from '.';
@@ -18,11 +19,12 @@ export type ParsedReceipt = {
18
19
  };
19
20
  export interface ExecutionParams {
20
21
  signer: Signer;
21
- step: Step;
22
+ step: LifiStep;
22
23
  statusManager: StatusManager;
23
24
  settings: InternalExecutionSettings;
24
25
  }
25
26
  export type CallbackFunction = (updatedRoute: Route) => void;
27
+ export type TxRequestCallbackFunction = (updatedTxRequest: TransactionRequest) => Promise<TransactionRequest>;
26
28
  export type Config = {
27
29
  apiUrl: string;
28
30
  rpcs: Record<ChainId, string[]>;
@@ -30,6 +32,9 @@ export type Config = {
30
32
  defaultExecutionSettings: InternalExecutionSettings;
31
33
  defaultRouteOptions: RouteOptions;
32
34
  disableVersionCheck?: boolean;
35
+ userId?: string;
36
+ integrator: string;
37
+ widgetVersion?: string;
33
38
  };
34
39
  export type ConfigUpdate = {
35
40
  apiUrl?: string;
@@ -38,6 +43,9 @@ export type ConfigUpdate = {
38
43
  defaultExecutionSettings?: ExecutionSettings;
39
44
  defaultRouteOptions?: RouteOptions;
40
45
  disableVersionCheck?: boolean;
46
+ userId?: string;
47
+ integrator: string;
48
+ widgetVersion?: string;
41
49
  };
42
50
  export type SwitchChainHook = (requiredChainId: number) => Promise<Signer | undefined>;
43
51
  export interface AcceptSlippageUpdateHookParams {
@@ -54,7 +62,7 @@ export interface ExchangeRateUpdateParams {
54
62
  newToAmount: string;
55
63
  }
56
64
  export type AcceptExchangeRateUpdateHook = (params: ExchangeRateUpdateParams) => Promise<boolean | undefined>;
57
- export interface ExecutionData {
65
+ export interface RouteExecutionData {
58
66
  route: Route;
59
67
  executors: StepExecutor[];
60
68
  settings: InternalExecutionSettings;
@@ -63,20 +71,16 @@ export type ExecutionSettings = Partial<InternalExecutionSettings>;
63
71
  export interface InternalExecutionSettings {
64
72
  updateCallback: CallbackFunction;
65
73
  switchChainHook: SwitchChainHook;
66
- acceptSlippageUpdateHook: AcceptSlippageUpdateHook;
67
74
  acceptExchangeRateUpdateHook: AcceptExchangeRateUpdateHook;
68
75
  infiniteApproval: boolean;
69
76
  executeInBackground: boolean;
77
+ updateTransactionRequest?: TxRequestCallbackFunction;
70
78
  }
71
79
  export type EnforcedObjectProperties<T> = T & {
72
80
  [P in keyof T]-?: T[P];
73
81
  };
74
- export interface ActiveRouteDictionary {
75
- [k: string]: {
76
- executionData: ExecutionData;
77
- executionPromise: Promise<Route>;
78
- };
79
- }
82
+ export type RouteExecutionDictionary = Partial<Record<string, RouteExecutionData>>;
83
+ export type RouteExecutionPromiseDictionary = Partial<Record<string, Promise<Route>>>;
80
84
  export type RevokeTokenData = {
81
85
  token: Token;
82
86
  approvalAddress: string;
@@ -86,3 +90,43 @@ export interface InteractionSettings {
86
90
  allowUpdates?: boolean;
87
91
  stopExecution?: boolean;
88
92
  }
93
+ export interface TenderlyResponse {
94
+ hash: string;
95
+ block_hash: string;
96
+ block_number: number;
97
+ from: string;
98
+ gas: number;
99
+ gas_price: number;
100
+ gas_fee_cap: number;
101
+ gas_tip_cap: number;
102
+ cumulative_gas_used: number;
103
+ gas_used: number;
104
+ effective_gas_price: number;
105
+ input: string;
106
+ nonce: number;
107
+ to: string;
108
+ index: number;
109
+ value: string;
110
+ access_list: any;
111
+ status: boolean;
112
+ addresses: string[];
113
+ contract_ids: string[];
114
+ network_id: string;
115
+ timestamp: string;
116
+ function_selector: string;
117
+ l1_block_number: number;
118
+ l1_timestamp: number;
119
+ deposit_tx: boolean;
120
+ system_tx: boolean;
121
+ mint: number;
122
+ sig: Signature;
123
+ error_message: string;
124
+ method: string;
125
+ decoded_input: any;
126
+ call_trace: any;
127
+ }
128
+ export interface Signature {
129
+ v: string;
130
+ r: string;
131
+ s: string;
132
+ }
@@ -22,7 +22,26 @@ export declare enum LifiErrorCode {
22
22
  TransactionCanceled = 1010,
23
23
  SlippageError = 1011,
24
24
  TransactionRejected = 1012,
25
- BalanceError = 1013
25
+ BalanceError = 1013,
26
+ AllowanceRequired = 1014
27
+ }
28
+ export declare enum EthersErrorType {
29
+ CallExecption = "CALL_EXCEPTION",
30
+ ActionRejected = "ACTION_REJECTED"
31
+ }
32
+ export declare enum EthersErrorMessage {
33
+ ERC20Allowance = "ERC20: transfer amount exceeds allowance",
34
+ LowGas = "intrinsic gas too low",
35
+ OutOfGas = "out of gas",
36
+ Underpriced = "underpriced",
37
+ LowReplacementFee = "replacement fee too low"
38
+ }
39
+ export declare enum ErrorMessage {
40
+ UnknownError = "Unknown error occurred.",
41
+ SlippageError = "The slippage is larger than the defined threshold. Please request a new route to get a fresh quote.",
42
+ GasLimitLow = "Gas limit is too low.",
43
+ TransactionUnderpriced = "Transaction is underpriced.",
44
+ Default = "Something went wrong."
26
45
  }
27
46
  export declare enum MetaMaskRPCErrorCode {
28
47
  invalidInput = -32000,
@@ -25,7 +25,29 @@ export var LifiErrorCode;
25
25
  LifiErrorCode[LifiErrorCode["SlippageError"] = 1011] = "SlippageError";
26
26
  LifiErrorCode[LifiErrorCode["TransactionRejected"] = 1012] = "TransactionRejected";
27
27
  LifiErrorCode[LifiErrorCode["BalanceError"] = 1013] = "BalanceError";
28
+ LifiErrorCode[LifiErrorCode["AllowanceRequired"] = 1014] = "AllowanceRequired";
28
29
  })(LifiErrorCode || (LifiErrorCode = {}));
30
+ export var EthersErrorType;
31
+ (function (EthersErrorType) {
32
+ EthersErrorType["CallExecption"] = "CALL_EXCEPTION";
33
+ EthersErrorType["ActionRejected"] = "ACTION_REJECTED";
34
+ })(EthersErrorType || (EthersErrorType = {}));
35
+ export var EthersErrorMessage;
36
+ (function (EthersErrorMessage) {
37
+ EthersErrorMessage["ERC20Allowance"] = "ERC20: transfer amount exceeds allowance";
38
+ EthersErrorMessage["LowGas"] = "intrinsic gas too low";
39
+ EthersErrorMessage["OutOfGas"] = "out of gas";
40
+ EthersErrorMessage["Underpriced"] = "underpriced";
41
+ EthersErrorMessage["LowReplacementFee"] = "replacement fee too low";
42
+ })(EthersErrorMessage || (EthersErrorMessage = {}));
43
+ export var ErrorMessage;
44
+ (function (ErrorMessage) {
45
+ ErrorMessage["UnknownError"] = "Unknown error occurred.";
46
+ ErrorMessage["SlippageError"] = "The slippage is larger than the defined threshold. Please request a new route to get a fresh quote.";
47
+ ErrorMessage["GasLimitLow"] = "Gas limit is too low.";
48
+ ErrorMessage["TransactionUnderpriced"] = "Transaction is underpriced.";
49
+ ErrorMessage["Default"] = "Something went wrong.";
50
+ })(ErrorMessage || (ErrorMessage = {}));
29
51
  export var MetaMaskRPCErrorCode;
30
52
  (function (MetaMaskRPCErrorCode) {
31
53
  MetaMaskRPCErrorCode[MetaMaskRPCErrorCode["invalidInput"] = -32000] = "invalidInput";
@@ -1,4 +1,4 @@
1
- import { Process, Step } from '@lifi/types';
1
+ import { LifiStep, Process } from '@lifi/types';
2
2
  import { LifiError } from './errors';
3
3
  /**
4
4
  * Available MetaMask error codes:
@@ -31,7 +31,7 @@ import { LifiError } from './errors';
31
31
  * https://eips.ethereum.org/EIPS/eip-1474#error-codes
32
32
  * https://eips.ethereum.org/EIPS/eip-1193#provider-errors
33
33
  */
34
- export declare const getTransactionNotSentMessage: (step?: Step, process?: Process) => Promise<string>;
35
- export declare const getTransactionFailedMessage: (step: Step, txLink?: string) => Promise<string>;
36
- export declare const parseError: (e: any, step?: Step, process?: Process) => Promise<LifiError>;
34
+ export declare const getTransactionNotSentMessage: (step?: LifiStep, process?: Process) => Promise<string>;
35
+ export declare const getTransactionFailedMessage: (step: LifiStep, txLink?: string) => Promise<string>;
36
+ export declare const parseError: (e: any, step?: LifiStep, process?: Process) => Promise<LifiError>;
37
37
  export declare const parseBackendError: (e: any) => Promise<LifiError>;
@@ -1,7 +1,8 @@
1
1
  import { errorCodes as MetaMaskErrorCodes, getMessageFromCode, } from 'eth-rpc-errors';
2
2
  import ChainsService from '../services/ChainsService';
3
- import { LifiError, LifiErrorCode, MetaMaskProviderErrorCode, NotFoundError, ProviderError, RPCError, ServerError, SlippageError, TransactionError, UnknownError, ValidationError, } from './errors';
3
+ import { ErrorMessage, EthersErrorType, EthersErrorMessage, LifiError, LifiErrorCode, MetaMaskProviderErrorCode, NotFoundError, ProviderError, RPCError, ServerError, SlippageError, TransactionError, UnknownError, ValidationError, } from './errors';
4
4
  import { formatTokenAmountOnly } from './utils';
5
+ import { fetchTxErrorDetails } from '../helpers';
5
6
  /**
6
7
  * Available MetaMask error codes:
7
8
  *
@@ -71,13 +72,13 @@ export const parseError = async (e, step, process) => {
71
72
  // rpc errors
72
73
  // underpriced errors are sent as internal errors, so we need to parse the message manually
73
74
  if (e.code === MetaMaskErrorCodes.rpc.internal &&
74
- (e.message?.includes('underpriced') ||
75
- e.message?.includes('replacement fee too low'))) {
76
- return new RPCError(LifiErrorCode.TransactionUnderpriced, 'Transaction is underpriced.', await getTransactionNotSentMessage(step, process), e.stack);
75
+ (e.message?.includes(EthersErrorMessage.Underpriced) ||
76
+ e.message?.includes(EthersErrorMessage.LowReplacementFee))) {
77
+ return new RPCError(LifiErrorCode.TransactionUnderpriced, ErrorMessage.TransactionUnderpriced, await getTransactionNotSentMessage(step, process), e.stack);
77
78
  }
78
- if (e.message?.includes('intrinsic gas too low') ||
79
- e.message?.includes('out of gas')) {
80
- return new TransactionError(LifiErrorCode.GasLimitError, 'Gas limit is too low.', await getTransactionNotSentMessage(step, process), e.stack);
79
+ if (e.message?.includes(EthersErrorMessage.LowGas) ||
80
+ e.message?.includes(EthersErrorMessage.OutOfGas)) {
81
+ return new TransactionError(LifiErrorCode.GasLimitError, ErrorMessage.GasLimitLow, await getTransactionNotSentMessage(step, process), e.stack);
81
82
  }
82
83
  return new RPCError(e.code, getMessageFromCode(e.code), await getTransactionNotSentMessage(step, process), e.stack);
83
84
  }
@@ -88,9 +89,25 @@ export const parseError = async (e, step, process) => {
88
89
  }
89
90
  }
90
91
  switch (e.code) {
91
- case 'CALL_EXCEPTION':
92
- return new ProviderError(LifiErrorCode.TransactionFailed, e.reason, await getTransactionNotSentMessage(step, process), e.stack);
93
- case 'ACTION_REJECTED':
92
+ case EthersErrorType.CallExecption:
93
+ const defaultErrorMessage = await getTransactionNotSentMessage(step, process);
94
+ try {
95
+ if (!step?.action.fromChainId) {
96
+ throw new Error('Signer is not defined.');
97
+ }
98
+ const response = await fetchTxErrorDetails(e.transactionHash, step?.action.fromChainId);
99
+ const errorMessage = response?.error_message ?? e.reason;
100
+ const isAllowanceError = response?.error_message?.includes(EthersErrorMessage.ERC20Allowance) || e.reason?.includes(EthersErrorMessage.ERC20Allowance);
101
+ if (isAllowanceError) {
102
+ return new TransactionError(LifiErrorCode.AllowanceRequired, e.reason, errorMessage, e.stack);
103
+ }
104
+ // Error messages other than allowance error will be handled in catch block
105
+ throw new Error(e);
106
+ }
107
+ catch (error) {
108
+ return new ProviderError(LifiErrorCode.TransactionFailed, e.reason, defaultErrorMessage, e.stack);
109
+ }
110
+ case EthersErrorType.ActionRejected:
94
111
  case MetaMaskProviderErrorCode.userRejectedRequest:
95
112
  return new TransactionError(LifiErrorCode.TransactionRejected, e.message, await getTransactionNotSentMessage(step, process), e.stack);
96
113
  case LifiErrorCode.TransactionUnprepared:
@@ -98,7 +115,7 @@ export const parseError = async (e, step, process) => {
98
115
  case LifiErrorCode.ValidationError:
99
116
  return new TransactionError(LifiErrorCode.ValidationError, e.message, e.htmlMessage);
100
117
  default:
101
- return new UnknownError(LifiErrorCode.InternalError, e.message || 'Unknown error occurred.', undefined, e.stack);
118
+ return new UnknownError(LifiErrorCode.InternalError, e.message || ErrorMessage.UnknownError, undefined, e.stack);
102
119
  }
103
120
  };
104
121
  export const parseBackendError = async (e) => {
@@ -116,10 +133,10 @@ export const parseBackendError = async (e) => {
116
133
  return new NotFoundError(data?.message || e.response?.statusText, undefined, e.stack);
117
134
  }
118
135
  if (e.response?.status === 409) {
119
- return new SlippageError(data?.message || e.response?.statusText, 'The slippage is larger than the defined threshold. Please request a new route to get a fresh quote.', e.stack);
136
+ return new SlippageError(data?.message || e.response?.statusText, ErrorMessage.SlippageError, e.stack);
120
137
  }
121
138
  if (e.response?.status === 500) {
122
139
  return new ServerError(data?.message || e.response?.statusText, undefined, e.stack);
123
140
  }
124
- return new ServerError('Something went wrong.', undefined, e.stack);
141
+ return new ServerError(ErrorMessage.Default, undefined, e.stack);
125
142
  };
@@ -1,10 +1,10 @@
1
1
  import { TransactionReceipt } from '@ethersproject/providers';
2
- import { Token } from '@lifi/types';
2
+ import { LifiStep, Token } from '@lifi/types';
3
3
  import BigNumber from 'bignumber.js';
4
4
  import { Signer } from 'ethers';
5
- import { ChainId, Step } from '../types';
5
+ import { ChainId } from '../types';
6
6
  export declare const sleep: (mills: number) => Promise<undefined>;
7
- export declare const personalizeStep: (signer: Signer, step: Step) => Promise<Step>;
7
+ export declare const personalizeStep: (signer: Signer, step: LifiStep) => Promise<LifiStep>;
8
8
  export declare const splitListIntoChunks: <T>(list: T[], chunkSize: number) => T[][];
9
9
  export declare const formatTokenAmountOnly: (token: Token, amount: string | BigNumber | undefined) => string;
10
10
  /**
package/dist/version.d.ts CHANGED
@@ -1,2 +1,2 @@
1
1
  export declare const name = "@lifi/sdk";
2
- export declare const version = "2.0.0-beta.1";
2
+ export declare const version = "2.0.0-beta.11";
package/dist/version.js CHANGED
@@ -1,2 +1,2 @@
1
1
  export const name = '@lifi/sdk';
2
- export const version = '2.0.0-beta.1';
2
+ export const version = '2.0.0-beta.11';