@toruslabs/ethereum-controllers 4.10.1 → 5.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.
@@ -26,6 +26,9 @@ declare class AccountTrackerController extends BaseController<AccountTrackerConf
26
26
  private getIdentities;
27
27
  private getCurrentChainId;
28
28
  constructor({ config, state, provider, blockTracker, getIdentities, onPreferencesStateChange, getCurrentChainId, }: AccountTrackerControllerOptions);
29
+ blockTrackerListener(block: EthereumBlock): void;
30
+ startPolling(): void;
31
+ stopPolling(): void;
29
32
  syncAccounts(): boolean;
30
33
  refresh(): Promise<void>;
31
34
  private _updateAccounts;
@@ -1,6 +1,5 @@
1
- import { BasePreferencesController, CustomNft, CustomToken, IPreferencesController, PreferencesConfig, PreferencesState, UserInfo } from "@toruslabs/base-controllers";
1
+ import { BasePreferencesController, CustomNft, CustomToken, InitPreferencesParams, IPreferencesController, PreferencesConfig, PreferencesState } from "@toruslabs/base-controllers";
2
2
  import { SafeEventEmitterProvider } from "@toruslabs/openlogin-jrpc";
3
- import PollingBlockTracker from "../Block/PollingBlockTracker";
4
3
  import KeyringController from "../Keyring/KeyringController";
5
4
  import NetworkController from "../Network/NetworkController";
6
5
  import type { AddChainMessageParams, CustomNetworkPayload, CustomNftInfo, CustomTokenInfo, ExtendedAddressPreferences, TransactionPayload } from "../utils/interfaces";
@@ -8,7 +7,6 @@ interface IPreferencesControllerOptions {
8
7
  config?: Partial<PreferencesConfig> & Pick<PreferencesConfig, "api" | "commonApiHost" | "signInPrefix">;
9
8
  state?: Partial<PreferencesState<ExtendedAddressPreferences>>;
10
9
  provider: SafeEventEmitterProvider;
11
- blockTracker?: PollingBlockTracker;
12
10
  signAuthMessage?: KeyringController["signAuthMessage"];
13
11
  getProviderConfig?: NetworkController["getProviderConfig"];
14
12
  setProviderConfig?: NetworkController["setProviderConfig"];
@@ -19,28 +17,17 @@ export default class PreferencesController extends BasePreferencesController<Ext
19
17
  private getProviderConfig;
20
18
  private setProviderConfig;
21
19
  private provider;
22
- private blockTracker;
23
- constructor({ config, state, provider, blockTracker, signAuthMessage, getProviderConfig, setProviderConfig }: IPreferencesControllerOptions);
20
+ constructor({ config, state, provider, signAuthMessage, getProviderConfig, setProviderConfig }: IPreferencesControllerOptions);
24
21
  poll(interval?: number): Promise<void>;
25
- initPreferences(params: {
26
- address: string;
27
- jwtToken?: string;
28
- calledFromEmbed?: boolean;
29
- userInfo?: UserInfo;
30
- rehydrate?: boolean;
31
- locale?: string;
32
- type?: string;
33
- signatures?: string[];
34
- network?: string;
35
- }): Promise<void>;
22
+ initPreferences(params: InitPreferencesParams): Promise<void>;
36
23
  getSelectedAddress(): string;
37
24
  sync(address: string): Promise<boolean>;
38
25
  patchNewTx(tx: TransactionPayload, address: string): Promise<void>;
39
26
  recalculatePastTx(address?: string): void;
40
- refetchEtherscanTx(address?: string): Promise<void>;
27
+ refetchEtherscanTx(address?: string): Promise<unknown[]>;
41
28
  fetchEtherscanTx<T>(parameters: {
42
29
  selectedAddress: string;
43
- selectedNetwork: string;
30
+ chainId: string;
44
31
  }): Promise<T[]>;
45
32
  getEtherScanTokens(address: string, chainId: string): Promise<CustomTokenInfo[]>;
46
33
  getSimpleHashNfts(address: string, chainId: string): Promise<CustomNftInfo[]>;
@@ -60,7 +47,6 @@ export default class PreferencesController extends BasePreferencesController<Ext
60
47
  network: CustomNetworkPayload;
61
48
  id: number | null;
62
49
  }): Promise<boolean>;
63
- private calculatePaymentTx;
64
50
  private getChainOptions;
65
51
  private calculatePastTx;
66
52
  private cancelTxCalculate;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@toruslabs/ethereum-controllers",
3
- "version": "4.10.1",
3
+ "version": "5.0.0",
4
4
  "homepage": "https://github.com/torusresearch/controllers#readme",
5
5
  "license": "ISC",
6
6
  "main": "dist/ethereumControllers.cjs.js",
@@ -24,13 +24,13 @@
24
24
  "@ethereumjs/util": "^9.0.1",
25
25
  "@metamask/eth-sig-util": "^7.0.1",
26
26
  "@metamask/rpc-errors": "^6.1.0",
27
- "@toruslabs/base-controllers": "^4.10.1",
28
- "@toruslabs/http-helpers": "^5.0.0",
27
+ "@toruslabs/base-controllers": "^5.0.0",
28
+ "@toruslabs/http-helpers": "^6.0.0",
29
29
  "@toruslabs/openlogin-jrpc": "^6.1.0",
30
30
  "async-mutex": "^0.4.0",
31
31
  "bignumber.js": "^9.1.2",
32
32
  "bn.js": "^5.2.1",
33
- "ethers": "^6.9.0",
33
+ "ethers": "^6.9.1",
34
34
  "fast-json-patch": "^3.1.1",
35
35
  "jsonschema": "^1.4.1",
36
36
  "lodash": "^4.17.21",
@@ -64,9 +64,9 @@
64
64
  "publishConfig": {
65
65
  "access": "public"
66
66
  },
67
- "gitHead": "eedc319d29c069f37fce6f52065502b72f37a8c4",
67
+ "gitHead": "f63427503cff9c9a08240da584ebee008f1d7527",
68
68
  "devDependencies": {
69
69
  "@nomicfoundation/hardhat-toolbox": "^4.0.0",
70
- "hardhat": "^2.19.2"
70
+ "hardhat": "^2.19.3"
71
71
  }
72
72
  }
@@ -65,12 +65,6 @@ class AccountTrackerController
65
65
  this.blockTracker = blockTracker;
66
66
  this.ethersProvider = new BrowserProvider(this.provider, "any");
67
67
 
68
- // Initiate block tracker internal tracking.
69
- this.blockTracker.on("latest", (block: EthereumBlock) => {
70
- this.configure({ _currentBlock: block });
71
- this.refresh();
72
- });
73
-
74
68
  this.getIdentities = getIdentities;
75
69
  this.getCurrentChainId = getCurrentChainId;
76
70
 
@@ -79,6 +73,25 @@ class AccountTrackerController
79
73
  const refreshNeeded = this.syncAccounts();
80
74
  if (refreshNeeded) this.refresh();
81
75
  });
76
+ this.blockTrackerListener = this.blockTrackerListener.bind(this);
77
+ }
78
+
79
+ blockTrackerListener(block: EthereumBlock) {
80
+ this.configure({ _currentBlock: block });
81
+ this.refresh();
82
+ }
83
+
84
+ startPolling(): void {
85
+ this.stopPolling();
86
+ // Initiate block tracker internal tracking.
87
+ if (Object.keys(this.state.accounts).length > 0) {
88
+ // Adding this listener on block tracker triggers it to start polling.
89
+ this.blockTracker.on("latest", this.blockTrackerListener);
90
+ }
91
+ }
92
+
93
+ stopPolling(): void {
94
+ this.blockTracker.removeListener("latest", this.blockTrackerListener);
82
95
  }
83
96
 
84
97
  syncAccounts(): boolean {
@@ -1,26 +1,23 @@
1
1
  import { stripHexPrefix } from "@ethereumjs/util";
2
2
  import {
3
- ACTIVITY_ACTION_RECEIVE,
4
- ACTIVITY_ACTION_SEND,
5
- ACTIVITY_ACTION_TOPUP,
3
+ ACCOUNT_TYPE,
6
4
  BasePreferencesController,
7
5
  CustomNft,
8
6
  CustomToken,
7
+ InitPreferencesParams,
9
8
  IPreferencesController,
10
9
  PreferencesConfig,
11
10
  PreferencesState,
12
11
  TransactionStatus,
13
- UserInfo,
14
12
  } from "@toruslabs/base-controllers";
15
13
  import { get, patch, post, remove } from "@toruslabs/http-helpers";
16
14
  import { SafeEventEmitterProvider } from "@toruslabs/openlogin-jrpc";
17
15
  import { Mutex } from "async-mutex";
18
16
  import log from "loglevel";
19
17
 
20
- import PollingBlockTracker from "../Block/PollingBlockTracker";
21
18
  import KeyringController from "../Keyring/KeyringController";
22
19
  import NetworkController from "../Network/NetworkController";
23
- import { SUPPORTED_NETWORKS } from "../utils/constants";
20
+ import { ETHERSCAN_SUPPORTED_CHAINS, SUPPORTED_NETWORKS } from "../utils/constants";
24
21
  import { formatDate, formatPastTx, formatTime, getEthTxStatus } from "../utils/helpers";
25
22
  import type {
26
23
  AddChainMessageParams,
@@ -31,7 +28,6 @@ import type {
31
28
  EthereumProviderConfig,
32
29
  EthereumUser,
33
30
  ExtendedAddressPreferences,
34
- FetchCommonTransaction,
35
31
  FetchedTransaction,
36
32
  FormattedTransactionActivity,
37
33
  TransactionPayload,
@@ -41,8 +37,6 @@ interface IPreferencesControllerOptions {
41
37
  config?: Partial<PreferencesConfig> & Pick<PreferencesConfig, "api" | "commonApiHost" | "signInPrefix">;
42
38
  state?: Partial<PreferencesState<ExtendedAddressPreferences>>;
43
39
  provider: SafeEventEmitterProvider;
44
- // TODO: Require later
45
- blockTracker?: PollingBlockTracker;
46
40
  signAuthMessage?: KeyringController["signAuthMessage"];
47
41
  getProviderConfig?: NetworkController["getProviderConfig"];
48
42
  setProviderConfig?: NetworkController["setProviderConfig"];
@@ -62,15 +56,11 @@ export default class PreferencesController
62
56
 
63
57
  private provider: SafeEventEmitterProvider;
64
58
 
65
- private blockTracker: PollingBlockTracker;
66
-
67
- constructor({ config, state, provider, blockTracker, signAuthMessage, getProviderConfig, setProviderConfig }: IPreferencesControllerOptions) {
59
+ constructor({ config, state, provider, signAuthMessage, getProviderConfig, setProviderConfig }: IPreferencesControllerOptions) {
68
60
  super({ config, state, defaultPreferences: { formattedPastTransactions: [], fetchedPastTx: [], paymentTx: [] }, signAuthMessage });
69
61
  this.provider = provider;
70
62
  this.getProviderConfig = getProviderConfig;
71
63
  this.setProviderConfig = setProviderConfig;
72
- this.blockTracker = blockTracker;
73
- log.info(this.blockTracker);
74
64
  }
75
65
 
76
66
  public async poll(interval?: number): Promise<void> {
@@ -89,19 +79,9 @@ export default class PreferencesController
89
79
  }, this.config.pollInterval);
90
80
  }
91
81
 
92
- public async initPreferences(params: {
93
- address: string;
94
- jwtToken?: string;
95
- calledFromEmbed?: boolean;
96
- userInfo?: UserInfo;
97
- rehydrate?: boolean;
98
- locale?: string;
99
- type?: string;
100
- signatures?: string[];
101
- network?: string;
102
- }): Promise<void> {
103
- const { address, jwtToken, calledFromEmbed, userInfo, rehydrate, locale = "en-US", type, signatures, network } = params;
104
- await super.init(address, userInfo, jwtToken, { type, email: userInfo.email, signatures, network });
82
+ public async initPreferences(params: InitPreferencesParams): Promise<void> {
83
+ const { address, jwtToken, calledFromEmbed, userInfo, rehydrate, locale = "en-US", type, signatures, web3AuthClientId, web3AuthNetwork } = params;
84
+ await super.init({ address, userInfo, idToken: jwtToken, type, metadata: { email: userInfo.email, signatures } });
105
85
  const { aggregateVerifier, verifier, verifierId } = userInfo || {};
106
86
  const userExists = await this.sync(address);
107
87
  if (!userExists) {
@@ -113,10 +93,18 @@ export default class PreferencesController
113
93
  verifierId,
114
94
  locale,
115
95
  address,
96
+ type,
97
+ web3AuthNetwork,
116
98
  });
117
99
  }
118
- if (!rehydrate)
119
- await this.storeUserLogin({ verifier: aggregateVerifier || verifier, verifierId, options: { calledFromEmbed, rehydrate }, address });
100
+ await this.storeUserLogin({
101
+ verifier: aggregateVerifier || verifier,
102
+ verifierId,
103
+ options: { calledFromEmbed, rehydrate },
104
+ address,
105
+ web3AuthClientId,
106
+ web3AuthNetwork,
107
+ });
120
108
  }
121
109
 
122
110
  public getSelectedAddress(): string {
@@ -137,6 +125,7 @@ export default class PreferencesController
137
125
  customNetworks,
138
126
  customTokens,
139
127
  customNfts,
128
+ account_type: accountType,
140
129
  } = user || {};
141
130
 
142
131
  // update latest data in state.
@@ -150,6 +139,7 @@ export default class PreferencesController
150
139
  customTokens,
151
140
  customNfts,
152
141
  customNetworks,
142
+ accountType: accountType as ACCOUNT_TYPE,
153
143
  },
154
144
  address
155
145
  );
@@ -164,15 +154,9 @@ export default class PreferencesController
164
154
  this.getWalletOrders<FetchedTransaction>(address).catch((error) => {
165
155
  log.error("unable to fetch wallet orders", error);
166
156
  }),
167
- this.getTopUpOrders<FetchCommonTransaction>(address).catch((error) => {
168
- log.error("unable to fetch top up orders", error);
169
- }),
170
157
  ])
171
158
  .then((data) => {
172
- const [walletTx, paymentTx] = data;
173
- if (paymentTx) {
174
- this.calculatePaymentTx(paymentTx, address);
175
- }
159
+ const [walletTx] = data;
176
160
  // eslint-disable-next-line promise/always-return
177
161
  if (walletTx && walletTx.length > 0) {
178
162
  this.updateState({ fetchedPastTx: [...walletTx] }, address);
@@ -218,18 +202,16 @@ export default class PreferencesController
218
202
  public async refetchEtherscanTx(address?: string) {
219
203
  const selectedAddress = address || this.state.selectedAddress;
220
204
  if (this.getAddressState(selectedAddress)?.jwtToken) {
221
- // const selectedNetwork = this.getProviderConfig().rpcTarget;
222
- // if (ETHERSCAN_SUPPORTED_NETWORKS.has(selectedNetwork)) {
223
- // const data = await this.fetchEtherscanTx({ selectedAddress, selectedNetwork });
224
- // if (data.length) {
225
- // this.emit("addEtherscanTransactions", data, selectedNetwork);
226
- // }
227
- // }
205
+ const { chainId } = this.getProviderConfig();
206
+ if (ETHERSCAN_SUPPORTED_CHAINS.includes(chainId)) {
207
+ return this.fetchEtherscanTx({ selectedAddress, chainId: this.getProviderConfig().chainId });
208
+ }
228
209
  }
229
210
  }
230
211
 
231
- async fetchEtherscanTx<T>(parameters: { selectedAddress: string; selectedNetwork: string }): Promise<T[]> {
212
+ async fetchEtherscanTx<T>(parameters: { selectedAddress: string; chainId: string }): Promise<T[]> {
232
213
  try {
214
+ // TODO: rewrite this api to use chainId
233
215
  const url = new URL(`${this.config.api}/etherscan`);
234
216
  Object.keys(parameters).forEach((key) => url.searchParams.append(key, parameters[key as keyof typeof parameters]));
235
217
  const response = await get<{ success: boolean; data: T[] }>(url.href, this.headers(parameters.selectedAddress));
@@ -365,38 +347,6 @@ export default class PreferencesController
365
347
  }
366
348
  }
367
349
 
368
- private calculatePaymentTx(txs: FetchCommonTransaction[], address: string) {
369
- const accumulator: FetchCommonTransaction[] = [];
370
- for (const x of txs) {
371
- let action = "";
372
- const lowerCaseAction = x.action.toLowerCase();
373
- if (ACTIVITY_ACTION_TOPUP.includes(lowerCaseAction)) action = ACTIVITY_ACTION_TOPUP;
374
- else if (ACTIVITY_ACTION_SEND.includes(lowerCaseAction)) action = ACTIVITY_ACTION_SEND;
375
- else if (ACTIVITY_ACTION_RECEIVE.includes(lowerCaseAction)) action = ACTIVITY_ACTION_RECEIVE;
376
-
377
- accumulator.push({
378
- id: x.id,
379
- date: new Date(x.date).toDateString(),
380
- from: x.from,
381
- slicedFrom: x.slicedFrom,
382
- action,
383
- to: x.to,
384
- slicedTo: x.slicedTo,
385
- totalAmount: x.totalAmount,
386
- totalAmountString: x.totalAmountString,
387
- currencyAmount: x.currencyAmount,
388
- currencyAmountString: x.currencyAmountString,
389
- amount: x.amount,
390
- ethRate: x.ethRate,
391
- status: x.status.toLowerCase(),
392
- etherscanLink: x.etherscanLink || "",
393
- blockExplorerLink: "",
394
- currencyUsed: x.currencyUsed,
395
- });
396
- }
397
- this.updateState({ paymentTx: accumulator }, address);
398
- }
399
-
400
350
  private getChainOptions(address: string = this.state.selectedAddress): EthereumProviderConfig[] {
401
351
  const { identities } = this.state;
402
352
  const customNetworks = identities[address]?.customNetworks ?? [];