@lunch-money/ethereum-to-lunch-money 1.4.0 → 2.0.1

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/README.md CHANGED
@@ -15,31 +15,49 @@ yarn
15
15
  yarn test
16
16
  ```
17
17
 
18
+ ## Ethereum Network Service Provider and aggregator usage and configuration
19
+ The connector provides an interface to create an Ethereum walletClient which provides an interface to check the wallet's balances. Ethereum supports multiple networks (or "chains"), but each walletClient is created for a single network. It is suggested to use the ethereum mainnet when creating the clients. A future optimization may be to support other networks.
20
+
21
+ Once created the walletClient uses the ethers library to query balances in an ethereum wallet. By default this returns only the wallet's ethereum balance unless it is given a list of other tokens to look for. Each token lookup uses gas which counts against rate limits by the Ethereum service providers.
22
+
23
+ To minimize gas usage, but to support other tokens, the Moralis and Etherscan APIs are used to query the wallet for a list of tokens they maintain. While these API requests also cost some gas, reducing the list of tokens to just those required generally optimizes the cost of the balance lookup. Moralis provides better results but has a less generous free tier. Etherscan (if set) is used as a secondary service when the Moralis API request fails. In order to leverage these APIs the following environment variables must be set:
24
+
25
+ - **MORALIS_API_KEY**: [set up a key here](https://moralis.io/). Used for token discovery as the primary method. Moralis provides comprehensive ERC20 token discovery.
26
+ - **ETHERSCAN_API_KEY**: [set up a key here](https://etherscan.io/apis). Used as a fallback for token discovery if Moralis fails. Etherscan provides token transfer event discovery.
27
+
28
+ These lookups will return a list of all tokens the wallets have ever encountered, including test tokens and possibly tokens associated with scams. To further reduce the cost of balance lookups the list of discovered tokens is filtered against the list provided by 1inch, a decentralized exchange aggregator, that maintains a list of tokens with good reputations and liquidity. Filtering the list of all tokens ever used by the wallet against 1inch further reduces cost by eliminating tokens not on the provisioned network, or those that don't meet reputation standards.
29
+
30
+ We use a static list of tokens from 1inch, generated at the time the library is released, as the filter.
31
+
32
+ Once the list of tokens contained in a wallet is obtained, the ethers library is used to obtain the balances for these tokens. Ethers uses one or more Ethereum Service Providers. It is recommended to provision API Key for both of the following service providers which are used in a primary/secondary fashion:
33
+ - **ALCHEMY_API_KEY**: [set up a key here](https://dashboard.alchemy.com/). This is the recommended service to use.
34
+ - **INFURA_API_KEY**: [set up a key here](https://developer.metamask.io/). If set with Alchemy, it will be used as a secondary.
35
+
36
+ While it is possible to perform initialization and balance lookups without setting any of these API keys it is strongly recommended to set all of them.x
37
+
38
+ Net/Net when properly provisioned, this service will provide Lunch Money users with ethereum wallet balances for tokens on the network specified by Lunch Money (the default mainnet) and that have a well established reputation with 1inch.
39
+
18
40
  ## Debugging
19
41
 
20
- The following environment variables can be run with the test script or when using the plugin with Lunch Money
42
+ The following optional environment variables can be run with the test script or when using the plugin with Lunch Money
21
43
 
22
44
  - DEBUG_ETHEREUM - set to enable detailed debug messages and enable API Key validation
45
+
23
46
  - ETHEREUM_BALANCE_TIMEOUT_MSECS - the number of msecs to wait for a response before timing out
24
-
25
47
  The timeout was added to avoid a false CORS message when the API never returns.
26
48
 
27
49
  Tweaking this to about 1000-2000, and watching the debug messages can be useful for validating that failover is working as expected.
28
50
 
29
- ## Live Testing
30
-
31
- There is a script, `get-balances.ts`, that can be invoked to invoke the client against a real or test wallet. This mimics the behavior of the Lunch Money server when a user attempts to connect an Ethereum wallet.
51
+ - DEBUG_ETHEREUM_FAIL_ON_ERROR - set to true to have the test script (or lunch money server) fail if any of the ethereum service provider keys are invalid.
32
52
 
33
- Copy [env.example](./env.example) to .env and set some or all of the environment variables that the script and connector use.
53
+ Whenever the values of the Ethereum Service Provider keys are updated in an environment it is suggested to temporarily set DEBUG_ETHEREUM_FAIL_ON_ERROR to true and to watch the console messages on startup. If the app reports that all keys are valid and does not exit, then remove the environment variable prior to a final deploy.
34
54
 
35
- ### Ethereum Service Provider API Keys
55
+ ## Live Testing
36
56
 
37
- If no keys are set, the script will use the public APIs which may or may not work. One or both of the following are recommended:
57
+ There is a script, `get-balances.ts`, that can be invoked to invoke the client against a real or test wallet. This mimics the behavior of the Lunch Money server when a user attempts to connect an Ethereum wallet.
38
58
 
39
- - ALCHEMY_API_KEY - [set up a key here](https://dashboard.alchemy.com/). This is the recommended service to use
40
- - INFURA_API_KEY - [set up a key here](https://developer.metamask.io/). If set with Alchemy will be used as a secondary
59
+ Copy [env.example](./env.example) to .env and set some or all of the environment variables that the script and connector use.
41
60
 
42
- While the connector can run with other service node keys, such as Etherscan, the test script will not support it.
43
61
 
44
62
  ### Wallet Configuration
45
63
  - LM_ETHEREUM_WALLET_ADDRESS
@@ -52,7 +70,7 @@ To run the script
52
70
  ```
53
71
  yarn test-live
54
72
  ```
55
- A .vscode/launch.json configuration is include to facilitate running the script in the debugger with VSCode.
73
+ A .vscode/launch.json configuration is included to facilitate running the script in the debugger with VSCode.
56
74
 
57
75
  ## Refreshing the Token List
58
76
 
@@ -60,3 +78,35 @@ This package uses a fixed token list fetched as the token list that the 1inch
60
78
  exchange uses. Run the included script
61
79
  `./bin/refresh-token-list.sh` to refresh the token list. Refreshing the token
62
80
  list will require a new version of this package to be released.
81
+
82
+ ## Automated Testing of Ethereum Provider and API Key Scenarios
83
+
84
+ This project includes an automated test script to validate a variety of API Key configuration scenarios. The script tests various scenarios to ensure that the keys are correctly validated and that the system behaves as expected under different conditions.
85
+
86
+ ### Purpose
87
+
88
+ The automated test script is designed to:
89
+ - Validate the presence and correctness of Ethereum service provider keys (e.g., Alchemy, Infura, Etherscan, Moralis).
90
+ - Check for deprecated or unsupported keys and generate warnings.
91
+ - Ensure that the system can fall back to appropriate methods when keys are missing or invalid.
92
+ - Ensure that meaningful warning messages are generated when supplied keys are missing or invalid.
93
+ - Ensure that the process ends when DEBUG_ETHEREUM_FAIL_ON_ERROR
94
+
95
+ ### How to Run the Tests
96
+
97
+ 1. **Ensure environment is built** - `yarn build`
98
+ 1. **Set Environment Variables**: Configure the necessary environment variables for the test scenarios. You can set these directly in your terminal or use a `.env` file.
99
+ 2. **Run the Scenario Script**:
100
+ ```
101
+ npm run scenarios
102
+ ```
103
+ This command will execute the test script, which will run through the predefined scenarios and log the results to the console.
104
+
105
+ ### Scenarios Tested
106
+
107
+ - **Valid and Invalid Alchemy and Infura Keys**: Tests with valid keys to ensure successful validation.
108
+ - **Valid and Invalid Etherscan and Moralis Keys**: Tests with valid keys to ensure successful validation.
109
+ - **Old Pocket API Key**: Tests with deprecated keys to generate warnings.
110
+
111
+ The results of each test scenario will be displayed in the console, indicating success or failure and any relevant warnings or errors.
112
+
@@ -1,11 +1,42 @@
1
1
  import * as ethscan from '@mycrypto/eth-scan';
2
- import * as ethers from 'ethers';
2
+ import { type Provider, type AbstractProvider } from 'ethers';
3
+ import { EthersProviderLike } from '@mycrypto/eth-scan/typings/src/providers/ethers.js';
4
+ import type { LunchMoneyCryptoConnectionBalances } from './types.js';
5
+ export type ProviderInfo = {
6
+ type: 'Service Provider' | 'API Provider';
7
+ name: string;
8
+ status: 'SUCCESS' | 'FAILED';
9
+ apiKey?: string;
10
+ provider?: Provider | AbstractProvider;
11
+ customProvider?: EthersProviderLike;
12
+ error?: string;
13
+ network?: string;
14
+ balance?: string;
15
+ };
16
+ /**
17
+ * Debug function that logs to console.log if DEBUG_ETHEREUM environment variable is set
18
+ */
19
+ export declare const debug: (...args: unknown[]) => void;
3
20
  export interface EthereumWalletClient {
4
- getChainId(): Promise<bigint>;
5
- getWeiBalance(walletAddress: string): Promise<bigint>;
6
- getTokensBalance(walletAddress: string, tokenContractAddresses: string[]): Promise<ethscan.BalanceMap<bigint>>;
21
+ getBalances(walletAddress: string, negligibleBalanceThreshold: number): Promise<LunchMoneyCryptoConnectionBalances>;
22
+ getWeiBalance(walletAddress: string, provider: AbstractProvider): Promise<bigint>;
23
+ getChainId(provider: AbstractProvider): Promise<bigint>;
24
+ getTokensBalance(walletAddress: string, tokenContractAddresses: string[], providerInfo: ProviderInfo): Promise<ethscan.BalanceMap<bigint>>;
25
+ discoverTokensHybrid(walletAddress: string, chainId: bigint): Promise<string[]>;
26
+ }
27
+ export declare class EtherscanProvider {
28
+ private apiKey;
29
+ private baseUrl;
30
+ constructor(apiKey: string);
31
+ discoverTokensForWallet(address: string, chainId?: bigint): Promise<string[]>;
32
+ }
33
+ export declare class MoralisProvider {
34
+ private apiKey;
35
+ private baseUrl;
36
+ constructor(apiKey: string);
37
+ discoverTokensForWallet(address: string, chainId?: bigint): Promise<string[]>;
7
38
  }
8
- export declare const createEthereumWalletClient: (provider: ethers.AbstractProvider) => EthereumWalletClient;
39
+ export declare const createEthereumWalletClient: (serviceProviderInfo?: ProviderInfo[], walletAPIProviderInfo?: ProviderInfo[]) => EthereumWalletClient;
9
40
  interface Token {
10
41
  address: string;
11
42
  chainId: number;
@@ -35,33 +35,369 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
35
35
  return (mod && mod.__esModule) ? mod : { "default": mod };
36
36
  };
37
37
  Object.defineProperty(exports, "__esModule", { value: true });
38
- exports.loadTokenList = exports.createEthereumWalletClient = void 0;
38
+ exports.loadTokenList = exports.createEthereumWalletClient = exports.MoralisProvider = exports.EtherscanProvider = exports.debug = void 0;
39
39
  const ethscan = __importStar(require("@mycrypto/eth-scan"));
40
+ const ethers_1 = require("ethers");
40
41
  const _1inch_json_1 = __importDefault(require("../fixtures/1inch.json"));
41
- const createEthereumWalletClient = (provider) => {
42
- // A custom ethscan provider implementation is needed to map `call` to `send` for ethscan to use the ethers client correctly.
43
- // This is a temporary solution until the ethscan library is updated to support ethers v6.
44
- const customProvider = {
45
- send(method, params) {
46
- // Type pulled from: https://github.com/MyCryptoHQ/eth-scan/blob/master/src/providers/provider.ts#L32
47
- const typedParams = params;
48
- return provider.call({ to: typedParams[0].to, data: typedParams[0].data });
49
- },
50
- };
42
+ // Use node-fetch for Node.js compatibility
43
+ const node_fetch_1 = __importDefault(require("node-fetch"));
44
+ /**
45
+ * Debug function that logs to console.log if DEBUG_ETHEREUM environment variable is set
46
+ */
47
+ const debug = (...args) => {
48
+ if (process.env.DEBUG_ETHEREUM) {
49
+ const timestamp = new Date().toISOString();
50
+ console.log(`[DEBUG_ETHEREUM] [${timestamp}]`, ...args);
51
+ }
52
+ };
53
+ exports.debug = debug;
54
+ class EtherscanProvider {
55
+ constructor(apiKey) {
56
+ this.baseUrl = 'https://api.etherscan.io/v2/api';
57
+ this.apiKey = apiKey;
58
+ }
59
+ discoverTokensForWallet(address, chainId) {
60
+ return __awaiter(this, void 0, void 0, function* () {
61
+ // Use chainId from provider, default to Ethereum mainnet (1)
62
+ const targetChainId = chainId ? Number(chainId) : 1;
63
+ const response = yield (0, node_fetch_1.default)(`${this.baseUrl}?chainid=${targetChainId}&module=account&action=tokentx&address=${address}&startblock=0&endblock=99999999&sort=desc&apikey=${this.apiKey}`);
64
+ const data = yield response.json();
65
+ // Handle valid "no transactions" response
66
+ if (data.status === '0' && data.message === 'No transactions found') {
67
+ return [];
68
+ }
69
+ // Handle API errors
70
+ if (data.status === '0' && data.message === 'NOTOK') {
71
+ throw new Error(`Etherscan V2 API error: ${data.result}`);
72
+ }
73
+ if (data.status !== '1') {
74
+ throw new Error(`Etherscan V2 API error: ${data.message}`);
75
+ }
76
+ // Extract unique token contract addresses from transfer events
77
+ const uniqueTokens = new Set();
78
+ for (const tx of data.result) {
79
+ uniqueTokens.add(tx.contractAddress);
80
+ }
81
+ return Array.from(uniqueTokens);
82
+ });
83
+ }
84
+ }
85
+ exports.EtherscanProvider = EtherscanProvider;
86
+ class MoralisProvider {
87
+ constructor(apiKey) {
88
+ this.baseUrl = 'https://deep-index.moralis.io/api/v2';
89
+ this.apiKey = apiKey;
90
+ }
91
+ discoverTokensForWallet(address, chainId) {
92
+ return __awaiter(this, void 0, void 0, function* () {
93
+ // Map chainId to Moralis chain format (only supports specific enum values)
94
+ let chainFormat;
95
+ if (chainId) {
96
+ switch (Number(chainId)) {
97
+ case 1:
98
+ chainFormat = 'eth';
99
+ break; // Ethereum mainnet
100
+ case 137:
101
+ chainFormat = 'polygon';
102
+ break; // Polygon
103
+ case 56:
104
+ chainFormat = 'bsc';
105
+ break; // BSC
106
+ case 42161:
107
+ chainFormat = 'arbitrum';
108
+ break; // Arbitrum
109
+ case 10:
110
+ chainFormat = 'optimism';
111
+ break; // Optimism
112
+ case 43114:
113
+ chainFormat = 'avalanche';
114
+ break; // Avalanche
115
+ case 250:
116
+ chainFormat = 'fantom';
117
+ break; // Fantom
118
+ default:
119
+ chainFormat = 'eth';
120
+ break; // Default to Ethereum
121
+ }
122
+ }
123
+ else {
124
+ chainFormat = 'eth'; // Default to Ethereum mainnet
125
+ }
126
+ const response = yield (0, node_fetch_1.default)(`${this.baseUrl}/${address}/erc20?chain=${chainFormat}`, {
127
+ headers: {
128
+ 'X-API-Key': this.apiKey,
129
+ },
130
+ });
131
+ if (!response.ok) {
132
+ const errorData = yield response.json().catch(() => ({}));
133
+ if (errorData.message && errorData.message.includes('over 2000 tokens')) {
134
+ throw new Error(`Moralis API error: Wallet has too many tokens (>2000) - ${errorData.message}`);
135
+ }
136
+ throw new Error(`Moralis API error: ${response.status} ${response.statusText}`);
137
+ }
138
+ const data = yield response.json();
139
+ // Extract unique token contract addresses from balance data
140
+ const uniqueTokens = new Set();
141
+ for (const item of data) {
142
+ if (item.token_address && item.balance !== '0') {
143
+ uniqueTokens.add(item.token_address);
144
+ }
145
+ }
146
+ return Array.from(uniqueTokens);
147
+ });
148
+ }
149
+ }
150
+ exports.MoralisProvider = MoralisProvider;
151
+ const createEthereumWalletClient = (serviceProviderInfo = [], walletAPIProviderInfo = []) => {
152
+ let providers = [];
153
+ let etherscanProvider = null;
154
+ let moralisProvider = null;
155
+ try {
156
+ // Initialize the custom provider(s) for ethscan to use the ethers client correctly.
157
+ // A custom ethscan provider implementation is needed to map `call` to `send` for ethscan to use the ethers client correctly.
158
+ // This is a temporary solution until the ethscan library is updated to support ethers v6.
159
+ if (serviceProviderInfo.length) {
160
+ providers = Object.freeze(serviceProviderInfo.map((providerInfo) => {
161
+ if (providerInfo.type === 'Service Provider' && providerInfo.provider) {
162
+ return Object.assign(Object.assign({}, providerInfo), { customProvider: {
163
+ send(method, params) {
164
+ var _a;
165
+ // Type pulled from: https://github.com/MyCryptoHQ/eth-scan/blob/master/src/providers/provider.ts#L32
166
+ const typedParams = params;
167
+ return (_a = providerInfo.provider) === null || _a === void 0 ? void 0 : _a.call({
168
+ to: typedParams[0].to,
169
+ data: typedParams[0].data,
170
+ });
171
+ },
172
+ } });
173
+ }
174
+ else {
175
+ throw new Error(`Invalid service provider: ${providerInfo.name} passed to createEthereumWalletClient`);
176
+ }
177
+ }));
178
+ // Initialize any wallet API providers
179
+ for (const walletKeyInfo of walletAPIProviderInfo) {
180
+ if (walletKeyInfo.type === 'API Provider') {
181
+ if (walletKeyInfo.name === 'Etherscan' && walletKeyInfo.apiKey) {
182
+ etherscanProvider = new EtherscanProvider(walletKeyInfo.apiKey);
183
+ }
184
+ else if (walletKeyInfo.name === 'Moralis' && walletKeyInfo.apiKey) {
185
+ moralisProvider = new MoralisProvider(walletKeyInfo.apiKey);
186
+ }
187
+ }
188
+ else {
189
+ throw new Error(`Invalid wallet API provider: ${walletKeyInfo.name} passed to createEthereumWalletClient`);
190
+ }
191
+ }
192
+ }
193
+ else {
194
+ // Create a wallet using the quorum of free service providers
195
+ const publicProvider = ethers_1.ethers.getDefaultProvider();
196
+ providers = Object.freeze([
197
+ ...providers,
198
+ {
199
+ type: 'Service Provider',
200
+ name: 'Public Provider',
201
+ provider: publicProvider,
202
+ status: 'SUCCESS',
203
+ customProvider: {
204
+ send(method, params) {
205
+ const typedParams = params;
206
+ return publicProvider === null || publicProvider === void 0 ? void 0 : publicProvider.call({ to: typedParams[0].to, data: typedParams[0].data });
207
+ },
208
+ },
209
+ },
210
+ ]);
211
+ }
212
+ }
213
+ catch (error) {
214
+ throw new Error(`Error creating Ethereum wallet client: ${error instanceof Error ? error.message : String(error)}`);
215
+ }
216
+ const internalGetBalances = (client, walletAddress, negligibleBalanceThreshold, provider, customProvider, obscuredWalletAddress) => __awaiter(void 0, void 0, void 0, function* () {
217
+ let timeoutId;
218
+ const timeoutDuration = process.env.ETHEREUM_BALANCE_TIMEOUT_MSECS
219
+ ? parseInt(process.env.ETHEREUM_BALANCE_TIMEOUT_MSECS)
220
+ : 60000;
221
+ const timeout = new Promise((_, reject) => {
222
+ timeoutId = setTimeout(() => {
223
+ reject(new Error(`Ethereum connector getBalances timed out after ${timeoutDuration} milliseconds.`));
224
+ }, timeoutDuration);
225
+ });
226
+ const result = yield Promise.race([
227
+ (() => __awaiter(void 0, void 0, void 0, function* () {
228
+ try {
229
+ const weiBalance = yield client.getWeiBalance(walletAddress, provider);
230
+ const chainId = yield client.getChainId(provider);
231
+ let filteredTokens = [];
232
+ try {
233
+ let discoveredTokens = [];
234
+ if (moralisProvider || etherscanProvider) {
235
+ discoveredTokens = yield client.discoverTokensHybrid(walletAddress, chainId);
236
+ if (discoveredTokens.length > 0) {
237
+ filteredTokens = yield (0, exports.loadTokenList)().then((tokens) => tokens.filter((t) => discoveredTokens.includes(t.address) && BigInt(t.chainId) === BigInt(chainId)));
238
+ (0, exports.debug)(`Wallet ${obscuredWalletAddress}: Filtered to ${filteredTokens.length} tokens on chain ${chainId}`);
239
+ }
240
+ else {
241
+ (0, exports.debug)(`Wallet ${obscuredWalletAddress}: No tokens discovered, using empty token list`);
242
+ }
243
+ }
244
+ else {
245
+ (0, exports.debug)(`Wallet ${obscuredWalletAddress}: No discovery APIs available, using full token list`);
246
+ filteredTokens = (yield (0, exports.loadTokenList)()).filter((t) => BigInt(t.chainId) === BigInt(chainId));
247
+ }
248
+ }
249
+ catch (error) {
250
+ (0, exports.debug)(`Wallet ${obscuredWalletAddress}: Token discovery failed, falling back to full token list:`, error);
251
+ filteredTokens = (yield (0, exports.loadTokenList)()).filter((t) => BigInt(t.chainId) === BigInt(chainId));
252
+ }
253
+ (0, exports.debug)(`Wallet ${obscuredWalletAddress}: Checking balances for ETH and ${filteredTokens.length} other tokens`);
254
+ const map = yield ethscan.getTokensBalance(customProvider, walletAddress, filteredTokens.map((t) => t.address));
255
+ return { weiBalance, chainId, map, filteredTokens };
256
+ }
257
+ finally {
258
+ if (timeoutId) {
259
+ clearTimeout(timeoutId);
260
+ }
261
+ }
262
+ }))(),
263
+ timeout,
264
+ ]);
265
+ const { weiBalance, chainId, map, filteredTokens } = result;
266
+ (0, exports.debug)('ethers.getTokensBalance returned for wallet address:', obscuredWalletAddress);
267
+ const balances = Object.entries(map)
268
+ .map(([address, balance]) => {
269
+ const token = filteredTokens.find((t) => t.address === address);
270
+ if (!token) {
271
+ throw new Error(`Token ${address} not found in discovered token list for chainId ${chainId}`);
272
+ }
273
+ return {
274
+ asset: token.symbol,
275
+ undivisedAmount: balance,
276
+ decimals: token.decimals,
277
+ };
278
+ })
279
+ .concat({ asset: 'ETH', undivisedAmount: weiBalance, decimals: 18 })
280
+ .map(({ asset, undivisedAmount, decimals }) => ({ asset, amount: ethers_1.ethers.formatUnits(undivisedAmount, decimals) }))
281
+ .filter((b) => ethers_1.ethers.parseUnits(b.amount, 18) > negligibleBalanceThreshold)
282
+ .map((b) => ({ asset: b.asset, amount: String(b.amount) }))
283
+ .sort((a, b) => a.asset.localeCompare(b.asset));
284
+ (0, exports.debug)(`Returning from getBalances for ${obscuredWalletAddress}:`, balances);
285
+ const balanceResult = {
286
+ providerName: 'wallet_ethereum',
287
+ balances,
288
+ };
289
+ return balanceResult;
290
+ });
51
291
  return {
52
- getChainId() {
292
+ getChainId(provider) {
53
293
  return __awaiter(this, void 0, void 0, function* () {
54
294
  return (yield provider.getNetwork()).chainId;
55
295
  });
56
296
  },
57
- getWeiBalance(walletAddress) {
297
+ getWeiBalance(walletAddress, provider) {
58
298
  return __awaiter(this, void 0, void 0, function* () {
59
299
  return yield provider.getBalance(walletAddress);
60
300
  });
61
301
  },
62
- getTokensBalance(walletAddress, tokenContractAddresses) {
302
+ getBalances(walletAddress, negligibleBalanceThreshold) {
303
+ return __awaiter(this, void 0, void 0, function* () {
304
+ const obscuredWalletAddress = `0x..${walletAddress.slice(-6)}`;
305
+ (0, exports.debug)('getBalances called for wallet address:', obscuredWalletAddress);
306
+ let result = {
307
+ providerName: 'wallet_ethereum',
308
+ balances: [],
309
+ };
310
+ if (providers.length === 0) {
311
+ throw new Error('No Ethereum providers available');
312
+ }
313
+ let providerIndex = 0;
314
+ let provider = providers[0].provider;
315
+ let customProvider = providers[0].customProvider;
316
+ let providerName = providers[0].name;
317
+ (0, exports.debug)(`Attempting lookup using primary provider: ${providerName}`);
318
+ let balanceFound = false;
319
+ while (!balanceFound) {
320
+ try {
321
+ result = yield internalGetBalances(this, walletAddress, negligibleBalanceThreshold, provider, customProvider, obscuredWalletAddress);
322
+ balanceFound = true;
323
+ }
324
+ catch (error) {
325
+ const errorMessage = error instanceof Error ? error.message : String(error);
326
+ (0, exports.debug)(`Error getting balances using provider ${providerName}: ${errorMessage}`);
327
+ if (errorMessage.includes('unconfigured name') || errorMessage.includes('bad address checksum')) {
328
+ balanceFound = true; // Should not be needed, but just in case
329
+ throw new Error(`Invalid wallet address. Account needs to be relinked.`);
330
+ }
331
+ else if (providerIndex === providers.length - 1) {
332
+ balanceFound = true; // Should not be needed, but just in case
333
+ throw error;
334
+ }
335
+ providerIndex = providerIndex + 1;
336
+ providerName = providers[providerIndex].name;
337
+ provider = providers[providerIndex].provider;
338
+ customProvider = providers[providerIndex].customProvider;
339
+ (0, exports.debug)(`Retrying lookup using provider: ${providerName}`);
340
+ }
341
+ }
342
+ return result;
343
+ });
344
+ },
345
+ getTokensBalance(walletAddress, tokenContractAddresses, providerInfo) {
346
+ return __awaiter(this, void 0, void 0, function* () {
347
+ if (providerInfo.customProvider) {
348
+ return ethscan.getTokensBalance(providerInfo.customProvider, walletAddress, tokenContractAddresses);
349
+ }
350
+ else {
351
+ throw new Error(`No ethscan compatible provider found for ${providerInfo.name}`);
352
+ }
353
+ });
354
+ },
355
+ discoverTokensHybrid(walletAddress, chainId) {
63
356
  return __awaiter(this, void 0, void 0, function* () {
64
- return ethscan.getTokensBalance(customProvider, walletAddress, tokenContractAddresses);
357
+ const allTokens = new Set();
358
+ // 1. Moralis Discovery (PRIMARY)
359
+ if (moralisProvider) {
360
+ try {
361
+ const moralisTokens = yield moralisProvider.discoverTokensForWallet(walletAddress, chainId);
362
+ (0, exports.debug)(`Moralis: Discovered ${moralisTokens.length} tokens`);
363
+ moralisTokens.forEach((t) => allTokens.add(t));
364
+ }
365
+ catch (error) {
366
+ (0, exports.debug)(`Moralis: Failed - ${error instanceof Error ? error.message : String(error)}`);
367
+ // 2. Etherscan Discovery (FALLBACK ONLY)
368
+ if (etherscanProvider) {
369
+ try {
370
+ const etherscanTokens = yield etherscanProvider.discoverTokensForWallet(walletAddress, chainId);
371
+ (0, exports.debug)(`Etherscan (fallback): Discovered ${etherscanTokens.length} tokens`);
372
+ etherscanTokens.forEach((t) => allTokens.add(t));
373
+ }
374
+ catch (fallbackError) {
375
+ (0, exports.debug)(`Etherscan (fallback): Failed - ${fallbackError instanceof Error ? fallbackError.message : String(fallbackError)}`);
376
+ }
377
+ }
378
+ else {
379
+ (0, exports.debug)('Etherscan: No API key provided for fallback');
380
+ }
381
+ }
382
+ }
383
+ else {
384
+ (0, exports.debug)('Moralis: No API key provided');
385
+ // 3. Etherscan Discovery (PRIMARY if no Moralis)
386
+ if (etherscanProvider) {
387
+ try {
388
+ const etherscanTokens = yield etherscanProvider.discoverTokensForWallet(walletAddress, chainId);
389
+ (0, exports.debug)(`Etherscan: Discovered ${etherscanTokens.length} tokens`);
390
+ etherscanTokens.forEach((t) => allTokens.add(t));
391
+ }
392
+ catch (error) {
393
+ (0, exports.debug)(`Etherscan: Failed - ${error instanceof Error ? error.message : String(error)}`);
394
+ }
395
+ }
396
+ else {
397
+ (0, exports.debug)('Etherscan: No API key provided');
398
+ }
399
+ }
400
+ return Array.from(allTokens);
65
401
  });
66
402
  },
67
403
  };
@@ -1 +1 @@
1
- {"version":3,"file":"client.js","sourceRoot":"","sources":["../../../src/client.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,4DAA8C;AAG9C,yEAAoD;AAS7C,MAAM,0BAA0B,GAAG,CAAC,QAAiC,EAAwB,EAAE;IACpG,6HAA6H;IAC7H,0FAA0F;IAC1F,MAAM,cAAc,GAAuB;QACzC,IAAI,CAAS,MAAc,EAAE,MAA2B;YACtD,qGAAqG;YACrG,MAAM,WAAW,GAAG,MAAgD,CAAC;YAErE,OAAO,QAAQ,CAAC,IAAI,CAAC,EAAE,EAAE,EAAE,WAAW,CAAC,CAAC,CAAC,CAAC,EAAE,EAAE,IAAI,EAAE,WAAW,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,CAAoB,CAAC;QAChG,CAAC;KACF,CAAC;IAEF,OAAO;QACC,UAAU;;gBACd,OAAO,CAAC,MAAM,QAAQ,CAAC,UAAU,EAAE,CAAC,CAAC,OAAO,CAAC;YAC/C,CAAC;SAAA;QACK,aAAa,CAAC,aAAa;;gBAC/B,OAAO,MAAM,QAAQ,CAAC,UAAU,CAAC,aAAa,CAAC,CAAC;YAClD,CAAC;SAAA;QACK,gBAAgB,CAAC,aAAa,EAAE,sBAAsB;;gBAC1D,OAAO,OAAO,CAAC,gBAAgB,CAAC,cAAc,EAAE,aAAa,EAAE,sBAAsB,CAAC,CAAC;YACzF,CAAC;SAAA;KACF,CAAC;AACJ,CAAC,CAAC;AAvBW,QAAA,0BAA0B,8BAuBrC;AAWK,MAAM,aAAa,GAAG,GAA2B,EAAE;IACxD,OAAO,qBAAc,CAAC,MAAM,CAAC;AAC/B,CAAC,CAAA,CAAC;AAFW,QAAA,aAAa,iBAExB"}
1
+ {"version":3,"file":"client.js","sourceRoot":"","sources":["../../../src/client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,34 @@
1
+ import type { ProviderInfo, EthereumWalletClient } from './client.js';
2
+ export interface EthereumIntegrationType {
3
+ initialized: boolean;
4
+ walletClient: EthereumWalletClient;
5
+ serviceProviderInfo: ProviderInfo[];
6
+ walletProviderInfo: ProviderInfo[];
7
+ [key: string]: unknown;
8
+ }
9
+ export interface INTEGRATIONS {
10
+ ethereum: EthereumIntegrationType;
11
+ [key: string]: unknown;
12
+ }
13
+ declare class EthereumInitializationService {
14
+ private integrations;
15
+ private logDebug;
16
+ private initialized;
17
+ private ethereumIntegration;
18
+ constructor(integrations: INTEGRATIONS, logDebug: (message: string) => void);
19
+ initialize(): Promise<EthereumIntegrationType>;
20
+ private validateAPIKeys;
21
+ private processResults;
22
+ private handleError;
23
+ private testProvider;
24
+ private testApiKey;
25
+ private getCleanErrorMessage;
26
+ private maskKey;
27
+ private warnAboutLegacyKeys;
28
+ private getPrivateProviders;
29
+ private getWalletTokenApiKeyTestInfo;
30
+ private handleMoralisResponse;
31
+ private handleEtherscanResponse;
32
+ private getErrorMessage;
33
+ }
34
+ export default EthereumInitializationService;