@metamask-previews/earn-controller 6.0.0-preview-50f93e3 → 6.0.0-preview-0b2bfc8a
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/CHANGELOG.md +0 -3
- package/dist/EarnController.cjs +21 -44
- package/dist/EarnController.cjs.map +1 -1
- package/dist/EarnController.d.cts +3 -4
- package/dist/EarnController.d.cts.map +1 -1
- package/dist/EarnController.d.mts +3 -4
- package/dist/EarnController.d.mts.map +1 -1
- package/dist/EarnController.mjs +21 -44
- package/dist/EarnController.mjs.map +1 -1
- package/package.json +1 -2
package/CHANGELOG.md
CHANGED
@@ -9,9 +9,6 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
9
9
|
|
10
10
|
### Changed
|
11
11
|
|
12
|
-
- **BREAKING:** Migrated from `AccountsController:getSelectedAccount` to `AccountTreeController:getAccountsFromSelectedAccountGroup` for retrieving BIP-44 selected account information ([#6402](https://github.com/MetaMask/core/pull/6402))
|
13
|
-
- **BREAKING:** Migrated from `AccountsController:selectedAccountChange` to `AccountTreeController:selectedAccountGroupChange` for BIP-44 account change management ([#6402](https://github.com/MetaMask/core/pull/6402))
|
14
|
-
- **BREAKING:** `EarnController` messenger must now allow `AccountTreeController:selectedAccountGroupChange` and `AccountTreeController:getAccountsFromSelectedAccountGroup` and must not allow `AccountsController:selectedAccountChange` and `AccountsController:getSelectedAccount` ([#6402](https://github.com/MetaMask/core/pull/6402))
|
15
12
|
- Bump `@metamask/base-controller` from `^8.1.0` to `^8.2.0` ([#6355](https://github.com/MetaMask/core/pull/6355))
|
16
13
|
|
17
14
|
## [6.0.0]
|
package/dist/EarnController.cjs
CHANGED
@@ -10,7 +10,7 @@ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (
|
|
10
10
|
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
11
11
|
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
12
12
|
};
|
13
|
-
var _EarnController_instances, _EarnController_earnSDK, _EarnController_selectedNetworkClientId, _EarnController_earnApiService, _EarnController_addTransactionFn, _EarnController_supportedPooledStakingChains, _EarnController_env, _EarnController_initializeSDK,
|
13
|
+
var _EarnController_instances, _EarnController_earnSDK, _EarnController_selectedNetworkClientId, _EarnController_earnApiService, _EarnController_addTransactionFn, _EarnController_supportedPooledStakingChains, _EarnController_env, _EarnController_initializeSDK, _EarnController_getCurrentAccount;
|
14
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
15
15
|
exports.EarnController = exports.getDefaultEarnControllerState = exports.DEFAULT_POOLED_STAKING_CHAIN_STATE = exports.DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES = exports.DEFAULT_LENDING_POSITION = exports.DEFAULT_LENDING_MARKET = exports.controllerName = void 0;
|
16
16
|
const providers_1 = require("@ethersproject/providers");
|
@@ -173,20 +173,19 @@ class EarnController extends base_controller_1.BaseController {
|
|
173
173
|
this.refreshLendingPositions().catch(console.error);
|
174
174
|
});
|
175
175
|
// Listen for account changes
|
176
|
-
this.messagingSystem.subscribe('
|
177
|
-
const address =
|
178
|
-
|
176
|
+
this.messagingSystem.subscribe('AccountsController:selectedAccountChange', (account) => {
|
177
|
+
const address = account?.address;
|
178
|
+
/**
|
179
|
+
* TEMP: There's a race condition where the account state isn't updated immediately.
|
180
|
+
* Until this has been fixed, we rely on the event payload for the latest account instead of #getCurrentAccount().
|
181
|
+
* Issue: https://github.com/MetaMask/accounts-planning/issues/887
|
182
|
+
*/
|
179
183
|
// TODO: temp solution, this will refresh lending eligibility also
|
180
184
|
// we could have a more general check, as what is happening is a compliance address check
|
181
185
|
this.refreshEarnEligibility({ address }).catch(console.error);
|
182
186
|
this.refreshPooledStakes({ address }).catch(console.error);
|
183
187
|
this.refreshLendingPositions({ address }).catch(console.error);
|
184
188
|
});
|
185
|
-
// test old account change code
|
186
|
-
this.messagingSystem.subscribe('AccountsController:selectedAccountChange', (account) => {
|
187
|
-
const address = account?.address;
|
188
|
-
throw new Error(`AccountsController:selectedAccountChange, address equals ${address}`);
|
189
|
-
});
|
190
189
|
// Listen for confirmed staking transactions
|
191
190
|
this.messagingSystem.subscribe('TransactionController:transactionConfirmed', (transactionMeta) => {
|
192
191
|
/**
|
@@ -220,7 +219,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
220
219
|
* @returns A promise that resolves when the stakes data has been updated
|
221
220
|
*/
|
222
221
|
async refreshPooledStakes({ resetCache = false, address, chainId = stake_sdk_1.ChainId.ETHEREUM, } = {}) {
|
223
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
222
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
224
223
|
if (!addressToUse) {
|
225
224
|
return;
|
226
225
|
}
|
@@ -249,7 +248,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
249
248
|
* @returns A promise that resolves when the eligibility status has been updated
|
250
249
|
*/
|
251
250
|
async refreshEarnEligibility({ address, } = {}) {
|
252
|
-
const addressToCheck = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
251
|
+
const addressToCheck = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
253
252
|
if (!addressToCheck) {
|
254
253
|
return;
|
255
254
|
}
|
@@ -388,7 +387,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
388
387
|
* @returns A promise that resolves when the lending positions have been updated
|
389
388
|
*/
|
390
389
|
async refreshLendingPositions({ address, } = {}) {
|
391
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
390
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
392
391
|
if (!addressToUse) {
|
393
392
|
return;
|
394
393
|
}
|
@@ -413,7 +412,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
413
412
|
* @returns A promise that resolves when the eligibility status has been updated
|
414
413
|
*/
|
415
414
|
async refreshLendingEligibility({ address, } = {}) {
|
416
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
415
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
417
416
|
// TODO: this is a temporary solution to refresh lending eligibility as
|
418
417
|
// the eligibility check is not yet implemented for lending
|
419
418
|
// this check will check the address against the same blocklist as the
|
@@ -470,7 +469,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
470
469
|
* @returns A promise that resolves when the lending position history has been updated
|
471
470
|
*/
|
472
471
|
getLendingPositionHistory({ address, chainId, positionId, marketId, marketAddress, protocol, days = 730, }) {
|
473
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
472
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
474
473
|
if (!addressToUse || !(0, stake_sdk_1.isSupportedLendingChain)(chainId)) {
|
475
474
|
return [];
|
476
475
|
}
|
@@ -507,10 +506,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
507
506
|
* @returns A promise that resolves to the transaction hash.
|
508
507
|
*/
|
509
508
|
async executeLendingDeposit({ amount, chainId, protocol, underlyingTokenAddress, gasOptions, txOptions, }) {
|
510
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
511
|
-
if (!address) {
|
512
|
-
throw new Error('No EVM-compatible account address found');
|
513
|
-
}
|
509
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
514
510
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeDepositTransactionData(amount, address, gasOptions);
|
515
511
|
if (!transactionData) {
|
516
512
|
throw new Error('Transaction data not found');
|
@@ -547,10 +543,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
547
543
|
* @returns A promise that resolves to the transaction hash.
|
548
544
|
*/
|
549
545
|
async executeLendingWithdraw({ amount, chainId, protocol, underlyingTokenAddress, gasOptions, txOptions, }) {
|
550
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
551
|
-
if (!address) {
|
552
|
-
throw new Error('No EVM-compatible account address found');
|
553
|
-
}
|
546
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
554
547
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(amount, address, gasOptions);
|
555
548
|
if (!transactionData) {
|
556
549
|
throw new Error('Transaction data not found');
|
@@ -587,10 +580,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
587
580
|
* @returns A promise that resolves to the transaction hash.
|
588
581
|
*/
|
589
582
|
async executeLendingTokenApprove({ protocol, amount, chainId, underlyingTokenAddress, gasOptions, txOptions, }) {
|
590
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
591
|
-
if (!address) {
|
592
|
-
throw new Error('No EVM-compatible account address found');
|
593
|
-
}
|
583
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
594
584
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(amount, address, gasOptions);
|
595
585
|
if (!transactionData) {
|
596
586
|
throw new Error('Transaction data not found');
|
@@ -620,10 +610,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
620
610
|
* @returns A promise that resolves to the allowance.
|
621
611
|
*/
|
622
612
|
async getLendingTokenAllowance(protocol, underlyingTokenAddress) {
|
623
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
624
|
-
if (!address) {
|
625
|
-
return undefined;
|
626
|
-
}
|
613
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
627
614
|
const allowance = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.underlyingTokenAllowance(address);
|
628
615
|
return allowance;
|
629
616
|
}
|
@@ -635,10 +622,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
635
622
|
* @returns A promise that resolves to the maximum withdraw amount.
|
636
623
|
*/
|
637
624
|
async getLendingTokenMaxWithdraw(protocol, underlyingTokenAddress) {
|
638
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
639
|
-
if (!address) {
|
640
|
-
return undefined;
|
641
|
-
}
|
625
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
642
626
|
const maxWithdraw = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.maxWithdraw(address);
|
643
627
|
return maxWithdraw;
|
644
628
|
}
|
@@ -650,10 +634,7 @@ class EarnController extends base_controller_1.BaseController {
|
|
650
634
|
* @returns A promise that resolves to the maximum deposit amount.
|
651
635
|
*/
|
652
636
|
async getLendingTokenMaxDeposit(protocol, underlyingTokenAddress) {
|
653
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
654
|
-
if (!address) {
|
655
|
-
return undefined;
|
656
|
-
}
|
637
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
657
638
|
const maxDeposit = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.maxDeposit(address);
|
658
639
|
return maxDeposit;
|
659
640
|
}
|
@@ -689,11 +670,7 @@ async function _EarnController_initializeSDK(networkClientId) {
|
|
689
670
|
console.error('Earn SDK initialization failed:', error);
|
690
671
|
}
|
691
672
|
}
|
692
|
-
},
|
693
|
-
return this.messagingSystem
|
694
|
-
.call('AccountTreeController:getAccountsFromSelectedAccountGroup')
|
695
|
-
.find((account) => account.type.startsWith('eip155:'));
|
696
|
-
}, _EarnController_getSelectedEvmAccountAddress = function _EarnController_getSelectedEvmAccountAddress() {
|
697
|
-
return __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getSelectedEvmAccount).call(this)?.address;
|
673
|
+
}, _EarnController_getCurrentAccount = function _EarnController_getCurrentAccount() {
|
674
|
+
return this.messagingSystem.call('AccountsController:getSelectedAccount');
|
698
675
|
};
|
699
676
|
//# sourceMappingURL=EarnController.cjs.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"EarnController.cjs","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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","sourcesContent":["import { Web3Provider } from '@ethersproject/providers';\nimport type {\n AccountTreeControllerGetAccountsFromSelectedAccountGroupAction,\n AccountTreeControllerSelectedAccountGroupChangeEvent,\n} from '@metamask/account-tree-controller';\nimport type { AccountsControllerSelectedAccountChangeEvent } from '@metamask/accounts-controller';\nimport type {\n ControllerGetStateAction,\n ControllerStateChangeEvent,\n RestrictedMessenger,\n StateMetadata,\n} from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { convertHexToDecimal, toHex } from '@metamask/controller-utils';\nimport type { InternalAccount } from '@metamask/keyring-internal-api';\nimport type {\n NetworkControllerGetNetworkClientByIdAction,\n NetworkControllerNetworkDidChangeEvent,\n NetworkState,\n} from '@metamask/network-controller';\nimport {\n EarnSdk,\n EarnApiService,\n isSupportedLendingChain,\n type LendingMarket,\n type PooledStake,\n type EarnSdkConfig,\n type VaultData,\n type VaultDailyApy,\n type VaultApyAverages,\n type LendingPosition,\n type GasLimitParams,\n type HistoricLendingMarketApys,\n EarnEnvironments,\n ChainId,\n isSupportedPooledStakingChain,\n} from '@metamask/stake-sdk';\nimport {\n type TransactionController,\n TransactionType,\n type TransactionControllerTransactionConfirmedEvent,\n type TransactionMeta,\n} from '@metamask/transaction-controller';\n\nimport type {\n RefreshEarnEligibilityOptions,\n RefreshLendingEligibilityOptions,\n RefreshLendingPositionsOptions,\n RefreshPooledStakesOptions,\n RefreshPooledStakingDataOptions,\n RefreshPooledStakingVaultDailyApysOptions,\n} from './types';\n\nexport const controllerName = 'EarnController';\n\nexport type PooledStakingState = {\n [chainId: number]: {\n pooledStakes: PooledStake;\n exchangeRate: string;\n vaultMetadata: VaultData;\n vaultDailyApys: VaultDailyApy[];\n vaultApyAverages: VaultApyAverages;\n };\n isEligible: boolean;\n};\n\nexport type LendingPositionWithMarket = LendingPosition & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\n// extends LendingPosition to include a marketId, marketAddress, and protocol reference\nexport type LendingPositionWithMarketReference = Omit<\n LendingPosition,\n 'market'\n> & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\nexport type LendingMarketWithPosition = LendingMarket & {\n position: LendingPositionWithMarketReference;\n};\n\nexport type LendingState = {\n markets: LendingMarket[]; // list of markets\n positions: LendingPositionWithMarketReference[]; // list of positions\n isEligible: boolean;\n};\n\ntype StakingTransactionTypes =\n | TransactionType.stakingDeposit\n | TransactionType.stakingUnstake\n | TransactionType.stakingClaim;\n\nconst stakingTransactionTypes = new Set<StakingTransactionTypes>([\n TransactionType.stakingDeposit,\n TransactionType.stakingUnstake,\n TransactionType.stakingClaim,\n]);\n\ntype LendingTransactionTypes =\n | TransactionType.lendingDeposit\n | TransactionType.lendingWithdraw;\n\nconst lendingTransactionTypes = new Set<LendingTransactionTypes>([\n TransactionType.lendingDeposit,\n TransactionType.lendingWithdraw,\n]);\n\n/**\n * Metadata for the EarnController.\n */\nconst earnControllerMetadata: StateMetadata<EarnControllerState> = {\n pooled_staking: {\n persist: true,\n anonymous: false,\n },\n lending: {\n persist: true,\n anonymous: false,\n },\n lastUpdated: {\n persist: false,\n anonymous: true,\n },\n};\n\n// === State Types ===\nexport type EarnControllerState = {\n pooled_staking: PooledStakingState;\n lending: LendingState;\n lastUpdated: number;\n};\n\n// === Default State ===\nexport const DEFAULT_LENDING_MARKET: LendingMarket = {\n id: '',\n chainId: 0,\n protocol: '' as LendingMarket['protocol'],\n name: '',\n address: '',\n tvlUnderlying: '0',\n netSupplyRate: 0,\n totalSupplyRate: 0,\n underlying: {\n address: '',\n chainId: 0,\n },\n outputToken: {\n address: '',\n chainId: 0,\n },\n rewards: [\n {\n token: {\n address: '',\n chainId: 0,\n },\n rate: 0,\n },\n ],\n};\n\nexport const DEFAULT_LENDING_POSITION: LendingPositionWithMarketReference = {\n id: '',\n chainId: 0,\n assets: '0',\n marketId: '',\n marketAddress: '',\n protocol: '',\n};\n\nexport const DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES: VaultApyAverages = {\n oneDay: '0',\n oneWeek: '0',\n oneMonth: '0',\n threeMonths: '0',\n sixMonths: '0',\n oneYear: '0',\n};\n\nexport const DEFAULT_POOLED_STAKING_CHAIN_STATE = {\n pooledStakes: {\n account: '',\n lifetimeRewards: '0',\n assets: '0',\n exitRequests: [],\n },\n exchangeRate: '1',\n vaultMetadata: {\n apy: '0',\n capacity: '0',\n feePercent: 0,\n totalAssets: '0',\n vaultAddress: '0x0000000000000000000000000000000000000000',\n },\n vaultDailyApys: [],\n vaultApyAverages: DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES,\n};\n\n/**\n * Gets the default state for the EarnController.\n *\n * @returns The default EarnController state.\n */\nexport function getDefaultEarnControllerState(): EarnControllerState {\n return {\n pooled_staking: {\n isEligible: false,\n },\n lending: {\n markets: [DEFAULT_LENDING_MARKET],\n positions: [DEFAULT_LENDING_POSITION],\n isEligible: false,\n },\n lastUpdated: 0,\n };\n}\n\n// === MESSENGER ===\n\n/**\n * The action which can be used to retrieve the state of the EarnController.\n */\nexport type EarnControllerGetStateAction = ControllerGetStateAction<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All actions that EarnController registers, to be called externally.\n */\nexport type EarnControllerActions = EarnControllerGetStateAction;\n\n/**\n * All actions that EarnController calls internally.\n */\nexport type AllowedActions =\n | NetworkControllerGetNetworkClientByIdAction\n | AccountTreeControllerGetAccountsFromSelectedAccountGroupAction;\n\n/**\n * The event that EarnController publishes when updating state.\n */\nexport type EarnControllerStateChangeEvent = ControllerStateChangeEvent<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All events that EarnController publishes, to be subscribed to externally.\n */\nexport type EarnControllerEvents = EarnControllerStateChangeEvent;\n\n/**\n * All events that EarnController subscribes to internally.\n */\nexport type AllowedEvents =\n | AccountTreeControllerSelectedAccountGroupChangeEvent\n | AccountsControllerSelectedAccountChangeEvent\n | TransactionControllerTransactionConfirmedEvent\n | NetworkControllerNetworkDidChangeEvent;\n\n/**\n * The messenger which is restricted to actions and events accessed by\n * EarnController.\n */\nexport type EarnControllerMessenger = RestrictedMessenger<\n typeof controllerName,\n EarnControllerActions | AllowedActions,\n EarnControllerEvents | AllowedEvents,\n AllowedActions['type'],\n AllowedEvents['type']\n>;\n\n// === CONTROLLER DEFINITION ===\n\n/**\n * EarnController manages DeFi earning opportunities across different protocols and chains.\n */\nexport class EarnController extends BaseController<\n typeof controllerName,\n EarnControllerState,\n EarnControllerMessenger\n> {\n #earnSDK: EarnSdk | null = null;\n\n #selectedNetworkClientId: string;\n\n readonly #earnApiService: EarnApiService;\n\n readonly #addTransactionFn: typeof TransactionController.prototype.addTransaction;\n\n readonly #supportedPooledStakingChains: number[];\n\n readonly #env: EarnEnvironments;\n\n constructor({\n messenger,\n state = {},\n addTransactionFn,\n selectedNetworkClientId,\n env = EarnEnvironments.PROD,\n }: {\n messenger: EarnControllerMessenger;\n state?: Partial<EarnControllerState>;\n addTransactionFn: typeof TransactionController.prototype.addTransaction;\n selectedNetworkClientId: string;\n env?: EarnEnvironments;\n }) {\n super({\n name: controllerName,\n metadata: earnControllerMetadata,\n messenger,\n state: {\n ...getDefaultEarnControllerState(),\n ...state,\n },\n });\n\n this.#env = env;\n\n this.#earnApiService = new EarnApiService(this.#env);\n\n // temporary array of supported chains\n // TODO: remove this once we export a supported chains list from the sdk\n // from sdk or api to get lending and pooled staking chains\n this.#supportedPooledStakingChains = [ChainId.ETHEREUM, ChainId.HOODI];\n\n this.#addTransactionFn = addTransactionFn;\n\n this.#selectedNetworkClientId = selectedNetworkClientId;\n\n this.#initializeSDK(selectedNetworkClientId).catch(console.error);\n this.refreshPooledStakingData().catch(console.error);\n this.refreshLendingData().catch(console.error);\n\n // Listen for network changes\n this.messagingSystem.subscribe(\n 'NetworkController:networkDidChange',\n (networkControllerState: NetworkState) => {\n this.#selectedNetworkClientId =\n networkControllerState.selectedNetworkClientId;\n\n this.#initializeSDK(this.#selectedNetworkClientId).catch(console.error);\n\n // refresh pooled staking data\n this.refreshPooledStakingVaultMetadata().catch(console.error);\n this.refreshPooledStakingVaultDailyApys().catch(console.error);\n this.refreshPooledStakingVaultApyAverages().catch(console.error);\n this.refreshPooledStakes().catch(console.error);\n\n // refresh lending data for all chains\n this.refreshLendingMarkets().catch(console.error);\n this.refreshLendingPositions().catch(console.error);\n },\n );\n\n // Listen for account changes\n this.messagingSystem.subscribe(\n 'AccountTreeController:selectedAccountGroupChange',\n () => {\n const address = this.#getSelectedEvmAccountAddress();\n throw new Error(\n `AccountTreeController:selectedAccountGroupChange, address equals ${address}`,\n );\n\n // TODO: temp solution, this will refresh lending eligibility also\n // we could have a more general check, as what is happening is a compliance address check\n this.refreshEarnEligibility({ address }).catch(console.error);\n this.refreshPooledStakes({ address }).catch(console.error);\n this.refreshLendingPositions({ address }).catch(console.error);\n },\n );\n\n // test old account change code\n this.messagingSystem.subscribe(\n 'AccountsController:selectedAccountChange',\n (account) => {\n const address = account?.address;\n throw new Error(\n `AccountsController:selectedAccountChange, address equals ${address}`,\n );\n },\n );\n\n // Listen for confirmed staking transactions\n this.messagingSystem.subscribe(\n 'TransactionController:transactionConfirmed',\n (transactionMeta: TransactionMeta) => {\n /**\n * When we speed up a transaction, we set the type as Retry and we lose\n * information about type of transaction that is being set up, so we use\n * original type to track that information.\n */\n const { type, originalType } = transactionMeta;\n\n const isStakingTransaction =\n stakingTransactionTypes.has(type as StakingTransactionTypes) ||\n stakingTransactionTypes.has(originalType as StakingTransactionTypes);\n\n const isLendingTransaction =\n lendingTransactionTypes.has(type as LendingTransactionTypes) ||\n lendingTransactionTypes.has(originalType as LendingTransactionTypes);\n\n const sender = transactionMeta.txParams.from;\n\n if (isStakingTransaction) {\n this.refreshPooledStakes({ resetCache: true, address: sender }).catch(\n console.error,\n );\n }\n if (isLendingTransaction) {\n this.refreshLendingPositions({ address: sender }).catch(\n console.error,\n );\n }\n },\n );\n }\n\n /**\n * Initializes the Earn SDK.\n *\n * @param networkClientId - The network client id to initialize the Earn SDK for.\n */\n async #initializeSDK(networkClientId: string) {\n const networkClient = this.messagingSystem.call(\n 'NetworkController:getNetworkClientById',\n networkClientId,\n );\n\n if (!networkClient?.provider) {\n this.#earnSDK = null;\n return;\n }\n\n const provider = new Web3Provider(networkClient.provider);\n const { chainId } = networkClient.configuration;\n\n // Initialize appropriate contracts based on chainId\n const config: EarnSdkConfig = {\n chainId: convertHexToDecimal(chainId),\n env: this.#env,\n };\n\n try {\n this.#earnSDK = await EarnSdk.create(provider, config);\n } catch (error) {\n this.#earnSDK = null;\n // Only log unexpected errors, not unsupported chain errors\n if (\n !(\n error instanceof Error &&\n error.message.includes('Unsupported chainId')\n )\n ) {\n console.error('Earn SDK initialization failed:', error);\n }\n }\n }\n\n /**\n * Gets the EVM account from the selected account group.\n *\n * @returns The EVM account or undefined if no EVM account is found.\n */\n #getSelectedEvmAccount(): InternalAccount | undefined {\n return this.messagingSystem\n .call('AccountTreeController:getAccountsFromSelectedAccountGroup')\n .find((account: InternalAccount) => account.type.startsWith('eip155:'));\n }\n\n /**\n * Gets the EVM account address from the selected account group.\n *\n * @returns The EVM account address or undefined if no EVM account is found.\n */\n #getSelectedEvmAccountAddress(): string | undefined {\n return this.#getSelectedEvmAccount()?.address;\n }\n\n /**\n * Refreshes the pooled stakes data for the current account.\n * Fetches updated stake information including lifetime rewards, assets, and exit requests\n * from the staking API service and updates the state.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @param [options.chainId] - The chain id to refresh pooled stakes for (optional).\n * @returns A promise that resolves when the stakes data has been updated\n */\n async refreshPooledStakes({\n resetCache = false,\n address,\n chainId = ChainId.ETHEREUM,\n }: RefreshPooledStakesOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse) {\n return;\n }\n\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const { accounts, exchangeRate } =\n await this.#earnApiService.pooledStaking.getPooledStakes(\n [addressToUse],\n chainIdToUse,\n resetCache,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n pooledStakes: accounts[0],\n exchangeRate,\n };\n });\n }\n\n /**\n * Refreshes the earn eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * Note: Pooled-staking and Lending used the same result since there isn't a need to split these up right now.\n *\n * @param options - Optional arguments\n * @param [options.address] - Address to refresh earn eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshEarnEligibility({\n address,\n }: RefreshEarnEligibilityOptions = {}): Promise<void> {\n const addressToCheck = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToCheck) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToCheck,\n ]);\n\n this.update((state) => {\n state.pooled_staking.isEligible = isEligible;\n state.lending.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes pooled staking vault metadata for the current chain.\n * Updates the vault metadata in the controller state including APY, capacity,\n * fee percentage, total assets, and vault address.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault metadata for (optional).\n * @returns A promise that resolves when the vault metadata has been updated\n */\n async refreshPooledStakingVaultMetadata(\n chainId: number = ChainId.ETHEREUM,\n ): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultMetadata =\n await this.#earnApiService.pooledStaking.getVaultData(chainIdToUse);\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultMetadata,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault daily apys for the current chain.\n * Updates the pooled staking vault daily apys controller state.\n *\n * @param [options] - The options for refreshing pooled staking vault daily apys.\n * @param [options.chainId] - The chain id to refresh pooled staking vault daily apys for (defaults to Ethereum).\n * @param [options.days] - The number of days to fetch pooled staking vault daily apys for (defaults to 365).\n * @param [options.order] - The order in which to fetch pooled staking vault daily apys. Descending order fetches the latest N days (latest working backwards). Ascending order fetches the oldest N days (oldest working forwards) (defaults to 'desc').\n * @returns A promise that resolves when the pooled staking vault daily apys have been updated.\n */\n async refreshPooledStakingVaultDailyApys({\n chainId = ChainId.ETHEREUM,\n days = 365,\n order = 'desc',\n }: RefreshPooledStakingVaultDailyApysOptions = {}): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultDailyApys =\n await this.#earnApiService.pooledStaking.getVaultDailyApys(\n chainIdToUse,\n days,\n order,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultDailyApys,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault apy averages for the current chain.\n * Updates the pooled staking vault apy averages controller state.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault apy averages for (optional).\n * @returns A promise that resolves when the pooled staking vault apy averages have been updated.\n */\n async refreshPooledStakingVaultApyAverages(\n chainId: number = ChainId.ETHEREUM,\n ) {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultApyAverages =\n await this.#earnApiService.pooledStaking.getVaultApyAverages(\n chainIdToUse,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultApyAverages,\n };\n });\n }\n\n /**\n * Refreshes all pooled staking related data including stakes, eligibility, and vault data.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshPooledStakingData({\n resetCache,\n address,\n }: RefreshPooledStakingDataOptions = {}): Promise<void> {\n const errors: Error[] = [];\n\n // Refresh earn eligibility once since it's not chain-specific\n await this.refreshEarnEligibility({ address }).catch((error) => {\n errors.push(error);\n });\n\n for (const chainId of this.#supportedPooledStakingChains) {\n await Promise.all([\n this.refreshPooledStakes({ resetCache, address, chainId }).catch(\n (error) => {\n errors.push(error);\n },\n ),\n this.refreshPooledStakingVaultMetadata(chainId).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultDailyApys({ chainId }).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultApyAverages(chainId).catch((error) => {\n errors.push(error);\n }),\n ]);\n }\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some staking data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Refreshes the lending markets data for all chains.\n * Updates the lending markets in the controller state.\n *\n * @returns A promise that resolves when the lending markets have been updated\n */\n async refreshLendingMarkets(): Promise<void> {\n const markets = await this.#earnApiService.lending.getMarkets();\n\n this.update((state) => {\n state.lending.markets = markets;\n });\n }\n\n /**\n * Refreshes the lending positions for the current account.\n * Updates the lending positions in the controller state.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending positions for (optional).\n * @returns A promise that resolves when the lending positions have been updated\n */\n async refreshLendingPositions({\n address,\n }: RefreshLendingPositionsOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse) {\n return;\n }\n\n // linter complaining about this not being a promise, but it is\n // TODO: figure out why this is not seen as a promise\n const positions = await Promise.resolve(\n this.#earnApiService.lending.getPositions(addressToUse),\n );\n\n this.update((state) => {\n state.lending.positions = positions.map((position) => ({\n ...position,\n marketId: position.market.id,\n marketAddress: position.market.address,\n protocol: position.market.protocol,\n }));\n });\n }\n\n /**\n * Refreshes the lending eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshLendingEligibility({\n address,\n }: RefreshLendingEligibilityOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n // TODO: this is a temporary solution to refresh lending eligibility as\n // the eligibility check is not yet implemented for lending\n // this check will check the address against the same blocklist as the\n // staking eligibility check\n\n if (!addressToUse) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToUse,\n ]);\n\n this.update((state) => {\n state.lending.isEligible = isEligible;\n state.pooled_staking.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes all lending related data including markets, positions, and eligibility.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshLendingData(): Promise<void> {\n const errors: Error[] = [];\n\n await Promise.all([\n this.refreshLendingMarkets().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingPositions().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingEligibility().catch((error) => {\n errors.push(error);\n }),\n ]);\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some lending data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Gets the lending position history for the current account.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to get lending position history for (optional).\n * @param options.chainId - The chain id to get lending position history for.\n * @param [options.positionId] - The position id to get lending position history for.\n * @param [options.marketId] - The market id to get lending position history for.\n * @param [options.marketAddress] - The market address to get lending position history for.\n * @param [options.protocol] - The protocol to get lending position history for.\n * @param [options.days] - The number of days to get lending position history for (optional).\n * @returns A promise that resolves when the lending position history has been updated\n */\n getLendingPositionHistory({\n address,\n chainId,\n positionId,\n marketId,\n marketAddress,\n protocol,\n days = 730,\n }: {\n address?: string;\n chainId: number;\n positionId: string;\n marketId: string;\n marketAddress: string;\n protocol: string;\n days?: number;\n }) {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse || !isSupportedLendingChain(chainId)) {\n return [];\n }\n\n return this.#earnApiService.lending.getPositionHistory(\n addressToUse,\n chainId,\n protocol,\n marketId,\n marketAddress,\n positionId,\n days,\n );\n }\n\n /**\n * Gets the lending market daily apys and averages for the current chain.\n *\n * @param options - Optional arguments\n * @param options.chainId - The chain id to get lending market daily apys and averages for.\n * @param [options.protocol] - The protocol to get lending market daily apys and averages for.\n * @param [options.marketId] - The market id to get lending market daily apys and averages for.\n * @param [options.days] - The number of days to get lending market daily apys and averages for (optional).\n * @returns A promise that resolves when the lending market daily apys and averages have been updated\n */\n getLendingMarketDailyApysAndAverages({\n chainId,\n protocol,\n marketId,\n days = 365,\n }: {\n chainId: number;\n protocol: string;\n marketId: string;\n days?: number;\n }): Promise<HistoricLendingMarketApys> | undefined {\n if (!isSupportedLendingChain(chainId)) {\n return undefined;\n }\n\n return this.#earnApiService.lending.getHistoricMarketApys(\n chainId,\n protocol,\n marketId,\n days,\n );\n }\n\n /**\n * Executes a lending deposit transaction.\n *\n * @param options - The options for the lending deposit transaction.\n * @param options.amount - The amount to deposit.\n * @param options.chainId - The chain ID for the lending deposit transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingDeposit({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeDepositTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending withdraw transaction.\n *\n * @param options - The options for the lending withdraw transaction.\n * @param options.amount - The amount to withdraw.\n * @param options.chainId - The chain ID for the lending withdraw transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingWithdraw({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending token approve transaction.\n *\n * @param options - The options for the lending token approve transaction.\n * @param options.amount - The amount to approve.\n * @param options.chainId - The chain ID for the lending token approve transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingTokenApprove({\n protocol,\n amount,\n chainId,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n protocol: LendingMarket['protocol'];\n amount: string;\n chainId: string;\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Gets the allowance for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the allowance.\n */\n async getLendingTokenAllowance(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const allowance =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.underlyingTokenAllowance(address);\n\n return allowance;\n }\n\n /**\n * Gets the maximum withdraw amount for a lending token's output token or shares if no output token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum withdraw amount.\n */\n async getLendingTokenMaxWithdraw(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const maxWithdraw =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxWithdraw(address);\n\n return maxWithdraw;\n }\n\n /**\n * Gets the maximum deposit amount for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum deposit amount.\n */\n async getLendingTokenMaxDeposit(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const maxDeposit =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxDeposit(address);\n\n return maxDeposit;\n }\n}\n"]}
|
1
|
+
{"version":3,"file":"EarnController.cjs","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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","sourcesContent":["import { Web3Provider } from '@ethersproject/providers';\nimport type {\n AccountsControllerGetSelectedAccountAction,\n AccountsControllerSelectedAccountChangeEvent,\n} from '@metamask/accounts-controller';\nimport type {\n ControllerGetStateAction,\n ControllerStateChangeEvent,\n RestrictedMessenger,\n StateMetadata,\n} from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { convertHexToDecimal, toHex } from '@metamask/controller-utils';\nimport type {\n NetworkControllerGetNetworkClientByIdAction,\n NetworkControllerNetworkDidChangeEvent,\n} from '@metamask/network-controller';\nimport {\n EarnSdk,\n EarnApiService,\n isSupportedLendingChain,\n type LendingMarket,\n type PooledStake,\n type EarnSdkConfig,\n type VaultData,\n type VaultDailyApy,\n type VaultApyAverages,\n type LendingPosition,\n type GasLimitParams,\n type HistoricLendingMarketApys,\n EarnEnvironments,\n ChainId,\n isSupportedPooledStakingChain,\n} from '@metamask/stake-sdk';\nimport {\n type TransactionController,\n TransactionType,\n type TransactionControllerTransactionConfirmedEvent,\n} from '@metamask/transaction-controller';\n\nimport type {\n RefreshEarnEligibilityOptions,\n RefreshLendingEligibilityOptions,\n RefreshLendingPositionsOptions,\n RefreshPooledStakesOptions,\n RefreshPooledStakingDataOptions,\n RefreshPooledStakingVaultDailyApysOptions,\n} from './types';\n\nexport const controllerName = 'EarnController';\n\nexport type PooledStakingState = {\n [chainId: number]: {\n pooledStakes: PooledStake;\n exchangeRate: string;\n vaultMetadata: VaultData;\n vaultDailyApys: VaultDailyApy[];\n vaultApyAverages: VaultApyAverages;\n };\n isEligible: boolean;\n};\n\nexport type LendingPositionWithMarket = LendingPosition & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\n// extends LendingPosition to include a marketId, marketAddress, and protocol reference\nexport type LendingPositionWithMarketReference = Omit<\n LendingPosition,\n 'market'\n> & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\nexport type LendingMarketWithPosition = LendingMarket & {\n position: LendingPositionWithMarketReference;\n};\n\nexport type LendingState = {\n markets: LendingMarket[]; // list of markets\n positions: LendingPositionWithMarketReference[]; // list of positions\n isEligible: boolean;\n};\n\ntype StakingTransactionTypes =\n | TransactionType.stakingDeposit\n | TransactionType.stakingUnstake\n | TransactionType.stakingClaim;\n\nconst stakingTransactionTypes = new Set<StakingTransactionTypes>([\n TransactionType.stakingDeposit,\n TransactionType.stakingUnstake,\n TransactionType.stakingClaim,\n]);\n\ntype LendingTransactionTypes =\n | TransactionType.lendingDeposit\n | TransactionType.lendingWithdraw;\n\nconst lendingTransactionTypes = new Set<LendingTransactionTypes>([\n TransactionType.lendingDeposit,\n TransactionType.lendingWithdraw,\n]);\n\n/**\n * Metadata for the EarnController.\n */\nconst earnControllerMetadata: StateMetadata<EarnControllerState> = {\n pooled_staking: {\n persist: true,\n anonymous: false,\n },\n lending: {\n persist: true,\n anonymous: false,\n },\n lastUpdated: {\n persist: false,\n anonymous: true,\n },\n};\n\n// === State Types ===\nexport type EarnControllerState = {\n pooled_staking: PooledStakingState;\n lending: LendingState;\n lastUpdated: number;\n};\n\n// === Default State ===\nexport const DEFAULT_LENDING_MARKET: LendingMarket = {\n id: '',\n chainId: 0,\n protocol: '' as LendingMarket['protocol'],\n name: '',\n address: '',\n tvlUnderlying: '0',\n netSupplyRate: 0,\n totalSupplyRate: 0,\n underlying: {\n address: '',\n chainId: 0,\n },\n outputToken: {\n address: '',\n chainId: 0,\n },\n rewards: [\n {\n token: {\n address: '',\n chainId: 0,\n },\n rate: 0,\n },\n ],\n};\n\nexport const DEFAULT_LENDING_POSITION: LendingPositionWithMarketReference = {\n id: '',\n chainId: 0,\n assets: '0',\n marketId: '',\n marketAddress: '',\n protocol: '',\n};\n\nexport const DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES: VaultApyAverages = {\n oneDay: '0',\n oneWeek: '0',\n oneMonth: '0',\n threeMonths: '0',\n sixMonths: '0',\n oneYear: '0',\n};\n\nexport const DEFAULT_POOLED_STAKING_CHAIN_STATE = {\n pooledStakes: {\n account: '',\n lifetimeRewards: '0',\n assets: '0',\n exitRequests: [],\n },\n exchangeRate: '1',\n vaultMetadata: {\n apy: '0',\n capacity: '0',\n feePercent: 0,\n totalAssets: '0',\n vaultAddress: '0x0000000000000000000000000000000000000000',\n },\n vaultDailyApys: [],\n vaultApyAverages: DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES,\n};\n\n/**\n * Gets the default state for the EarnController.\n *\n * @returns The default EarnController state.\n */\nexport function getDefaultEarnControllerState(): EarnControllerState {\n return {\n pooled_staking: {\n isEligible: false,\n },\n lending: {\n markets: [DEFAULT_LENDING_MARKET],\n positions: [DEFAULT_LENDING_POSITION],\n isEligible: false,\n },\n lastUpdated: 0,\n };\n}\n\n// === MESSENGER ===\n\n/**\n * The action which can be used to retrieve the state of the EarnController.\n */\nexport type EarnControllerGetStateAction = ControllerGetStateAction<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All actions that EarnController registers, to be called externally.\n */\nexport type EarnControllerActions = EarnControllerGetStateAction;\n\n/**\n * All actions that EarnController calls internally.\n */\nexport type AllowedActions =\n | NetworkControllerGetNetworkClientByIdAction\n | AccountsControllerGetSelectedAccountAction;\n\n/**\n * The event that EarnController publishes when updating state.\n */\nexport type EarnControllerStateChangeEvent = ControllerStateChangeEvent<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All events that EarnController publishes, to be subscribed to externally.\n */\nexport type EarnControllerEvents = EarnControllerStateChangeEvent;\n\n/**\n * All events that EarnController subscribes to internally.\n */\nexport type AllowedEvents =\n | AccountsControllerSelectedAccountChangeEvent\n | TransactionControllerTransactionConfirmedEvent\n | NetworkControllerNetworkDidChangeEvent;\n\n/**\n * The messenger which is restricted to actions and events accessed by\n * EarnController.\n */\nexport type EarnControllerMessenger = RestrictedMessenger<\n typeof controllerName,\n EarnControllerActions | AllowedActions,\n EarnControllerEvents | AllowedEvents,\n AllowedActions['type'],\n AllowedEvents['type']\n>;\n\n// === CONTROLLER DEFINITION ===\n\n/**\n * EarnController manages DeFi earning opportunities across different protocols and chains.\n */\nexport class EarnController extends BaseController<\n typeof controllerName,\n EarnControllerState,\n EarnControllerMessenger\n> {\n #earnSDK: EarnSdk | null = null;\n\n #selectedNetworkClientId: string;\n\n readonly #earnApiService: EarnApiService;\n\n readonly #addTransactionFn: typeof TransactionController.prototype.addTransaction;\n\n readonly #supportedPooledStakingChains: number[];\n\n readonly #env: EarnEnvironments;\n\n constructor({\n messenger,\n state = {},\n addTransactionFn,\n selectedNetworkClientId,\n env = EarnEnvironments.PROD,\n }: {\n messenger: EarnControllerMessenger;\n state?: Partial<EarnControllerState>;\n addTransactionFn: typeof TransactionController.prototype.addTransaction;\n selectedNetworkClientId: string;\n env?: EarnEnvironments;\n }) {\n super({\n name: controllerName,\n metadata: earnControllerMetadata,\n messenger,\n state: {\n ...getDefaultEarnControllerState(),\n ...state,\n },\n });\n\n this.#env = env;\n\n this.#earnApiService = new EarnApiService(this.#env);\n\n // temporary array of supported chains\n // TODO: remove this once we export a supported chains list from the sdk\n // from sdk or api to get lending and pooled staking chains\n this.#supportedPooledStakingChains = [ChainId.ETHEREUM, ChainId.HOODI];\n\n this.#addTransactionFn = addTransactionFn;\n\n this.#selectedNetworkClientId = selectedNetworkClientId;\n\n this.#initializeSDK(selectedNetworkClientId).catch(console.error);\n this.refreshPooledStakingData().catch(console.error);\n this.refreshLendingData().catch(console.error);\n\n // Listen for network changes\n this.messagingSystem.subscribe(\n 'NetworkController:networkDidChange',\n (networkControllerState) => {\n this.#selectedNetworkClientId =\n networkControllerState.selectedNetworkClientId;\n\n this.#initializeSDK(this.#selectedNetworkClientId).catch(console.error);\n\n // refresh pooled staking data\n this.refreshPooledStakingVaultMetadata().catch(console.error);\n this.refreshPooledStakingVaultDailyApys().catch(console.error);\n this.refreshPooledStakingVaultApyAverages().catch(console.error);\n this.refreshPooledStakes().catch(console.error);\n\n // refresh lending data for all chains\n this.refreshLendingMarkets().catch(console.error);\n this.refreshLendingPositions().catch(console.error);\n },\n );\n\n // Listen for account changes\n this.messagingSystem.subscribe(\n 'AccountsController:selectedAccountChange',\n (account) => {\n const address = account?.address;\n /**\n * TEMP: There's a race condition where the account state isn't updated immediately.\n * Until this has been fixed, we rely on the event payload for the latest account instead of #getCurrentAccount().\n * Issue: https://github.com/MetaMask/accounts-planning/issues/887\n */\n\n // TODO: temp solution, this will refresh lending eligibility also\n // we could have a more general check, as what is happening is a compliance address check\n this.refreshEarnEligibility({ address }).catch(console.error);\n this.refreshPooledStakes({ address }).catch(console.error);\n this.refreshLendingPositions({ address }).catch(console.error);\n },\n );\n\n // Listen for confirmed staking transactions\n this.messagingSystem.subscribe(\n 'TransactionController:transactionConfirmed',\n (transactionMeta) => {\n /**\n * When we speed up a transaction, we set the type as Retry and we lose\n * information about type of transaction that is being set up, so we use\n * original type to track that information.\n */\n const { type, originalType } = transactionMeta;\n\n const isStakingTransaction =\n stakingTransactionTypes.has(type as StakingTransactionTypes) ||\n stakingTransactionTypes.has(originalType as StakingTransactionTypes);\n\n const isLendingTransaction =\n lendingTransactionTypes.has(type as LendingTransactionTypes) ||\n lendingTransactionTypes.has(originalType as LendingTransactionTypes);\n\n const sender = transactionMeta.txParams.from;\n\n if (isStakingTransaction) {\n this.refreshPooledStakes({ resetCache: true, address: sender }).catch(\n console.error,\n );\n }\n if (isLendingTransaction) {\n this.refreshLendingPositions({ address: sender }).catch(\n console.error,\n );\n }\n },\n );\n }\n\n /**\n * Initializes the Earn SDK.\n *\n * @param networkClientId - The network client id to initialize the Earn SDK for.\n */\n async #initializeSDK(networkClientId: string) {\n const networkClient = this.messagingSystem.call(\n 'NetworkController:getNetworkClientById',\n networkClientId,\n );\n\n if (!networkClient?.provider) {\n this.#earnSDK = null;\n return;\n }\n\n const provider = new Web3Provider(networkClient.provider);\n const { chainId } = networkClient.configuration;\n\n // Initialize appropriate contracts based on chainId\n const config: EarnSdkConfig = {\n chainId: convertHexToDecimal(chainId),\n env: this.#env,\n };\n\n try {\n this.#earnSDK = await EarnSdk.create(provider, config);\n } catch (error) {\n this.#earnSDK = null;\n // Only log unexpected errors, not unsupported chain errors\n if (\n !(\n error instanceof Error &&\n error.message.includes('Unsupported chainId')\n )\n ) {\n console.error('Earn SDK initialization failed:', error);\n }\n }\n }\n\n /**\n * Gets the current account.\n *\n * @returns The current account.\n */\n #getCurrentAccount() {\n return this.messagingSystem.call('AccountsController:getSelectedAccount');\n }\n\n /**\n * Refreshes the pooled stakes data for the current account.\n * Fetches updated stake information including lifetime rewards, assets, and exit requests\n * from the staking API service and updates the state.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @param [options.chainId] - The chain id to refresh pooled stakes for (optional).\n * @returns A promise that resolves when the stakes data has been updated\n */\n async refreshPooledStakes({\n resetCache = false,\n address,\n chainId = ChainId.ETHEREUM,\n }: RefreshPooledStakesOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse) {\n return;\n }\n\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const { accounts, exchangeRate } =\n await this.#earnApiService.pooledStaking.getPooledStakes(\n [addressToUse],\n chainIdToUse,\n resetCache,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n pooledStakes: accounts[0],\n exchangeRate,\n };\n });\n }\n\n /**\n * Refreshes the earn eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * Note: Pooled-staking and Lending used the same result since there isn't a need to split these up right now.\n *\n * @param options - Optional arguments\n * @param [options.address] - Address to refresh earn eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshEarnEligibility({\n address,\n }: RefreshEarnEligibilityOptions = {}): Promise<void> {\n const addressToCheck = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToCheck) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToCheck,\n ]);\n\n this.update((state) => {\n state.pooled_staking.isEligible = isEligible;\n state.lending.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes pooled staking vault metadata for the current chain.\n * Updates the vault metadata in the controller state including APY, capacity,\n * fee percentage, total assets, and vault address.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault metadata for (optional).\n * @returns A promise that resolves when the vault metadata has been updated\n */\n async refreshPooledStakingVaultMetadata(\n chainId: number = ChainId.ETHEREUM,\n ): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultMetadata =\n await this.#earnApiService.pooledStaking.getVaultData(chainIdToUse);\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultMetadata,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault daily apys for the current chain.\n * Updates the pooled staking vault daily apys controller state.\n *\n * @param [options] - The options for refreshing pooled staking vault daily apys.\n * @param [options.chainId] - The chain id to refresh pooled staking vault daily apys for (defaults to Ethereum).\n * @param [options.days] - The number of days to fetch pooled staking vault daily apys for (defaults to 365).\n * @param [options.order] - The order in which to fetch pooled staking vault daily apys. Descending order fetches the latest N days (latest working backwards). Ascending order fetches the oldest N days (oldest working forwards) (defaults to 'desc').\n * @returns A promise that resolves when the pooled staking vault daily apys have been updated.\n */\n async refreshPooledStakingVaultDailyApys({\n chainId = ChainId.ETHEREUM,\n days = 365,\n order = 'desc',\n }: RefreshPooledStakingVaultDailyApysOptions = {}): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultDailyApys =\n await this.#earnApiService.pooledStaking.getVaultDailyApys(\n chainIdToUse,\n days,\n order,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultDailyApys,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault apy averages for the current chain.\n * Updates the pooled staking vault apy averages controller state.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault apy averages for (optional).\n * @returns A promise that resolves when the pooled staking vault apy averages have been updated.\n */\n async refreshPooledStakingVaultApyAverages(\n chainId: number = ChainId.ETHEREUM,\n ) {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultApyAverages =\n await this.#earnApiService.pooledStaking.getVaultApyAverages(\n chainIdToUse,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultApyAverages,\n };\n });\n }\n\n /**\n * Refreshes all pooled staking related data including stakes, eligibility, and vault data.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshPooledStakingData({\n resetCache,\n address,\n }: RefreshPooledStakingDataOptions = {}): Promise<void> {\n const errors: Error[] = [];\n\n // Refresh earn eligibility once since it's not chain-specific\n await this.refreshEarnEligibility({ address }).catch((error) => {\n errors.push(error);\n });\n\n for (const chainId of this.#supportedPooledStakingChains) {\n await Promise.all([\n this.refreshPooledStakes({ resetCache, address, chainId }).catch(\n (error) => {\n errors.push(error);\n },\n ),\n this.refreshPooledStakingVaultMetadata(chainId).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultDailyApys({ chainId }).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultApyAverages(chainId).catch((error) => {\n errors.push(error);\n }),\n ]);\n }\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some staking data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Refreshes the lending markets data for all chains.\n * Updates the lending markets in the controller state.\n *\n * @returns A promise that resolves when the lending markets have been updated\n */\n async refreshLendingMarkets(): Promise<void> {\n const markets = await this.#earnApiService.lending.getMarkets();\n\n this.update((state) => {\n state.lending.markets = markets;\n });\n }\n\n /**\n * Refreshes the lending positions for the current account.\n * Updates the lending positions in the controller state.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending positions for (optional).\n * @returns A promise that resolves when the lending positions have been updated\n */\n async refreshLendingPositions({\n address,\n }: RefreshLendingPositionsOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse) {\n return;\n }\n\n // linter complaining about this not being a promise, but it is\n // TODO: figure out why this is not seen as a promise\n const positions = await Promise.resolve(\n this.#earnApiService.lending.getPositions(addressToUse),\n );\n\n this.update((state) => {\n state.lending.positions = positions.map((position) => ({\n ...position,\n marketId: position.market.id,\n marketAddress: position.market.address,\n protocol: position.market.protocol,\n }));\n });\n }\n\n /**\n * Refreshes the lending eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshLendingEligibility({\n address,\n }: RefreshLendingEligibilityOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n // TODO: this is a temporary solution to refresh lending eligibility as\n // the eligibility check is not yet implemented for lending\n // this check will check the address against the same blocklist as the\n // staking eligibility check\n\n if (!addressToUse) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToUse,\n ]);\n\n this.update((state) => {\n state.lending.isEligible = isEligible;\n state.pooled_staking.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes all lending related data including markets, positions, and eligibility.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshLendingData(): Promise<void> {\n const errors: Error[] = [];\n\n await Promise.all([\n this.refreshLendingMarkets().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingPositions().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingEligibility().catch((error) => {\n errors.push(error);\n }),\n ]);\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some lending data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Gets the lending position history for the current account.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to get lending position history for (optional).\n * @param options.chainId - The chain id to get lending position history for.\n * @param [options.positionId] - The position id to get lending position history for.\n * @param [options.marketId] - The market id to get lending position history for.\n * @param [options.marketAddress] - The market address to get lending position history for.\n * @param [options.protocol] - The protocol to get lending position history for.\n * @param [options.days] - The number of days to get lending position history for (optional).\n * @returns A promise that resolves when the lending position history has been updated\n */\n getLendingPositionHistory({\n address,\n chainId,\n positionId,\n marketId,\n marketAddress,\n protocol,\n days = 730,\n }: {\n address?: string;\n chainId: number;\n positionId: string;\n marketId: string;\n marketAddress: string;\n protocol: string;\n days?: number;\n }) {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse || !isSupportedLendingChain(chainId)) {\n return [];\n }\n\n return this.#earnApiService.lending.getPositionHistory(\n addressToUse,\n chainId,\n protocol,\n marketId,\n marketAddress,\n positionId,\n days,\n );\n }\n\n /**\n * Gets the lending market daily apys and averages for the current chain.\n *\n * @param options - Optional arguments\n * @param options.chainId - The chain id to get lending market daily apys and averages for.\n * @param [options.protocol] - The protocol to get lending market daily apys and averages for.\n * @param [options.marketId] - The market id to get lending market daily apys and averages for.\n * @param [options.days] - The number of days to get lending market daily apys and averages for (optional).\n * @returns A promise that resolves when the lending market daily apys and averages have been updated\n */\n getLendingMarketDailyApysAndAverages({\n chainId,\n protocol,\n marketId,\n days = 365,\n }: {\n chainId: number;\n protocol: string;\n marketId: string;\n days?: number;\n }): Promise<HistoricLendingMarketApys> | undefined {\n if (!isSupportedLendingChain(chainId)) {\n return undefined;\n }\n\n return this.#earnApiService.lending.getHistoricMarketApys(\n chainId,\n protocol,\n marketId,\n days,\n );\n }\n\n /**\n * Executes a lending deposit transaction.\n *\n * @param options - The options for the lending deposit transaction.\n * @param options.amount - The amount to deposit.\n * @param options.chainId - The chain ID for the lending deposit transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingDeposit({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeDepositTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending withdraw transaction.\n *\n * @param options - The options for the lending withdraw transaction.\n * @param options.amount - The amount to withdraw.\n * @param options.chainId - The chain ID for the lending withdraw transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingWithdraw({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending token approve transaction.\n *\n * @param options - The options for the lending token approve transaction.\n * @param options.amount - The amount to approve.\n * @param options.chainId - The chain ID for the lending token approve transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingTokenApprove({\n protocol,\n amount,\n chainId,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n protocol: LendingMarket['protocol'];\n amount: string;\n chainId: string;\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Gets the allowance for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the allowance.\n */\n async getLendingTokenAllowance(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const allowance =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.underlyingTokenAllowance(address);\n\n return allowance;\n }\n\n /**\n * Gets the maximum withdraw amount for a lending token's output token or shares if no output token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum withdraw amount.\n */\n async getLendingTokenMaxWithdraw(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const maxWithdraw =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxWithdraw(address);\n\n return maxWithdraw;\n }\n\n /**\n * Gets the maximum deposit amount for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum deposit amount.\n */\n async getLendingTokenMaxDeposit(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const maxDeposit =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxDeposit(address);\n\n return maxDeposit;\n }\n}\n"]}
|
@@ -1,5 +1,4 @@
|
|
1
|
-
import type {
|
2
|
-
import type { AccountsControllerSelectedAccountChangeEvent } from "@metamask/accounts-controller";
|
1
|
+
import type { AccountsControllerGetSelectedAccountAction, AccountsControllerSelectedAccountChangeEvent } from "@metamask/accounts-controller";
|
3
2
|
import type { ControllerGetStateAction, ControllerStateChangeEvent, RestrictedMessenger } from "@metamask/base-controller";
|
4
3
|
import { BaseController } from "@metamask/base-controller";
|
5
4
|
import type { NetworkControllerGetNetworkClientByIdAction, NetworkControllerNetworkDidChangeEvent } from "@metamask/network-controller";
|
@@ -78,7 +77,7 @@ export type EarnControllerActions = EarnControllerGetStateAction;
|
|
78
77
|
/**
|
79
78
|
* All actions that EarnController calls internally.
|
80
79
|
*/
|
81
|
-
export type AllowedActions = NetworkControllerGetNetworkClientByIdAction |
|
80
|
+
export type AllowedActions = NetworkControllerGetNetworkClientByIdAction | AccountsControllerGetSelectedAccountAction;
|
82
81
|
/**
|
83
82
|
* The event that EarnController publishes when updating state.
|
84
83
|
*/
|
@@ -90,7 +89,7 @@ export type EarnControllerEvents = EarnControllerStateChangeEvent;
|
|
90
89
|
/**
|
91
90
|
* All events that EarnController subscribes to internally.
|
92
91
|
*/
|
93
|
-
export type AllowedEvents =
|
92
|
+
export type AllowedEvents = AccountsControllerSelectedAccountChangeEvent | TransactionControllerTransactionConfirmedEvent | NetworkControllerNetworkDidChangeEvent;
|
94
93
|
/**
|
95
94
|
* The messenger which is restricted to actions and events accessed by
|
96
95
|
* EarnController.
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"EarnController.d.cts","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,
|
1
|
+
{"version":3,"file":"EarnController.d.cts","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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"}
|
@@ -1,5 +1,4 @@
|
|
1
|
-
import type {
|
2
|
-
import type { AccountsControllerSelectedAccountChangeEvent } from "@metamask/accounts-controller";
|
1
|
+
import type { AccountsControllerGetSelectedAccountAction, AccountsControllerSelectedAccountChangeEvent } from "@metamask/accounts-controller";
|
3
2
|
import type { ControllerGetStateAction, ControllerStateChangeEvent, RestrictedMessenger } from "@metamask/base-controller";
|
4
3
|
import { BaseController } from "@metamask/base-controller";
|
5
4
|
import type { NetworkControllerGetNetworkClientByIdAction, NetworkControllerNetworkDidChangeEvent } from "@metamask/network-controller";
|
@@ -78,7 +77,7 @@ export type EarnControllerActions = EarnControllerGetStateAction;
|
|
78
77
|
/**
|
79
78
|
* All actions that EarnController calls internally.
|
80
79
|
*/
|
81
|
-
export type AllowedActions = NetworkControllerGetNetworkClientByIdAction |
|
80
|
+
export type AllowedActions = NetworkControllerGetNetworkClientByIdAction | AccountsControllerGetSelectedAccountAction;
|
82
81
|
/**
|
83
82
|
* The event that EarnController publishes when updating state.
|
84
83
|
*/
|
@@ -90,7 +89,7 @@ export type EarnControllerEvents = EarnControllerStateChangeEvent;
|
|
90
89
|
/**
|
91
90
|
* All events that EarnController subscribes to internally.
|
92
91
|
*/
|
93
|
-
export type AllowedEvents =
|
92
|
+
export type AllowedEvents = AccountsControllerSelectedAccountChangeEvent | TransactionControllerTransactionConfirmedEvent | NetworkControllerNetworkDidChangeEvent;
|
94
93
|
/**
|
95
94
|
* The messenger which is restricted to actions and events accessed by
|
96
95
|
* EarnController.
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"EarnController.d.mts","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,
|
1
|
+
{"version":3,"file":"EarnController.d.mts","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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"}
|
package/dist/EarnController.mjs
CHANGED
@@ -9,7 +9,7 @@ var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (
|
|
9
9
|
if (typeof state === "function" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError("Cannot read private member from an object whose class did not declare it");
|
10
10
|
return kind === "m" ? f : kind === "a" ? f.call(receiver) : f ? f.value : state.get(receiver);
|
11
11
|
};
|
12
|
-
var _EarnController_instances, _EarnController_earnSDK, _EarnController_selectedNetworkClientId, _EarnController_earnApiService, _EarnController_addTransactionFn, _EarnController_supportedPooledStakingChains, _EarnController_env, _EarnController_initializeSDK,
|
12
|
+
var _EarnController_instances, _EarnController_earnSDK, _EarnController_selectedNetworkClientId, _EarnController_earnApiService, _EarnController_addTransactionFn, _EarnController_supportedPooledStakingChains, _EarnController_env, _EarnController_initializeSDK, _EarnController_getCurrentAccount;
|
13
13
|
import { Web3Provider } from "@ethersproject/providers";
|
14
14
|
import { BaseController } from "@metamask/base-controller";
|
15
15
|
import { convertHexToDecimal, toHex } from "@metamask/controller-utils";
|
@@ -169,20 +169,19 @@ export class EarnController extends BaseController {
|
|
169
169
|
this.refreshLendingPositions().catch(console.error);
|
170
170
|
});
|
171
171
|
// Listen for account changes
|
172
|
-
this.messagingSystem.subscribe('
|
173
|
-
const address =
|
174
|
-
|
172
|
+
this.messagingSystem.subscribe('AccountsController:selectedAccountChange', (account) => {
|
173
|
+
const address = account?.address;
|
174
|
+
/**
|
175
|
+
* TEMP: There's a race condition where the account state isn't updated immediately.
|
176
|
+
* Until this has been fixed, we rely on the event payload for the latest account instead of #getCurrentAccount().
|
177
|
+
* Issue: https://github.com/MetaMask/accounts-planning/issues/887
|
178
|
+
*/
|
175
179
|
// TODO: temp solution, this will refresh lending eligibility also
|
176
180
|
// we could have a more general check, as what is happening is a compliance address check
|
177
181
|
this.refreshEarnEligibility({ address }).catch(console.error);
|
178
182
|
this.refreshPooledStakes({ address }).catch(console.error);
|
179
183
|
this.refreshLendingPositions({ address }).catch(console.error);
|
180
184
|
});
|
181
|
-
// test old account change code
|
182
|
-
this.messagingSystem.subscribe('AccountsController:selectedAccountChange', (account) => {
|
183
|
-
const address = account?.address;
|
184
|
-
throw new Error(`AccountsController:selectedAccountChange, address equals ${address}`);
|
185
|
-
});
|
186
185
|
// Listen for confirmed staking transactions
|
187
186
|
this.messagingSystem.subscribe('TransactionController:transactionConfirmed', (transactionMeta) => {
|
188
187
|
/**
|
@@ -216,7 +215,7 @@ export class EarnController extends BaseController {
|
|
216
215
|
* @returns A promise that resolves when the stakes data has been updated
|
217
216
|
*/
|
218
217
|
async refreshPooledStakes({ resetCache = false, address, chainId = ChainId.ETHEREUM, } = {}) {
|
219
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
218
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
220
219
|
if (!addressToUse) {
|
221
220
|
return;
|
222
221
|
}
|
@@ -245,7 +244,7 @@ export class EarnController extends BaseController {
|
|
245
244
|
* @returns A promise that resolves when the eligibility status has been updated
|
246
245
|
*/
|
247
246
|
async refreshEarnEligibility({ address, } = {}) {
|
248
|
-
const addressToCheck = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
247
|
+
const addressToCheck = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
249
248
|
if (!addressToCheck) {
|
250
249
|
return;
|
251
250
|
}
|
@@ -384,7 +383,7 @@ export class EarnController extends BaseController {
|
|
384
383
|
* @returns A promise that resolves when the lending positions have been updated
|
385
384
|
*/
|
386
385
|
async refreshLendingPositions({ address, } = {}) {
|
387
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
386
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
388
387
|
if (!addressToUse) {
|
389
388
|
return;
|
390
389
|
}
|
@@ -409,7 +408,7 @@ export class EarnController extends BaseController {
|
|
409
408
|
* @returns A promise that resolves when the eligibility status has been updated
|
410
409
|
*/
|
411
410
|
async refreshLendingEligibility({ address, } = {}) {
|
412
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
411
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
413
412
|
// TODO: this is a temporary solution to refresh lending eligibility as
|
414
413
|
// the eligibility check is not yet implemented for lending
|
415
414
|
// this check will check the address against the same blocklist as the
|
@@ -466,7 +465,7 @@ export class EarnController extends BaseController {
|
|
466
465
|
* @returns A promise that resolves when the lending position history has been updated
|
467
466
|
*/
|
468
467
|
getLendingPositionHistory({ address, chainId, positionId, marketId, marketAddress, protocol, days = 730, }) {
|
469
|
-
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m",
|
468
|
+
const addressToUse = address ?? __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
470
469
|
if (!addressToUse || !isSupportedLendingChain(chainId)) {
|
471
470
|
return [];
|
472
471
|
}
|
@@ -503,10 +502,7 @@ export class EarnController extends BaseController {
|
|
503
502
|
* @returns A promise that resolves to the transaction hash.
|
504
503
|
*/
|
505
504
|
async executeLendingDeposit({ amount, chainId, protocol, underlyingTokenAddress, gasOptions, txOptions, }) {
|
506
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
507
|
-
if (!address) {
|
508
|
-
throw new Error('No EVM-compatible account address found');
|
509
|
-
}
|
505
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
510
506
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeDepositTransactionData(amount, address, gasOptions);
|
511
507
|
if (!transactionData) {
|
512
508
|
throw new Error('Transaction data not found');
|
@@ -543,10 +539,7 @@ export class EarnController extends BaseController {
|
|
543
539
|
* @returns A promise that resolves to the transaction hash.
|
544
540
|
*/
|
545
541
|
async executeLendingWithdraw({ amount, chainId, protocol, underlyingTokenAddress, gasOptions, txOptions, }) {
|
546
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
547
|
-
if (!address) {
|
548
|
-
throw new Error('No EVM-compatible account address found');
|
549
|
-
}
|
542
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
550
543
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(amount, address, gasOptions);
|
551
544
|
if (!transactionData) {
|
552
545
|
throw new Error('Transaction data not found');
|
@@ -583,10 +576,7 @@ export class EarnController extends BaseController {
|
|
583
576
|
* @returns A promise that resolves to the transaction hash.
|
584
577
|
*/
|
585
578
|
async executeLendingTokenApprove({ protocol, amount, chainId, underlyingTokenAddress, gasOptions, txOptions, }) {
|
586
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
587
|
-
if (!address) {
|
588
|
-
throw new Error('No EVM-compatible account address found');
|
589
|
-
}
|
579
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
590
580
|
const transactionData = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(amount, address, gasOptions);
|
591
581
|
if (!transactionData) {
|
592
582
|
throw new Error('Transaction data not found');
|
@@ -616,10 +606,7 @@ export class EarnController extends BaseController {
|
|
616
606
|
* @returns A promise that resolves to the allowance.
|
617
607
|
*/
|
618
608
|
async getLendingTokenAllowance(protocol, underlyingTokenAddress) {
|
619
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
620
|
-
if (!address) {
|
621
|
-
return undefined;
|
622
|
-
}
|
609
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
623
610
|
const allowance = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.underlyingTokenAllowance(address);
|
624
611
|
return allowance;
|
625
612
|
}
|
@@ -631,10 +618,7 @@ export class EarnController extends BaseController {
|
|
631
618
|
* @returns A promise that resolves to the maximum withdraw amount.
|
632
619
|
*/
|
633
620
|
async getLendingTokenMaxWithdraw(protocol, underlyingTokenAddress) {
|
634
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
635
|
-
if (!address) {
|
636
|
-
return undefined;
|
637
|
-
}
|
621
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
638
622
|
const maxWithdraw = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.maxWithdraw(address);
|
639
623
|
return maxWithdraw;
|
640
624
|
}
|
@@ -646,10 +630,7 @@ export class EarnController extends BaseController {
|
|
646
630
|
* @returns A promise that resolves to the maximum deposit amount.
|
647
631
|
*/
|
648
632
|
async getLendingTokenMaxDeposit(protocol, underlyingTokenAddress) {
|
649
|
-
const address = __classPrivateFieldGet(this, _EarnController_instances, "m",
|
650
|
-
if (!address) {
|
651
|
-
return undefined;
|
652
|
-
}
|
633
|
+
const address = __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getCurrentAccount).call(this)?.address;
|
653
634
|
const maxDeposit = await __classPrivateFieldGet(this, _EarnController_earnSDK, "f")?.contracts?.lending?.[protocol]?.[underlyingTokenAddress]?.maxDeposit(address);
|
654
635
|
return maxDeposit;
|
655
636
|
}
|
@@ -684,11 +665,7 @@ async function _EarnController_initializeSDK(networkClientId) {
|
|
684
665
|
console.error('Earn SDK initialization failed:', error);
|
685
666
|
}
|
686
667
|
}
|
687
|
-
},
|
688
|
-
return this.messagingSystem
|
689
|
-
.call('AccountTreeController:getAccountsFromSelectedAccountGroup')
|
690
|
-
.find((account) => account.type.startsWith('eip155:'));
|
691
|
-
}, _EarnController_getSelectedEvmAccountAddress = function _EarnController_getSelectedEvmAccountAddress() {
|
692
|
-
return __classPrivateFieldGet(this, _EarnController_instances, "m", _EarnController_getSelectedEvmAccount).call(this)?.address;
|
668
|
+
}, _EarnController_getCurrentAccount = function _EarnController_getCurrentAccount() {
|
669
|
+
return this.messagingSystem.call('AccountsController:getSelectedAccount');
|
693
670
|
};
|
694
671
|
//# sourceMappingURL=EarnController.mjs.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"EarnController.mjs","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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","sourcesContent":["import { Web3Provider } from '@ethersproject/providers';\nimport type {\n AccountTreeControllerGetAccountsFromSelectedAccountGroupAction,\n AccountTreeControllerSelectedAccountGroupChangeEvent,\n} from '@metamask/account-tree-controller';\nimport type { AccountsControllerSelectedAccountChangeEvent } from '@metamask/accounts-controller';\nimport type {\n ControllerGetStateAction,\n ControllerStateChangeEvent,\n RestrictedMessenger,\n StateMetadata,\n} from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { convertHexToDecimal, toHex } from '@metamask/controller-utils';\nimport type { InternalAccount } from '@metamask/keyring-internal-api';\nimport type {\n NetworkControllerGetNetworkClientByIdAction,\n NetworkControllerNetworkDidChangeEvent,\n NetworkState,\n} from '@metamask/network-controller';\nimport {\n EarnSdk,\n EarnApiService,\n isSupportedLendingChain,\n type LendingMarket,\n type PooledStake,\n type EarnSdkConfig,\n type VaultData,\n type VaultDailyApy,\n type VaultApyAverages,\n type LendingPosition,\n type GasLimitParams,\n type HistoricLendingMarketApys,\n EarnEnvironments,\n ChainId,\n isSupportedPooledStakingChain,\n} from '@metamask/stake-sdk';\nimport {\n type TransactionController,\n TransactionType,\n type TransactionControllerTransactionConfirmedEvent,\n type TransactionMeta,\n} from '@metamask/transaction-controller';\n\nimport type {\n RefreshEarnEligibilityOptions,\n RefreshLendingEligibilityOptions,\n RefreshLendingPositionsOptions,\n RefreshPooledStakesOptions,\n RefreshPooledStakingDataOptions,\n RefreshPooledStakingVaultDailyApysOptions,\n} from './types';\n\nexport const controllerName = 'EarnController';\n\nexport type PooledStakingState = {\n [chainId: number]: {\n pooledStakes: PooledStake;\n exchangeRate: string;\n vaultMetadata: VaultData;\n vaultDailyApys: VaultDailyApy[];\n vaultApyAverages: VaultApyAverages;\n };\n isEligible: boolean;\n};\n\nexport type LendingPositionWithMarket = LendingPosition & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\n// extends LendingPosition to include a marketId, marketAddress, and protocol reference\nexport type LendingPositionWithMarketReference = Omit<\n LendingPosition,\n 'market'\n> & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\nexport type LendingMarketWithPosition = LendingMarket & {\n position: LendingPositionWithMarketReference;\n};\n\nexport type LendingState = {\n markets: LendingMarket[]; // list of markets\n positions: LendingPositionWithMarketReference[]; // list of positions\n isEligible: boolean;\n};\n\ntype StakingTransactionTypes =\n | TransactionType.stakingDeposit\n | TransactionType.stakingUnstake\n | TransactionType.stakingClaim;\n\nconst stakingTransactionTypes = new Set<StakingTransactionTypes>([\n TransactionType.stakingDeposit,\n TransactionType.stakingUnstake,\n TransactionType.stakingClaim,\n]);\n\ntype LendingTransactionTypes =\n | TransactionType.lendingDeposit\n | TransactionType.lendingWithdraw;\n\nconst lendingTransactionTypes = new Set<LendingTransactionTypes>([\n TransactionType.lendingDeposit,\n TransactionType.lendingWithdraw,\n]);\n\n/**\n * Metadata for the EarnController.\n */\nconst earnControllerMetadata: StateMetadata<EarnControllerState> = {\n pooled_staking: {\n persist: true,\n anonymous: false,\n },\n lending: {\n persist: true,\n anonymous: false,\n },\n lastUpdated: {\n persist: false,\n anonymous: true,\n },\n};\n\n// === State Types ===\nexport type EarnControllerState = {\n pooled_staking: PooledStakingState;\n lending: LendingState;\n lastUpdated: number;\n};\n\n// === Default State ===\nexport const DEFAULT_LENDING_MARKET: LendingMarket = {\n id: '',\n chainId: 0,\n protocol: '' as LendingMarket['protocol'],\n name: '',\n address: '',\n tvlUnderlying: '0',\n netSupplyRate: 0,\n totalSupplyRate: 0,\n underlying: {\n address: '',\n chainId: 0,\n },\n outputToken: {\n address: '',\n chainId: 0,\n },\n rewards: [\n {\n token: {\n address: '',\n chainId: 0,\n },\n rate: 0,\n },\n ],\n};\n\nexport const DEFAULT_LENDING_POSITION: LendingPositionWithMarketReference = {\n id: '',\n chainId: 0,\n assets: '0',\n marketId: '',\n marketAddress: '',\n protocol: '',\n};\n\nexport const DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES: VaultApyAverages = {\n oneDay: '0',\n oneWeek: '0',\n oneMonth: '0',\n threeMonths: '0',\n sixMonths: '0',\n oneYear: '0',\n};\n\nexport const DEFAULT_POOLED_STAKING_CHAIN_STATE = {\n pooledStakes: {\n account: '',\n lifetimeRewards: '0',\n assets: '0',\n exitRequests: [],\n },\n exchangeRate: '1',\n vaultMetadata: {\n apy: '0',\n capacity: '0',\n feePercent: 0,\n totalAssets: '0',\n vaultAddress: '0x0000000000000000000000000000000000000000',\n },\n vaultDailyApys: [],\n vaultApyAverages: DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES,\n};\n\n/**\n * Gets the default state for the EarnController.\n *\n * @returns The default EarnController state.\n */\nexport function getDefaultEarnControllerState(): EarnControllerState {\n return {\n pooled_staking: {\n isEligible: false,\n },\n lending: {\n markets: [DEFAULT_LENDING_MARKET],\n positions: [DEFAULT_LENDING_POSITION],\n isEligible: false,\n },\n lastUpdated: 0,\n };\n}\n\n// === MESSENGER ===\n\n/**\n * The action which can be used to retrieve the state of the EarnController.\n */\nexport type EarnControllerGetStateAction = ControllerGetStateAction<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All actions that EarnController registers, to be called externally.\n */\nexport type EarnControllerActions = EarnControllerGetStateAction;\n\n/**\n * All actions that EarnController calls internally.\n */\nexport type AllowedActions =\n | NetworkControllerGetNetworkClientByIdAction\n | AccountTreeControllerGetAccountsFromSelectedAccountGroupAction;\n\n/**\n * The event that EarnController publishes when updating state.\n */\nexport type EarnControllerStateChangeEvent = ControllerStateChangeEvent<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All events that EarnController publishes, to be subscribed to externally.\n */\nexport type EarnControllerEvents = EarnControllerStateChangeEvent;\n\n/**\n * All events that EarnController subscribes to internally.\n */\nexport type AllowedEvents =\n | AccountTreeControllerSelectedAccountGroupChangeEvent\n | AccountsControllerSelectedAccountChangeEvent\n | TransactionControllerTransactionConfirmedEvent\n | NetworkControllerNetworkDidChangeEvent;\n\n/**\n * The messenger which is restricted to actions and events accessed by\n * EarnController.\n */\nexport type EarnControllerMessenger = RestrictedMessenger<\n typeof controllerName,\n EarnControllerActions | AllowedActions,\n EarnControllerEvents | AllowedEvents,\n AllowedActions['type'],\n AllowedEvents['type']\n>;\n\n// === CONTROLLER DEFINITION ===\n\n/**\n * EarnController manages DeFi earning opportunities across different protocols and chains.\n */\nexport class EarnController extends BaseController<\n typeof controllerName,\n EarnControllerState,\n EarnControllerMessenger\n> {\n #earnSDK: EarnSdk | null = null;\n\n #selectedNetworkClientId: string;\n\n readonly #earnApiService: EarnApiService;\n\n readonly #addTransactionFn: typeof TransactionController.prototype.addTransaction;\n\n readonly #supportedPooledStakingChains: number[];\n\n readonly #env: EarnEnvironments;\n\n constructor({\n messenger,\n state = {},\n addTransactionFn,\n selectedNetworkClientId,\n env = EarnEnvironments.PROD,\n }: {\n messenger: EarnControllerMessenger;\n state?: Partial<EarnControllerState>;\n addTransactionFn: typeof TransactionController.prototype.addTransaction;\n selectedNetworkClientId: string;\n env?: EarnEnvironments;\n }) {\n super({\n name: controllerName,\n metadata: earnControllerMetadata,\n messenger,\n state: {\n ...getDefaultEarnControllerState(),\n ...state,\n },\n });\n\n this.#env = env;\n\n this.#earnApiService = new EarnApiService(this.#env);\n\n // temporary array of supported chains\n // TODO: remove this once we export a supported chains list from the sdk\n // from sdk or api to get lending and pooled staking chains\n this.#supportedPooledStakingChains = [ChainId.ETHEREUM, ChainId.HOODI];\n\n this.#addTransactionFn = addTransactionFn;\n\n this.#selectedNetworkClientId = selectedNetworkClientId;\n\n this.#initializeSDK(selectedNetworkClientId).catch(console.error);\n this.refreshPooledStakingData().catch(console.error);\n this.refreshLendingData().catch(console.error);\n\n // Listen for network changes\n this.messagingSystem.subscribe(\n 'NetworkController:networkDidChange',\n (networkControllerState: NetworkState) => {\n this.#selectedNetworkClientId =\n networkControllerState.selectedNetworkClientId;\n\n this.#initializeSDK(this.#selectedNetworkClientId).catch(console.error);\n\n // refresh pooled staking data\n this.refreshPooledStakingVaultMetadata().catch(console.error);\n this.refreshPooledStakingVaultDailyApys().catch(console.error);\n this.refreshPooledStakingVaultApyAverages().catch(console.error);\n this.refreshPooledStakes().catch(console.error);\n\n // refresh lending data for all chains\n this.refreshLendingMarkets().catch(console.error);\n this.refreshLendingPositions().catch(console.error);\n },\n );\n\n // Listen for account changes\n this.messagingSystem.subscribe(\n 'AccountTreeController:selectedAccountGroupChange',\n () => {\n const address = this.#getSelectedEvmAccountAddress();\n throw new Error(\n `AccountTreeController:selectedAccountGroupChange, address equals ${address}`,\n );\n\n // TODO: temp solution, this will refresh lending eligibility also\n // we could have a more general check, as what is happening is a compliance address check\n this.refreshEarnEligibility({ address }).catch(console.error);\n this.refreshPooledStakes({ address }).catch(console.error);\n this.refreshLendingPositions({ address }).catch(console.error);\n },\n );\n\n // test old account change code\n this.messagingSystem.subscribe(\n 'AccountsController:selectedAccountChange',\n (account) => {\n const address = account?.address;\n throw new Error(\n `AccountsController:selectedAccountChange, address equals ${address}`,\n );\n },\n );\n\n // Listen for confirmed staking transactions\n this.messagingSystem.subscribe(\n 'TransactionController:transactionConfirmed',\n (transactionMeta: TransactionMeta) => {\n /**\n * When we speed up a transaction, we set the type as Retry and we lose\n * information about type of transaction that is being set up, so we use\n * original type to track that information.\n */\n const { type, originalType } = transactionMeta;\n\n const isStakingTransaction =\n stakingTransactionTypes.has(type as StakingTransactionTypes) ||\n stakingTransactionTypes.has(originalType as StakingTransactionTypes);\n\n const isLendingTransaction =\n lendingTransactionTypes.has(type as LendingTransactionTypes) ||\n lendingTransactionTypes.has(originalType as LendingTransactionTypes);\n\n const sender = transactionMeta.txParams.from;\n\n if (isStakingTransaction) {\n this.refreshPooledStakes({ resetCache: true, address: sender }).catch(\n console.error,\n );\n }\n if (isLendingTransaction) {\n this.refreshLendingPositions({ address: sender }).catch(\n console.error,\n );\n }\n },\n );\n }\n\n /**\n * Initializes the Earn SDK.\n *\n * @param networkClientId - The network client id to initialize the Earn SDK for.\n */\n async #initializeSDK(networkClientId: string) {\n const networkClient = this.messagingSystem.call(\n 'NetworkController:getNetworkClientById',\n networkClientId,\n );\n\n if (!networkClient?.provider) {\n this.#earnSDK = null;\n return;\n }\n\n const provider = new Web3Provider(networkClient.provider);\n const { chainId } = networkClient.configuration;\n\n // Initialize appropriate contracts based on chainId\n const config: EarnSdkConfig = {\n chainId: convertHexToDecimal(chainId),\n env: this.#env,\n };\n\n try {\n this.#earnSDK = await EarnSdk.create(provider, config);\n } catch (error) {\n this.#earnSDK = null;\n // Only log unexpected errors, not unsupported chain errors\n if (\n !(\n error instanceof Error &&\n error.message.includes('Unsupported chainId')\n )\n ) {\n console.error('Earn SDK initialization failed:', error);\n }\n }\n }\n\n /**\n * Gets the EVM account from the selected account group.\n *\n * @returns The EVM account or undefined if no EVM account is found.\n */\n #getSelectedEvmAccount(): InternalAccount | undefined {\n return this.messagingSystem\n .call('AccountTreeController:getAccountsFromSelectedAccountGroup')\n .find((account: InternalAccount) => account.type.startsWith('eip155:'));\n }\n\n /**\n * Gets the EVM account address from the selected account group.\n *\n * @returns The EVM account address or undefined if no EVM account is found.\n */\n #getSelectedEvmAccountAddress(): string | undefined {\n return this.#getSelectedEvmAccount()?.address;\n }\n\n /**\n * Refreshes the pooled stakes data for the current account.\n * Fetches updated stake information including lifetime rewards, assets, and exit requests\n * from the staking API service and updates the state.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @param [options.chainId] - The chain id to refresh pooled stakes for (optional).\n * @returns A promise that resolves when the stakes data has been updated\n */\n async refreshPooledStakes({\n resetCache = false,\n address,\n chainId = ChainId.ETHEREUM,\n }: RefreshPooledStakesOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse) {\n return;\n }\n\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const { accounts, exchangeRate } =\n await this.#earnApiService.pooledStaking.getPooledStakes(\n [addressToUse],\n chainIdToUse,\n resetCache,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n pooledStakes: accounts[0],\n exchangeRate,\n };\n });\n }\n\n /**\n * Refreshes the earn eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * Note: Pooled-staking and Lending used the same result since there isn't a need to split these up right now.\n *\n * @param options - Optional arguments\n * @param [options.address] - Address to refresh earn eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshEarnEligibility({\n address,\n }: RefreshEarnEligibilityOptions = {}): Promise<void> {\n const addressToCheck = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToCheck) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToCheck,\n ]);\n\n this.update((state) => {\n state.pooled_staking.isEligible = isEligible;\n state.lending.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes pooled staking vault metadata for the current chain.\n * Updates the vault metadata in the controller state including APY, capacity,\n * fee percentage, total assets, and vault address.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault metadata for (optional).\n * @returns A promise that resolves when the vault metadata has been updated\n */\n async refreshPooledStakingVaultMetadata(\n chainId: number = ChainId.ETHEREUM,\n ): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultMetadata =\n await this.#earnApiService.pooledStaking.getVaultData(chainIdToUse);\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultMetadata,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault daily apys for the current chain.\n * Updates the pooled staking vault daily apys controller state.\n *\n * @param [options] - The options for refreshing pooled staking vault daily apys.\n * @param [options.chainId] - The chain id to refresh pooled staking vault daily apys for (defaults to Ethereum).\n * @param [options.days] - The number of days to fetch pooled staking vault daily apys for (defaults to 365).\n * @param [options.order] - The order in which to fetch pooled staking vault daily apys. Descending order fetches the latest N days (latest working backwards). Ascending order fetches the oldest N days (oldest working forwards) (defaults to 'desc').\n * @returns A promise that resolves when the pooled staking vault daily apys have been updated.\n */\n async refreshPooledStakingVaultDailyApys({\n chainId = ChainId.ETHEREUM,\n days = 365,\n order = 'desc',\n }: RefreshPooledStakingVaultDailyApysOptions = {}): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultDailyApys =\n await this.#earnApiService.pooledStaking.getVaultDailyApys(\n chainIdToUse,\n days,\n order,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultDailyApys,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault apy averages for the current chain.\n * Updates the pooled staking vault apy averages controller state.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault apy averages for (optional).\n * @returns A promise that resolves when the pooled staking vault apy averages have been updated.\n */\n async refreshPooledStakingVaultApyAverages(\n chainId: number = ChainId.ETHEREUM,\n ) {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultApyAverages =\n await this.#earnApiService.pooledStaking.getVaultApyAverages(\n chainIdToUse,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultApyAverages,\n };\n });\n }\n\n /**\n * Refreshes all pooled staking related data including stakes, eligibility, and vault data.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshPooledStakingData({\n resetCache,\n address,\n }: RefreshPooledStakingDataOptions = {}): Promise<void> {\n const errors: Error[] = [];\n\n // Refresh earn eligibility once since it's not chain-specific\n await this.refreshEarnEligibility({ address }).catch((error) => {\n errors.push(error);\n });\n\n for (const chainId of this.#supportedPooledStakingChains) {\n await Promise.all([\n this.refreshPooledStakes({ resetCache, address, chainId }).catch(\n (error) => {\n errors.push(error);\n },\n ),\n this.refreshPooledStakingVaultMetadata(chainId).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultDailyApys({ chainId }).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultApyAverages(chainId).catch((error) => {\n errors.push(error);\n }),\n ]);\n }\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some staking data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Refreshes the lending markets data for all chains.\n * Updates the lending markets in the controller state.\n *\n * @returns A promise that resolves when the lending markets have been updated\n */\n async refreshLendingMarkets(): Promise<void> {\n const markets = await this.#earnApiService.lending.getMarkets();\n\n this.update((state) => {\n state.lending.markets = markets;\n });\n }\n\n /**\n * Refreshes the lending positions for the current account.\n * Updates the lending positions in the controller state.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending positions for (optional).\n * @returns A promise that resolves when the lending positions have been updated\n */\n async refreshLendingPositions({\n address,\n }: RefreshLendingPositionsOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse) {\n return;\n }\n\n // linter complaining about this not being a promise, but it is\n // TODO: figure out why this is not seen as a promise\n const positions = await Promise.resolve(\n this.#earnApiService.lending.getPositions(addressToUse),\n );\n\n this.update((state) => {\n state.lending.positions = positions.map((position) => ({\n ...position,\n marketId: position.market.id,\n marketAddress: position.market.address,\n protocol: position.market.protocol,\n }));\n });\n }\n\n /**\n * Refreshes the lending eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshLendingEligibility({\n address,\n }: RefreshLendingEligibilityOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n // TODO: this is a temporary solution to refresh lending eligibility as\n // the eligibility check is not yet implemented for lending\n // this check will check the address against the same blocklist as the\n // staking eligibility check\n\n if (!addressToUse) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToUse,\n ]);\n\n this.update((state) => {\n state.lending.isEligible = isEligible;\n state.pooled_staking.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes all lending related data including markets, positions, and eligibility.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshLendingData(): Promise<void> {\n const errors: Error[] = [];\n\n await Promise.all([\n this.refreshLendingMarkets().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingPositions().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingEligibility().catch((error) => {\n errors.push(error);\n }),\n ]);\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some lending data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Gets the lending position history for the current account.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to get lending position history for (optional).\n * @param options.chainId - The chain id to get lending position history for.\n * @param [options.positionId] - The position id to get lending position history for.\n * @param [options.marketId] - The market id to get lending position history for.\n * @param [options.marketAddress] - The market address to get lending position history for.\n * @param [options.protocol] - The protocol to get lending position history for.\n * @param [options.days] - The number of days to get lending position history for (optional).\n * @returns A promise that resolves when the lending position history has been updated\n */\n getLendingPositionHistory({\n address,\n chainId,\n positionId,\n marketId,\n marketAddress,\n protocol,\n days = 730,\n }: {\n address?: string;\n chainId: number;\n positionId: string;\n marketId: string;\n marketAddress: string;\n protocol: string;\n days?: number;\n }) {\n const addressToUse = address ?? this.#getSelectedEvmAccountAddress();\n\n if (!addressToUse || !isSupportedLendingChain(chainId)) {\n return [];\n }\n\n return this.#earnApiService.lending.getPositionHistory(\n addressToUse,\n chainId,\n protocol,\n marketId,\n marketAddress,\n positionId,\n days,\n );\n }\n\n /**\n * Gets the lending market daily apys and averages for the current chain.\n *\n * @param options - Optional arguments\n * @param options.chainId - The chain id to get lending market daily apys and averages for.\n * @param [options.protocol] - The protocol to get lending market daily apys and averages for.\n * @param [options.marketId] - The market id to get lending market daily apys and averages for.\n * @param [options.days] - The number of days to get lending market daily apys and averages for (optional).\n * @returns A promise that resolves when the lending market daily apys and averages have been updated\n */\n getLendingMarketDailyApysAndAverages({\n chainId,\n protocol,\n marketId,\n days = 365,\n }: {\n chainId: number;\n protocol: string;\n marketId: string;\n days?: number;\n }): Promise<HistoricLendingMarketApys> | undefined {\n if (!isSupportedLendingChain(chainId)) {\n return undefined;\n }\n\n return this.#earnApiService.lending.getHistoricMarketApys(\n chainId,\n protocol,\n marketId,\n days,\n );\n }\n\n /**\n * Executes a lending deposit transaction.\n *\n * @param options - The options for the lending deposit transaction.\n * @param options.amount - The amount to deposit.\n * @param options.chainId - The chain ID for the lending deposit transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingDeposit({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeDepositTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending withdraw transaction.\n *\n * @param options - The options for the lending withdraw transaction.\n * @param options.amount - The amount to withdraw.\n * @param options.chainId - The chain ID for the lending withdraw transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingWithdraw({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending token approve transaction.\n *\n * @param options - The options for the lending token approve transaction.\n * @param options.amount - The amount to approve.\n * @param options.chainId - The chain ID for the lending token approve transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingTokenApprove({\n protocol,\n amount,\n chainId,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n protocol: LendingMarket['protocol'];\n amount: string;\n chainId: string;\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n throw new Error('No EVM-compatible account address found');\n }\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Gets the allowance for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the allowance.\n */\n async getLendingTokenAllowance(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const allowance =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.underlyingTokenAllowance(address);\n\n return allowance;\n }\n\n /**\n * Gets the maximum withdraw amount for a lending token's output token or shares if no output token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum withdraw amount.\n */\n async getLendingTokenMaxWithdraw(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const maxWithdraw =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxWithdraw(address);\n\n return maxWithdraw;\n }\n\n /**\n * Gets the maximum deposit amount for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum deposit amount.\n */\n async getLendingTokenMaxDeposit(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getSelectedEvmAccountAddress();\n\n if (!address) {\n return undefined;\n }\n\n const maxDeposit =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxDeposit(address);\n\n return maxDeposit;\n }\n}\n"]}
|
1
|
+
{"version":3,"file":"EarnController.mjs","sourceRoot":"","sources":["../src/EarnController.ts"],"names":[],"mappings":"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","sourcesContent":["import { Web3Provider } from '@ethersproject/providers';\nimport type {\n AccountsControllerGetSelectedAccountAction,\n AccountsControllerSelectedAccountChangeEvent,\n} from '@metamask/accounts-controller';\nimport type {\n ControllerGetStateAction,\n ControllerStateChangeEvent,\n RestrictedMessenger,\n StateMetadata,\n} from '@metamask/base-controller';\nimport { BaseController } from '@metamask/base-controller';\nimport { convertHexToDecimal, toHex } from '@metamask/controller-utils';\nimport type {\n NetworkControllerGetNetworkClientByIdAction,\n NetworkControllerNetworkDidChangeEvent,\n} from '@metamask/network-controller';\nimport {\n EarnSdk,\n EarnApiService,\n isSupportedLendingChain,\n type LendingMarket,\n type PooledStake,\n type EarnSdkConfig,\n type VaultData,\n type VaultDailyApy,\n type VaultApyAverages,\n type LendingPosition,\n type GasLimitParams,\n type HistoricLendingMarketApys,\n EarnEnvironments,\n ChainId,\n isSupportedPooledStakingChain,\n} from '@metamask/stake-sdk';\nimport {\n type TransactionController,\n TransactionType,\n type TransactionControllerTransactionConfirmedEvent,\n} from '@metamask/transaction-controller';\n\nimport type {\n RefreshEarnEligibilityOptions,\n RefreshLendingEligibilityOptions,\n RefreshLendingPositionsOptions,\n RefreshPooledStakesOptions,\n RefreshPooledStakingDataOptions,\n RefreshPooledStakingVaultDailyApysOptions,\n} from './types';\n\nexport const controllerName = 'EarnController';\n\nexport type PooledStakingState = {\n [chainId: number]: {\n pooledStakes: PooledStake;\n exchangeRate: string;\n vaultMetadata: VaultData;\n vaultDailyApys: VaultDailyApy[];\n vaultApyAverages: VaultApyAverages;\n };\n isEligible: boolean;\n};\n\nexport type LendingPositionWithMarket = LendingPosition & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\n// extends LendingPosition to include a marketId, marketAddress, and protocol reference\nexport type LendingPositionWithMarketReference = Omit<\n LendingPosition,\n 'market'\n> & {\n marketId: string;\n marketAddress: string;\n protocol: string;\n};\n\nexport type LendingMarketWithPosition = LendingMarket & {\n position: LendingPositionWithMarketReference;\n};\n\nexport type LendingState = {\n markets: LendingMarket[]; // list of markets\n positions: LendingPositionWithMarketReference[]; // list of positions\n isEligible: boolean;\n};\n\ntype StakingTransactionTypes =\n | TransactionType.stakingDeposit\n | TransactionType.stakingUnstake\n | TransactionType.stakingClaim;\n\nconst stakingTransactionTypes = new Set<StakingTransactionTypes>([\n TransactionType.stakingDeposit,\n TransactionType.stakingUnstake,\n TransactionType.stakingClaim,\n]);\n\ntype LendingTransactionTypes =\n | TransactionType.lendingDeposit\n | TransactionType.lendingWithdraw;\n\nconst lendingTransactionTypes = new Set<LendingTransactionTypes>([\n TransactionType.lendingDeposit,\n TransactionType.lendingWithdraw,\n]);\n\n/**\n * Metadata for the EarnController.\n */\nconst earnControllerMetadata: StateMetadata<EarnControllerState> = {\n pooled_staking: {\n persist: true,\n anonymous: false,\n },\n lending: {\n persist: true,\n anonymous: false,\n },\n lastUpdated: {\n persist: false,\n anonymous: true,\n },\n};\n\n// === State Types ===\nexport type EarnControllerState = {\n pooled_staking: PooledStakingState;\n lending: LendingState;\n lastUpdated: number;\n};\n\n// === Default State ===\nexport const DEFAULT_LENDING_MARKET: LendingMarket = {\n id: '',\n chainId: 0,\n protocol: '' as LendingMarket['protocol'],\n name: '',\n address: '',\n tvlUnderlying: '0',\n netSupplyRate: 0,\n totalSupplyRate: 0,\n underlying: {\n address: '',\n chainId: 0,\n },\n outputToken: {\n address: '',\n chainId: 0,\n },\n rewards: [\n {\n token: {\n address: '',\n chainId: 0,\n },\n rate: 0,\n },\n ],\n};\n\nexport const DEFAULT_LENDING_POSITION: LendingPositionWithMarketReference = {\n id: '',\n chainId: 0,\n assets: '0',\n marketId: '',\n marketAddress: '',\n protocol: '',\n};\n\nexport const DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES: VaultApyAverages = {\n oneDay: '0',\n oneWeek: '0',\n oneMonth: '0',\n threeMonths: '0',\n sixMonths: '0',\n oneYear: '0',\n};\n\nexport const DEFAULT_POOLED_STAKING_CHAIN_STATE = {\n pooledStakes: {\n account: '',\n lifetimeRewards: '0',\n assets: '0',\n exitRequests: [],\n },\n exchangeRate: '1',\n vaultMetadata: {\n apy: '0',\n capacity: '0',\n feePercent: 0,\n totalAssets: '0',\n vaultAddress: '0x0000000000000000000000000000000000000000',\n },\n vaultDailyApys: [],\n vaultApyAverages: DEFAULT_POOLED_STAKING_VAULT_APY_AVERAGES,\n};\n\n/**\n * Gets the default state for the EarnController.\n *\n * @returns The default EarnController state.\n */\nexport function getDefaultEarnControllerState(): EarnControllerState {\n return {\n pooled_staking: {\n isEligible: false,\n },\n lending: {\n markets: [DEFAULT_LENDING_MARKET],\n positions: [DEFAULT_LENDING_POSITION],\n isEligible: false,\n },\n lastUpdated: 0,\n };\n}\n\n// === MESSENGER ===\n\n/**\n * The action which can be used to retrieve the state of the EarnController.\n */\nexport type EarnControllerGetStateAction = ControllerGetStateAction<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All actions that EarnController registers, to be called externally.\n */\nexport type EarnControllerActions = EarnControllerGetStateAction;\n\n/**\n * All actions that EarnController calls internally.\n */\nexport type AllowedActions =\n | NetworkControllerGetNetworkClientByIdAction\n | AccountsControllerGetSelectedAccountAction;\n\n/**\n * The event that EarnController publishes when updating state.\n */\nexport type EarnControllerStateChangeEvent = ControllerStateChangeEvent<\n typeof controllerName,\n EarnControllerState\n>;\n\n/**\n * All events that EarnController publishes, to be subscribed to externally.\n */\nexport type EarnControllerEvents = EarnControllerStateChangeEvent;\n\n/**\n * All events that EarnController subscribes to internally.\n */\nexport type AllowedEvents =\n | AccountsControllerSelectedAccountChangeEvent\n | TransactionControllerTransactionConfirmedEvent\n | NetworkControllerNetworkDidChangeEvent;\n\n/**\n * The messenger which is restricted to actions and events accessed by\n * EarnController.\n */\nexport type EarnControllerMessenger = RestrictedMessenger<\n typeof controllerName,\n EarnControllerActions | AllowedActions,\n EarnControllerEvents | AllowedEvents,\n AllowedActions['type'],\n AllowedEvents['type']\n>;\n\n// === CONTROLLER DEFINITION ===\n\n/**\n * EarnController manages DeFi earning opportunities across different protocols and chains.\n */\nexport class EarnController extends BaseController<\n typeof controllerName,\n EarnControllerState,\n EarnControllerMessenger\n> {\n #earnSDK: EarnSdk | null = null;\n\n #selectedNetworkClientId: string;\n\n readonly #earnApiService: EarnApiService;\n\n readonly #addTransactionFn: typeof TransactionController.prototype.addTransaction;\n\n readonly #supportedPooledStakingChains: number[];\n\n readonly #env: EarnEnvironments;\n\n constructor({\n messenger,\n state = {},\n addTransactionFn,\n selectedNetworkClientId,\n env = EarnEnvironments.PROD,\n }: {\n messenger: EarnControllerMessenger;\n state?: Partial<EarnControllerState>;\n addTransactionFn: typeof TransactionController.prototype.addTransaction;\n selectedNetworkClientId: string;\n env?: EarnEnvironments;\n }) {\n super({\n name: controllerName,\n metadata: earnControllerMetadata,\n messenger,\n state: {\n ...getDefaultEarnControllerState(),\n ...state,\n },\n });\n\n this.#env = env;\n\n this.#earnApiService = new EarnApiService(this.#env);\n\n // temporary array of supported chains\n // TODO: remove this once we export a supported chains list from the sdk\n // from sdk or api to get lending and pooled staking chains\n this.#supportedPooledStakingChains = [ChainId.ETHEREUM, ChainId.HOODI];\n\n this.#addTransactionFn = addTransactionFn;\n\n this.#selectedNetworkClientId = selectedNetworkClientId;\n\n this.#initializeSDK(selectedNetworkClientId).catch(console.error);\n this.refreshPooledStakingData().catch(console.error);\n this.refreshLendingData().catch(console.error);\n\n // Listen for network changes\n this.messagingSystem.subscribe(\n 'NetworkController:networkDidChange',\n (networkControllerState) => {\n this.#selectedNetworkClientId =\n networkControllerState.selectedNetworkClientId;\n\n this.#initializeSDK(this.#selectedNetworkClientId).catch(console.error);\n\n // refresh pooled staking data\n this.refreshPooledStakingVaultMetadata().catch(console.error);\n this.refreshPooledStakingVaultDailyApys().catch(console.error);\n this.refreshPooledStakingVaultApyAverages().catch(console.error);\n this.refreshPooledStakes().catch(console.error);\n\n // refresh lending data for all chains\n this.refreshLendingMarkets().catch(console.error);\n this.refreshLendingPositions().catch(console.error);\n },\n );\n\n // Listen for account changes\n this.messagingSystem.subscribe(\n 'AccountsController:selectedAccountChange',\n (account) => {\n const address = account?.address;\n /**\n * TEMP: There's a race condition where the account state isn't updated immediately.\n * Until this has been fixed, we rely on the event payload for the latest account instead of #getCurrentAccount().\n * Issue: https://github.com/MetaMask/accounts-planning/issues/887\n */\n\n // TODO: temp solution, this will refresh lending eligibility also\n // we could have a more general check, as what is happening is a compliance address check\n this.refreshEarnEligibility({ address }).catch(console.error);\n this.refreshPooledStakes({ address }).catch(console.error);\n this.refreshLendingPositions({ address }).catch(console.error);\n },\n );\n\n // Listen for confirmed staking transactions\n this.messagingSystem.subscribe(\n 'TransactionController:transactionConfirmed',\n (transactionMeta) => {\n /**\n * When we speed up a transaction, we set the type as Retry and we lose\n * information about type of transaction that is being set up, so we use\n * original type to track that information.\n */\n const { type, originalType } = transactionMeta;\n\n const isStakingTransaction =\n stakingTransactionTypes.has(type as StakingTransactionTypes) ||\n stakingTransactionTypes.has(originalType as StakingTransactionTypes);\n\n const isLendingTransaction =\n lendingTransactionTypes.has(type as LendingTransactionTypes) ||\n lendingTransactionTypes.has(originalType as LendingTransactionTypes);\n\n const sender = transactionMeta.txParams.from;\n\n if (isStakingTransaction) {\n this.refreshPooledStakes({ resetCache: true, address: sender }).catch(\n console.error,\n );\n }\n if (isLendingTransaction) {\n this.refreshLendingPositions({ address: sender }).catch(\n console.error,\n );\n }\n },\n );\n }\n\n /**\n * Initializes the Earn SDK.\n *\n * @param networkClientId - The network client id to initialize the Earn SDK for.\n */\n async #initializeSDK(networkClientId: string) {\n const networkClient = this.messagingSystem.call(\n 'NetworkController:getNetworkClientById',\n networkClientId,\n );\n\n if (!networkClient?.provider) {\n this.#earnSDK = null;\n return;\n }\n\n const provider = new Web3Provider(networkClient.provider);\n const { chainId } = networkClient.configuration;\n\n // Initialize appropriate contracts based on chainId\n const config: EarnSdkConfig = {\n chainId: convertHexToDecimal(chainId),\n env: this.#env,\n };\n\n try {\n this.#earnSDK = await EarnSdk.create(provider, config);\n } catch (error) {\n this.#earnSDK = null;\n // Only log unexpected errors, not unsupported chain errors\n if (\n !(\n error instanceof Error &&\n error.message.includes('Unsupported chainId')\n )\n ) {\n console.error('Earn SDK initialization failed:', error);\n }\n }\n }\n\n /**\n * Gets the current account.\n *\n * @returns The current account.\n */\n #getCurrentAccount() {\n return this.messagingSystem.call('AccountsController:getSelectedAccount');\n }\n\n /**\n * Refreshes the pooled stakes data for the current account.\n * Fetches updated stake information including lifetime rewards, assets, and exit requests\n * from the staking API service and updates the state.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @param [options.chainId] - The chain id to refresh pooled stakes for (optional).\n * @returns A promise that resolves when the stakes data has been updated\n */\n async refreshPooledStakes({\n resetCache = false,\n address,\n chainId = ChainId.ETHEREUM,\n }: RefreshPooledStakesOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse) {\n return;\n }\n\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const { accounts, exchangeRate } =\n await this.#earnApiService.pooledStaking.getPooledStakes(\n [addressToUse],\n chainIdToUse,\n resetCache,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n pooledStakes: accounts[0],\n exchangeRate,\n };\n });\n }\n\n /**\n * Refreshes the earn eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * Note: Pooled-staking and Lending used the same result since there isn't a need to split these up right now.\n *\n * @param options - Optional arguments\n * @param [options.address] - Address to refresh earn eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshEarnEligibility({\n address,\n }: RefreshEarnEligibilityOptions = {}): Promise<void> {\n const addressToCheck = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToCheck) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToCheck,\n ]);\n\n this.update((state) => {\n state.pooled_staking.isEligible = isEligible;\n state.lending.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes pooled staking vault metadata for the current chain.\n * Updates the vault metadata in the controller state including APY, capacity,\n * fee percentage, total assets, and vault address.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault metadata for (optional).\n * @returns A promise that resolves when the vault metadata has been updated\n */\n async refreshPooledStakingVaultMetadata(\n chainId: number = ChainId.ETHEREUM,\n ): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultMetadata =\n await this.#earnApiService.pooledStaking.getVaultData(chainIdToUse);\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultMetadata,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault daily apys for the current chain.\n * Updates the pooled staking vault daily apys controller state.\n *\n * @param [options] - The options for refreshing pooled staking vault daily apys.\n * @param [options.chainId] - The chain id to refresh pooled staking vault daily apys for (defaults to Ethereum).\n * @param [options.days] - The number of days to fetch pooled staking vault daily apys for (defaults to 365).\n * @param [options.order] - The order in which to fetch pooled staking vault daily apys. Descending order fetches the latest N days (latest working backwards). Ascending order fetches the oldest N days (oldest working forwards) (defaults to 'desc').\n * @returns A promise that resolves when the pooled staking vault daily apys have been updated.\n */\n async refreshPooledStakingVaultDailyApys({\n chainId = ChainId.ETHEREUM,\n days = 365,\n order = 'desc',\n }: RefreshPooledStakingVaultDailyApysOptions = {}): Promise<void> {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultDailyApys =\n await this.#earnApiService.pooledStaking.getVaultDailyApys(\n chainIdToUse,\n days,\n order,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultDailyApys,\n };\n });\n }\n\n /**\n * Refreshes pooled staking vault apy averages for the current chain.\n * Updates the pooled staking vault apy averages controller state.\n *\n * @param [chainId] - The chain id to refresh pooled staking vault apy averages for (optional).\n * @returns A promise that resolves when the pooled staking vault apy averages have been updated.\n */\n async refreshPooledStakingVaultApyAverages(\n chainId: number = ChainId.ETHEREUM,\n ) {\n const chainIdToUse = isSupportedPooledStakingChain(chainId)\n ? chainId\n : ChainId.ETHEREUM;\n\n const vaultApyAverages =\n await this.#earnApiService.pooledStaking.getVaultApyAverages(\n chainIdToUse,\n );\n\n this.update((state) => {\n const chainState =\n state.pooled_staking[chainIdToUse] ??\n DEFAULT_POOLED_STAKING_CHAIN_STATE;\n state.pooled_staking[chainIdToUse] = {\n ...chainState,\n vaultApyAverages,\n };\n });\n }\n\n /**\n * Refreshes all pooled staking related data including stakes, eligibility, and vault data.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @param options - Optional arguments\n * @param [options.resetCache] - Control whether the BE cache should be invalidated (optional).\n * @param [options.address] - The address to refresh pooled stakes for (optional).\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshPooledStakingData({\n resetCache,\n address,\n }: RefreshPooledStakingDataOptions = {}): Promise<void> {\n const errors: Error[] = [];\n\n // Refresh earn eligibility once since it's not chain-specific\n await this.refreshEarnEligibility({ address }).catch((error) => {\n errors.push(error);\n });\n\n for (const chainId of this.#supportedPooledStakingChains) {\n await Promise.all([\n this.refreshPooledStakes({ resetCache, address, chainId }).catch(\n (error) => {\n errors.push(error);\n },\n ),\n this.refreshPooledStakingVaultMetadata(chainId).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultDailyApys({ chainId }).catch((error) => {\n errors.push(error);\n }),\n this.refreshPooledStakingVaultApyAverages(chainId).catch((error) => {\n errors.push(error);\n }),\n ]);\n }\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some staking data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Refreshes the lending markets data for all chains.\n * Updates the lending markets in the controller state.\n *\n * @returns A promise that resolves when the lending markets have been updated\n */\n async refreshLendingMarkets(): Promise<void> {\n const markets = await this.#earnApiService.lending.getMarkets();\n\n this.update((state) => {\n state.lending.markets = markets;\n });\n }\n\n /**\n * Refreshes the lending positions for the current account.\n * Updates the lending positions in the controller state.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending positions for (optional).\n * @returns A promise that resolves when the lending positions have been updated\n */\n async refreshLendingPositions({\n address,\n }: RefreshLendingPositionsOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse) {\n return;\n }\n\n // linter complaining about this not being a promise, but it is\n // TODO: figure out why this is not seen as a promise\n const positions = await Promise.resolve(\n this.#earnApiService.lending.getPositions(addressToUse),\n );\n\n this.update((state) => {\n state.lending.positions = positions.map((position) => ({\n ...position,\n marketId: position.market.id,\n marketAddress: position.market.address,\n protocol: position.market.protocol,\n }));\n });\n }\n\n /**\n * Refreshes the lending eligibility status for the current account.\n * Updates the eligibility status in the controller state based on the location and address blocklist for compliance.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to refresh lending eligibility for (optional).\n * @returns A promise that resolves when the eligibility status has been updated\n */\n async refreshLendingEligibility({\n address,\n }: RefreshLendingEligibilityOptions = {}): Promise<void> {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n // TODO: this is a temporary solution to refresh lending eligibility as\n // the eligibility check is not yet implemented for lending\n // this check will check the address against the same blocklist as the\n // staking eligibility check\n\n if (!addressToUse) {\n return;\n }\n\n const { eligible: isEligible } =\n await this.#earnApiService.pooledStaking.getPooledStakingEligibility([\n addressToUse,\n ]);\n\n this.update((state) => {\n state.lending.isEligible = isEligible;\n state.pooled_staking.isEligible = isEligible;\n });\n }\n\n /**\n * Refreshes all lending related data including markets, positions, and eligibility.\n * This method allows partial success, meaning some data may update while other requests fail.\n * All errors are collected and thrown as a single error message.\n *\n * @returns A promise that resolves when all possible data has been updated\n * @throws {Error} If any of the refresh operations fail, with concatenated error messages\n */\n async refreshLendingData(): Promise<void> {\n const errors: Error[] = [];\n\n await Promise.all([\n this.refreshLendingMarkets().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingPositions().catch((error) => {\n errors.push(error);\n }),\n this.refreshLendingEligibility().catch((error) => {\n errors.push(error);\n }),\n ]);\n\n if (errors.length > 0) {\n throw new Error(\n `Failed to refresh some lending data: ${errors\n .map((e) => e.message)\n .join(', ')}`,\n );\n }\n }\n\n /**\n * Gets the lending position history for the current account.\n *\n * @param options - Optional arguments\n * @param [options.address] - The address to get lending position history for (optional).\n * @param options.chainId - The chain id to get lending position history for.\n * @param [options.positionId] - The position id to get lending position history for.\n * @param [options.marketId] - The market id to get lending position history for.\n * @param [options.marketAddress] - The market address to get lending position history for.\n * @param [options.protocol] - The protocol to get lending position history for.\n * @param [options.days] - The number of days to get lending position history for (optional).\n * @returns A promise that resolves when the lending position history has been updated\n */\n getLendingPositionHistory({\n address,\n chainId,\n positionId,\n marketId,\n marketAddress,\n protocol,\n days = 730,\n }: {\n address?: string;\n chainId: number;\n positionId: string;\n marketId: string;\n marketAddress: string;\n protocol: string;\n days?: number;\n }) {\n const addressToUse = address ?? this.#getCurrentAccount()?.address;\n\n if (!addressToUse || !isSupportedLendingChain(chainId)) {\n return [];\n }\n\n return this.#earnApiService.lending.getPositionHistory(\n addressToUse,\n chainId,\n protocol,\n marketId,\n marketAddress,\n positionId,\n days,\n );\n }\n\n /**\n * Gets the lending market daily apys and averages for the current chain.\n *\n * @param options - Optional arguments\n * @param options.chainId - The chain id to get lending market daily apys and averages for.\n * @param [options.protocol] - The protocol to get lending market daily apys and averages for.\n * @param [options.marketId] - The market id to get lending market daily apys and averages for.\n * @param [options.days] - The number of days to get lending market daily apys and averages for (optional).\n * @returns A promise that resolves when the lending market daily apys and averages have been updated\n */\n getLendingMarketDailyApysAndAverages({\n chainId,\n protocol,\n marketId,\n days = 365,\n }: {\n chainId: number;\n protocol: string;\n marketId: string;\n days?: number;\n }): Promise<HistoricLendingMarketApys> | undefined {\n if (!isSupportedLendingChain(chainId)) {\n return undefined;\n }\n\n return this.#earnApiService.lending.getHistoricMarketApys(\n chainId,\n protocol,\n marketId,\n days,\n );\n }\n\n /**\n * Executes a lending deposit transaction.\n *\n * @param options - The options for the lending deposit transaction.\n * @param options.amount - The amount to deposit.\n * @param options.chainId - The chain ID for the lending deposit transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingDeposit({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeDepositTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending withdraw transaction.\n *\n * @param options - The options for the lending withdraw transaction.\n * @param options.amount - The amount to withdraw.\n * @param options.chainId - The chain ID for the lending withdraw transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingWithdraw({\n amount,\n chainId,\n protocol,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n amount: string;\n chainId: string;\n protocol: LendingMarket['protocol'];\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeWithdrawTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Executes a lending token approve transaction.\n *\n * @param options - The options for the lending token approve transaction.\n * @param options.amount - The amount to approve.\n * @param options.chainId - The chain ID for the lending token approve transaction.\n * @param options.protocol - The protocol of the lending market.\n * @param options.underlyingTokenAddress - The address of the underlying token.\n * @param options.gasOptions - The gas options for the transaction.\n * @param options.gasOptions.gasLimit - The gas limit for the transaction.\n * @param options.gasOptions.gasBufferPct - The gas buffer percentage for the transaction.\n * @param options.txOptions - The transaction options for the transaction.\n * @returns A promise that resolves to the transaction hash.\n */\n async executeLendingTokenApprove({\n protocol,\n amount,\n chainId,\n underlyingTokenAddress,\n gasOptions,\n txOptions,\n }: {\n protocol: LendingMarket['protocol'];\n amount: string;\n chainId: string;\n underlyingTokenAddress: string;\n gasOptions: {\n gasLimit?: GasLimitParams;\n gasBufferPct?: number;\n };\n txOptions: Parameters<\n typeof TransactionController.prototype.addTransaction\n >[1];\n }) {\n const address = this.#getCurrentAccount()?.address;\n\n const transactionData = await this.#earnSDK?.contracts?.lending?.[\n protocol\n ]?.[underlyingTokenAddress]?.encodeUnderlyingTokenApproveTransactionData(\n amount,\n address,\n gasOptions,\n );\n\n if (!transactionData) {\n throw new Error('Transaction data not found');\n }\n\n if (!this.#selectedNetworkClientId) {\n throw new Error('Selected network client id not found');\n }\n\n const gasLimit = !transactionData.gasLimit\n ? undefined\n : toHex(transactionData.gasLimit);\n\n const txHash = await this.#addTransactionFn(\n {\n ...transactionData,\n value: transactionData.value.toString(),\n chainId: toHex(chainId),\n gasLimit,\n },\n {\n ...txOptions,\n networkClientId: this.#selectedNetworkClientId,\n },\n );\n\n return txHash;\n }\n\n /**\n * Gets the allowance for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the allowance.\n */\n async getLendingTokenAllowance(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const allowance =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.underlyingTokenAllowance(address);\n\n return allowance;\n }\n\n /**\n * Gets the maximum withdraw amount for a lending token's output token or shares if no output token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum withdraw amount.\n */\n async getLendingTokenMaxWithdraw(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const maxWithdraw =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxWithdraw(address);\n\n return maxWithdraw;\n }\n\n /**\n * Gets the maximum deposit amount for a lending token.\n *\n * @param protocol - The protocol of the lending market.\n * @param underlyingTokenAddress - The address of the underlying token.\n * @returns A promise that resolves to the maximum deposit amount.\n */\n async getLendingTokenMaxDeposit(\n protocol: LendingMarket['protocol'],\n underlyingTokenAddress: string,\n ) {\n const address = this.#getCurrentAccount()?.address;\n\n const maxDeposit =\n await this.#earnSDK?.contracts?.lending?.[protocol]?.[\n underlyingTokenAddress\n ]?.maxDeposit(address);\n\n return maxDeposit;\n }\n}\n"]}
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "@metamask-previews/earn-controller",
|
3
|
-
"version": "6.0.0-preview-
|
3
|
+
"version": "6.0.0-preview-0b2bfc8a",
|
4
4
|
"description": "Manages state for earning features and coordinates interactions between staking services, SDK integrations, and other controllers to enable users to participate in various earning opportunities",
|
5
5
|
"keywords": [
|
6
6
|
"MetaMask",
|
@@ -55,7 +55,6 @@
|
|
55
55
|
"reselect": "^5.1.1"
|
56
56
|
},
|
57
57
|
"devDependencies": {
|
58
|
-
"@metamask/account-tree-controller": "^0.12.0",
|
59
58
|
"@metamask/accounts-controller": "^33.0.0",
|
60
59
|
"@metamask/auto-changelog": "^3.4.4",
|
61
60
|
"@metamask/network-controller": "^24.1.0",
|