@defisaver/positions-sdk 2.1.167 → 2.1.168-stable-pair-dev

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (89) hide show
  1. package/cjs/aaveV2/index.js +8 -29
  2. package/cjs/aaveV3/index.js +2 -31
  3. package/cjs/aaveV4/index.d.ts +25 -0
  4. package/cjs/aaveV4/index.js +4 -1
  5. package/cjs/compoundV2/index.d.ts +1 -1
  6. package/cjs/compoundV2/index.js +2 -2
  7. package/cjs/curveUsd/index.d.ts +1 -1
  8. package/cjs/curveUsd/index.js +6 -1
  9. package/cjs/fluid/index.js +13 -12
  10. package/cjs/helpers/aaveBalances.d.ts +5 -0
  11. package/cjs/helpers/aaveBalances.js +51 -0
  12. package/cjs/helpers/aaveV4Helpers/index.js +11 -1
  13. package/cjs/helpers/fluidBalances.d.ts +6 -0
  14. package/cjs/helpers/fluidBalances.js +36 -0
  15. package/cjs/liquityV2/index.d.ts +8 -0
  16. package/cjs/liquityV2/index.js +3 -3
  17. package/cjs/llamaLend/index.d.ts +1 -1
  18. package/cjs/llamaLend/index.js +6 -1
  19. package/cjs/moneymarket/moneymarketCommonService.js +12 -2
  20. package/cjs/morphoMidnight/index.d.ts +1 -1
  21. package/cjs/morphoMidnight/index.js +6 -1
  22. package/cjs/portfolio/index.d.ts +1 -0
  23. package/cjs/portfolio/index.js +3 -0
  24. package/cjs/portfolio/lendingSummaries.d.ts +7 -0
  25. package/cjs/portfolio/lendingSummaries.js +262 -0
  26. package/cjs/portfolio/lendingSummaryTransport.d.ts +8 -0
  27. package/cjs/portfolio/lendingSummaryTransport.js +109 -0
  28. package/cjs/spark/index.js +2 -31
  29. package/cjs/types/common.d.ts +1 -0
  30. package/cjs/types/common.js +1 -0
  31. package/cjs/types/index.d.ts +1 -0
  32. package/cjs/types/index.js +1 -0
  33. package/cjs/types/lendingSummary.d.ts +34 -0
  34. package/cjs/types/lendingSummary.js +2 -0
  35. package/esm/aaveV2/index.js +11 -32
  36. package/esm/aaveV3/index.js +3 -32
  37. package/esm/aaveV4/index.d.ts +25 -0
  38. package/esm/aaveV4/index.js +3 -1
  39. package/esm/compoundV2/index.d.ts +1 -1
  40. package/esm/compoundV2/index.js +2 -2
  41. package/esm/curveUsd/index.d.ts +1 -1
  42. package/esm/curveUsd/index.js +6 -1
  43. package/esm/fluid/index.js +13 -12
  44. package/esm/helpers/aaveBalances.d.ts +5 -0
  45. package/esm/helpers/aaveBalances.js +45 -0
  46. package/esm/helpers/aaveV4Helpers/index.js +11 -1
  47. package/esm/helpers/fluidBalances.d.ts +6 -0
  48. package/esm/helpers/fluidBalances.js +28 -0
  49. package/esm/liquityV2/index.d.ts +8 -0
  50. package/esm/liquityV2/index.js +1 -1
  51. package/esm/llamaLend/index.d.ts +1 -1
  52. package/esm/llamaLend/index.js +6 -1
  53. package/esm/moneymarket/moneymarketCommonService.js +12 -2
  54. package/esm/morphoMidnight/index.d.ts +1 -1
  55. package/esm/morphoMidnight/index.js +6 -1
  56. package/esm/portfolio/index.d.ts +1 -0
  57. package/esm/portfolio/index.js +1 -0
  58. package/esm/portfolio/lendingSummaries.d.ts +7 -0
  59. package/esm/portfolio/lendingSummaries.js +256 -0
  60. package/esm/portfolio/lendingSummaryTransport.d.ts +8 -0
  61. package/esm/portfolio/lendingSummaryTransport.js +104 -0
  62. package/esm/spark/index.js +4 -33
  63. package/esm/types/common.d.ts +1 -0
  64. package/esm/types/common.js +1 -0
  65. package/esm/types/index.d.ts +1 -0
  66. package/esm/types/index.js +1 -0
  67. package/esm/types/lendingSummary.d.ts +34 -0
  68. package/esm/types/lendingSummary.js +1 -0
  69. package/package.json +1 -1
  70. package/src/aaveV2/index.ts +8 -48
  71. package/src/aaveV3/index.ts +2 -48
  72. package/src/aaveV4/index.ts +6 -1
  73. package/src/compoundV2/index.ts +2 -2
  74. package/src/curveUsd/index.ts +6 -1
  75. package/src/fluid/index.ts +13 -12
  76. package/src/helpers/aaveBalances.ts +41 -0
  77. package/src/helpers/aaveV4Helpers/index.ts +12 -1
  78. package/src/helpers/fluidBalances.ts +34 -0
  79. package/src/liquityV2/index.ts +1 -1
  80. package/src/llamaLend/index.ts +6 -1
  81. package/src/moneymarket/moneymarketCommonService.ts +13 -2
  82. package/src/morphoMidnight/index.ts +6 -1
  83. package/src/portfolio/index.ts +2 -0
  84. package/src/portfolio/lendingSummaries.ts +216 -0
  85. package/src/portfolio/lendingSummaryTransport.ts +84 -0
  86. package/src/spark/index.ts +3 -49
  87. package/src/types/common.ts +1 -0
  88. package/src/types/index.ts +2 -1
  89. package/src/types/lendingSummary.ts +41 -0
@@ -5,6 +5,31 @@ export { getAaveV4MerkleCampaigns } from './merkl';
5
5
  export declare function _getAaveV4SpokeData(provider: Client, network: NetworkNumber, market: AaveV4SpokeInfo, blockNumber?: 'latest' | number): Promise<AaveV4SpokeData>;
6
6
  export declare function getAaveV4SpokeData(provider: EthereumProvider, network: NetworkNumber, spoke: AaveV4SpokeInfo, blockNumber?: 'latest' | number): Promise<AaveV4SpokeData>;
7
7
  export declare function _getAaveV4AccountData(provider: Client, network: NetworkNumber, spokeData: AaveV4SpokeData, address: EthAddress, blockNumber?: 'latest' | number): Promise<AaveV4AccountData>;
8
+ /** Shared raw read; no spoke metadata or market enrichment. */
9
+ export declare const _getAaveV4LoanBalances: (provider: Client, network: NetworkNumber, block: Blockish, address: EthAddress, spoke: EthAddress) => Promise<{
10
+ user: `0x${string}`;
11
+ riskPremium: bigint;
12
+ avgCollateralFactor: bigint;
13
+ healthFactor: bigint;
14
+ totalCollateralInUsd: bigint;
15
+ totalDebtInUsdRay: bigint;
16
+ activeCollateralCount: bigint;
17
+ borrowCount: bigint;
18
+ reserves: readonly {
19
+ reserveId: bigint;
20
+ assetId: number;
21
+ underlying: `0x${string}`;
22
+ supplied: bigint;
23
+ drawn: bigint;
24
+ premium: bigint;
25
+ totalDebt: bigint;
26
+ collateralFactor: number;
27
+ maxLiquidationBonus: number;
28
+ liquidationFee: number;
29
+ isUsingAsCollateral: boolean;
30
+ isBorrowing: boolean;
31
+ }[];
32
+ }>;
8
33
  /**
9
34
  * Lightweight existence check for Loan Shifter / UI discovery.
10
35
  * Reads only `getLoanData(spoke, user)` and returns whether any reserve has
@@ -9,7 +9,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  };
10
10
  import Dec from 'decimal.js';
11
11
  import { assetAmountInEth, assetAmountInWei, getAssetInfoByAddress } from '@defisaver/tokens';
12
- import { getViemProvider } from '../services/viem';
12
+ import { getViemProvider, setViemBlockNumber } from '../services/viem';
13
13
  import { IncentiveKind, } from '../types';
14
14
  import { AaveV4ViewContractViem } from '../contracts';
15
15
  import { getStakingApy, STAKING_ASSETS } from '../staking';
@@ -251,6 +251,8 @@ export function _getAaveV4AccountData(provider_1, network_1, spokeData_1, addres
251
251
  riskPremiumBps });
252
252
  });
253
253
  }
254
+ /** Shared raw read; no spoke metadata or market enrichment. */
255
+ export const _getAaveV4LoanBalances = (provider, network, block, address, spoke) => (AaveV4ViewContractViem(provider, network, block).read.getLoanData([spoke, address], setViemBlockNumber(block)));
254
256
  /**
255
257
  * Lightweight existence check for Loan Shifter / UI discovery.
256
258
  * Reads only `getLoanData(spoke, user)` and returns whether any reserve has
@@ -17,7 +17,7 @@ export declare const EMPTY_COMPOUND_DATA: {
17
17
  borrowStableSupplyUnstable: boolean;
18
18
  exposure: string;
19
19
  };
20
- export declare const _getCompoundV2AccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress) => Promise<PositionBalances>;
20
+ export declare const _getCompoundV2AccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, tokens?: EthAddress[]) => Promise<PositionBalances>;
21
21
  export declare const getCompoundV2AccountBalances: (provider: EthereumProvider, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress) => Promise<PositionBalances>;
22
22
  export declare const _getCompoundV2AccountData: (provider: Client, network: NetworkNumber, address: EthAddress, assetsData: CompoundV2AssetsData) => Promise<CompoundV2PositionData>;
23
23
  export declare const getCompoundV2AccountData: (provider: EthereumProvider, network: NetworkNumber, address: EthAddress, assetsData: CompoundV2AssetsData) => Promise<CompoundV2PositionData>;
@@ -101,7 +101,7 @@ const getAllMarketAddresses = (provider, network, block) => __awaiter(void 0, vo
101
101
  const contract = ComptrollerContractViem(provider, network);
102
102
  return contract.read.getAllMarkets(setViemBlockNumber(block));
103
103
  });
104
- export const _getCompoundV2AccountBalances = (provider, network, block, addressMapping, address) => __awaiter(void 0, void 0, void 0, function* () {
104
+ export const _getCompoundV2AccountBalances = (provider, network, block, addressMapping, address, tokens) => __awaiter(void 0, void 0, void 0, function* () {
105
105
  let balances = {
106
106
  collateral: {},
107
107
  debt: {},
@@ -109,7 +109,7 @@ export const _getCompoundV2AccountBalances = (provider, network, block, addressM
109
109
  if (!address) {
110
110
  return balances;
111
111
  }
112
- const assets = yield getAllMarketAddresses(provider, network, block);
112
+ const assets = tokens || (yield getAllMarketAddresses(provider, network, block));
113
113
  const assetInfo = assets.map(a => getAssetInfoByAddress(a, network));
114
114
  const loanInfoContract = CompoundLoanInfoContractViem(provider, network, block);
115
115
  const loanInfo = yield loanInfoContract.read.getTokenBalances([address, assets], setViemBlockNumber(block));
@@ -3,7 +3,7 @@ import { CrvUSDGlobalMarketData, CrvUSDMarketData, CrvUSDUserData } from '../typ
3
3
  import { Blockish, EthAddress, EthereumProvider, NetworkNumber, PositionBalances } from '../types/common';
4
4
  export declare const _getCurveUsdGlobalData: (provider: Client, network: NetworkNumber, selectedMarket: CrvUSDMarketData) => Promise<CrvUSDGlobalMarketData>;
5
5
  export declare const getCurveUsdGlobalData: (provider: EthereumProvider, network: NetworkNumber, selectedMarket: CrvUSDMarketData) => Promise<CrvUSDGlobalMarketData>;
6
- export declare const _getCrvUsdAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress) => Promise<PositionBalances>;
6
+ export declare const _getCrvUsdAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress, includeDeposited?: boolean) => Promise<PositionBalances>;
7
7
  export declare const getCrvUsdAccountBalances: (provider: EthereumProvider, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress) => Promise<PositionBalances>;
8
8
  /**
9
9
  * @param borrowRate market borrow APY in % (`CrvUSDGlobalMarketData.borrowRate`); when omitted it is read from the view contract
@@ -99,7 +99,7 @@ const getStatusForUser = (bandRange, activeBand, crvUSDSupplied, collSupplied, h
99
99
  return CrvUSDStatus.SoftLiquidated; // or is fully soft liquidated
100
100
  return CrvUSDStatus.Nonexistant;
101
101
  };
102
- export const _getCrvUsdAccountBalances = (provider, network, block, addressMapping, address, controllerAddress) => __awaiter(void 0, void 0, void 0, function* () {
102
+ export const _getCrvUsdAccountBalances = (provider_1, network_1, block_1, addressMapping_1, address_1, controllerAddress_1, ...args_1) => __awaiter(void 0, [provider_1, network_1, block_1, addressMapping_1, address_1, controllerAddress_1, ...args_1], void 0, function* (provider, network, block, addressMapping, address, controllerAddress, includeDeposited = false) {
103
103
  let balances = {
104
104
  collateral: {},
105
105
  debt: {},
@@ -118,6 +118,11 @@ export const _getCrvUsdAccountBalances = (provider, network, block, addressMappi
118
118
  [addressMapping ? getAssetInfo(wethToEth(selectedMarket.baseAsset), network).address.toLowerCase() : wethToEth(selectedMarket.baseAsset)]: data.debtAmount.toString(),
119
119
  },
120
120
  };
121
+ if (includeDeposited) {
122
+ balances.deposited = {
123
+ [addressMapping ? getAssetInfo(wethToEth(selectedMarket.baseAsset), network).address.toLowerCase() : wethToEth(selectedMarket.baseAsset)]: data.curveUsdCollateralAmount.toString(),
124
+ };
125
+ }
121
126
  return balances;
122
127
  });
123
128
  export const getCrvUsdAccountBalances = (provider, network, block, addressMapping, address, controllerAddress) => __awaiter(void 0, void 0, void 0, function* () { return _getCrvUsdAccountBalances(getViemProvider(provider, network), network, block, addressMapping, address, controllerAddress); });
@@ -9,6 +9,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  };
10
10
  import Dec from 'decimal.js';
11
11
  import { assetAmountInEth, getAssetInfo, getAssetInfoByAddress, } from '@defisaver/tokens';
12
+ import { fluidTokenAmount } from '../helpers/fluidBalances';
12
13
  import { IncentiveKind, NetworkNumber, } from '../types/common';
13
14
  import { FluidVaultType, } from '../types';
14
15
  import { BTCPriceFeedContractViem, DFSFeedRegistryContractViem, ETHPriceFeedContractViem, FeedRegistryContractViem, FluidViewContractViem, } from '../contracts';
@@ -925,8 +926,8 @@ const parseT1UserData = (userPositionData, vaultData) => {
925
926
  const collAsset = getAssetInfo(marketData.collAsset0);
926
927
  const debtAsset = getAssetInfo(marketData.debtAsset0);
927
928
  // for T2 and T4 - this is the number of shares
928
- const supplied = getEthAmountForDecimals(userPositionData.supply.toString(), collAsset.decimals);
929
- const borrowed = getEthAmountForDecimals(userPositionData.borrow.toString(), debtAsset.decimals);
929
+ const supplied = fluidTokenAmount(userPositionData.supply, collAsset.decimals);
930
+ const borrowed = fluidTokenAmount(userPositionData.borrow, debtAsset.decimals);
930
931
  const collUsedAsset = Object.assign(Object.assign({}, EMPTY_USED_ASSET), { symbol: collAsset.symbol, collateral: true, supplied, suppliedUsd: new Dec(supplied).mul(assetsData[collAsset.symbol].price).toString(), isSupplied: new Dec(supplied).gt(0) });
931
932
  const debtUsedAsset = Object.assign(Object.assign({}, EMPTY_USED_ASSET), { symbol: debtAsset.symbol, collateral: false, borrowed, borrowedUsd: new Dec(borrowed).mul(assetsData[debtAsset.symbol].price).toString(), isBorrowed: new Dec(borrowed).gt(0) });
932
933
  const usedAssets = {
@@ -946,9 +947,9 @@ const parseT2UserData = (userPositionData, vaultData) => {
946
947
  const collAsset1 = getAssetInfo(marketData.collAsset1);
947
948
  const debtAsset = getAssetInfo(marketData.debtAsset0);
948
949
  const supplyShares = getEthAmountForDecimals(userPositionData.supply.toString(), 18); // this is supplied in coll shares
949
- const borrowed = getEthAmountForDecimals(userPositionData.borrow.toString(), debtAsset.decimals); // this is actual token borrow
950
- const supplied0 = new Dec(supplyShares).mul(assetsData[collAsset0.symbol].tokenPerSupplyShare).toString();
951
- const supplied1 = new Dec(supplyShares).mul(assetsData[collAsset1.symbol].tokenPerSupplyShare).toString();
950
+ const borrowed = fluidTokenAmount(userPositionData.borrow, debtAsset.decimals); // this is actual token borrow
951
+ const supplied0 = fluidTokenAmount(userPositionData.supply, collAsset0.decimals, assetsData[collAsset0.symbol].tokenPerSupplyShare);
952
+ const supplied1 = fluidTokenAmount(userPositionData.supply, collAsset1.decimals, assetsData[collAsset1.symbol].tokenPerSupplyShare);
952
953
  const collUsedAsset0 = {
953
954
  symbol: collAsset0.symbol,
954
955
  collateral: true,
@@ -991,10 +992,10 @@ const parseT3UserData = (userPositionData, vaultData) => {
991
992
  const collAsset = getAssetInfo(marketData.collAsset0);
992
993
  const debtAsset0 = getAssetInfo(marketData.debtAsset0);
993
994
  const debtAsset1 = getAssetInfo(marketData.debtAsset1);
994
- const supplied = getEthAmountForDecimals(userPositionData.supply.toString(), collAsset.decimals); // this is actual token supply
995
+ const supplied = fluidTokenAmount(userPositionData.supply, collAsset.decimals); // this is actual token supply
995
996
  const borrowShares = getEthAmountForDecimals(userPositionData.borrow.toString(), 18); // this is actual token borrow
996
- const borrowed0 = new Dec(borrowShares).mul(assetsData[debtAsset0.symbol].tokenPerBorrowShare).toString();
997
- const borrowed1 = new Dec(borrowShares).mul(assetsData[debtAsset1.symbol].tokenPerBorrowShare).toString();
997
+ const borrowed0 = fluidTokenAmount(userPositionData.borrow, debtAsset0.decimals, assetsData[debtAsset0.symbol].tokenPerBorrowShare);
998
+ const borrowed1 = fluidTokenAmount(userPositionData.borrow, debtAsset1.decimals, assetsData[debtAsset1.symbol].tokenPerBorrowShare);
998
999
  const collUsedAsset = {
999
1000
  symbol: collAsset.symbol,
1000
1001
  collateral: true,
@@ -1039,10 +1040,10 @@ const parseT4UserData = (userPositionData, vaultData) => {
1039
1040
  const debtAsset1 = getAssetInfo(marketData.debtAsset1);
1040
1041
  const supplyShares = getEthAmountForDecimals(userPositionData.supply.toString(), 18); // this is actual token supply
1041
1042
  const borrowShares = getEthAmountForDecimals(userPositionData.borrow.toString(), 18); // this is actual token borrow
1042
- const supplied0 = new Dec(supplyShares).mul(assetsData[collAsset0.symbol].tokenPerSupplyShare).toString();
1043
- const supplied1 = new Dec(supplyShares).mul(assetsData[collAsset1.symbol].tokenPerSupplyShare).toString();
1044
- const borrowed0 = new Dec(borrowShares).mul(assetsData[debtAsset0.symbol].tokenPerBorrowShare).toString();
1045
- const borrowed1 = new Dec(borrowShares).mul(assetsData[debtAsset1.symbol].tokenPerBorrowShare).toString();
1043
+ const supplied0 = fluidTokenAmount(userPositionData.supply, collAsset0.decimals, assetsData[collAsset0.symbol].tokenPerSupplyShare);
1044
+ const supplied1 = fluidTokenAmount(userPositionData.supply, collAsset1.decimals, assetsData[collAsset1.symbol].tokenPerSupplyShare);
1045
+ const borrowed0 = fluidTokenAmount(userPositionData.borrow, debtAsset0.decimals, assetsData[debtAsset0.symbol].tokenPerBorrowShare);
1046
+ const borrowed1 = fluidTokenAmount(userPositionData.borrow, debtAsset1.decimals, assetsData[debtAsset1.symbol].tokenPerBorrowShare);
1046
1047
  const collUsedAsset0 = {
1047
1048
  symbol: collAsset0.symbol,
1048
1049
  collateral: true,
@@ -0,0 +1,5 @@
1
+ import { Client } from 'viem';
2
+ import { AaveMarketInfo, SparkMarketData } from '../types';
3
+ import { Blockish, EthAddress, NetworkNumber, PositionBalances } from '../types/common';
4
+ /** Raw token balances shared by Aave/Spark getters and lending previews. */
5
+ export declare function getAaveLikeBalances(client: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, market: Pick<AaveMarketInfo | SparkMarketData, 'providerAddress' | 'protocolData' | 'protocolDataAddress'>, view: 'AaveLoanInfoV2' | 'AaveV3View' | 'SparkView', tokens?: EthAddress[]): Promise<PositionBalances>;
@@ -0,0 +1,45 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import Dec from 'decimal.js';
11
+ import { getAssetInfoByAddress } from '@defisaver/tokens';
12
+ import { createViemContractFromConfigFunc } from '../contracts';
13
+ import { setViemBlockNumber } from '../services/viem';
14
+ import { wethToEth, wethToEthByAddress } from '../services/utils';
15
+ /** Raw token balances shared by Aave/Spark getters and lending previews. */
16
+ export function getAaveLikeBalances(client, network, block, addressMapping, address, market, view, tokens) {
17
+ return __awaiter(this, void 0, void 0, function* () {
18
+ const balances = { collateral: {}, debt: {} };
19
+ if (!address)
20
+ return balances;
21
+ let reserves;
22
+ if (tokens)
23
+ reserves = tokens.map(tokenAddress => ({ tokenAddress, symbol: getAssetInfoByAddress(tokenAddress, network).symbol }));
24
+ else {
25
+ if (!market.protocolData)
26
+ throw new Error('Missing protocol data provider');
27
+ reserves = [...yield createViemContractFromConfigFunc(market.protocolData, market.protocolDataAddress)(client, network)
28
+ .read.getAllReservesTokens(setViemBlockNumber(block))];
29
+ }
30
+ const addresses = reserves.map(token => token.tokenAddress);
31
+ const contract = createViemContractFromConfigFunc(view)(client, network, block);
32
+ const middle = tokens ? Math.ceil(addresses.length / 2) : Math.floor(addresses.length / 2);
33
+ // Preserve legacy V2 single-call and V3/Spark two-call behavior.
34
+ const parts = !tokens && view === 'AaveLoanInfoV2' ? [addresses] : [addresses.slice(0, middle), addresses.slice(middle)];
35
+ const data = (yield Promise.all((tokens ? parts.filter(part => part.length) : parts)
36
+ .map(part => contract.read.getTokenBalances([market.providerAddress, address, part], setViemBlockNumber(block))))).flat();
37
+ data.forEach((token, i) => {
38
+ // The views leave token.token unset; input order identifies the reserve.
39
+ const key = addressMapping ? wethToEthByAddress(reserves[i].tokenAddress, network).toLowerCase() : wethToEth(reserves[i].symbol);
40
+ balances.collateral[key] = token.balance.toString();
41
+ balances.debt[key] = new Dec(token.borrowsStable.toString()).add(token.borrowsVariable.toString()).toString();
42
+ });
43
+ return balances;
44
+ });
45
+ }
@@ -151,12 +151,15 @@ export const isLeveragedPosAaveV4 = (usedAssets, dustLimit = 5) => {
151
151
  let supplyUnstable = 0;
152
152
  let longAsset = '';
153
153
  let shortAsset = '';
154
+ let stableCollAsset = '';
154
155
  Object.values(usedAssets).forEach(({ symbol, suppliedUsd, borrowedUsd, collateral, reserveId, }) => {
155
156
  const spokeAsset = `${symbol}-${reserveId}`;
156
157
  const isSupplied = (+suppliedUsd) > dustLimit; // ignore dust like <limit leftover supply
157
158
  const isBorrowed = (+borrowedUsd) > dustLimit; // ignore dust like <limit leftover supply
158
- if (isSupplied && STABLE_ASSETS.includes(symbol) && collateral)
159
+ if (isSupplied && STABLE_ASSETS.includes(symbol) && collateral) {
159
160
  supplyStable += 1;
161
+ stableCollAsset = spokeAsset;
162
+ }
160
163
  if (isBorrowed && STABLE_ASSETS.includes(symbol))
161
164
  borrowStable += 1;
162
165
  if (isBorrowed && !STABLE_ASSETS.includes(symbol)) {
@@ -171,6 +174,7 @@ export const isLeveragedPosAaveV4 = (usedAssets, dustLimit = 5) => {
171
174
  const isLong = borrowStable > 0 && borrowUnstable === 0 && supplyUnstable === 1 && supplyStable === 0;
172
175
  const isShort = supplyStable > 0 && supplyUnstable === 0 && borrowUnstable === 1 && borrowStable === 0;
173
176
  const isVolatilePair = supplyUnstable === 1 && borrowUnstable === 1 && supplyStable === 0 && borrowStable === 0;
177
+ const isStablePair = supplyStable === 1 && borrowStable === 1 && supplyUnstable === 0 && borrowUnstable === 0;
174
178
  if (isLong) {
175
179
  return {
176
180
  leveragedType: LeverageType.Long,
@@ -189,6 +193,12 @@ export const isLeveragedPosAaveV4 = (usedAssets, dustLimit = 5) => {
189
193
  leveragedAsset: longAsset,
190
194
  };
191
195
  }
196
+ if (isStablePair) {
197
+ return {
198
+ leveragedType: LeverageType.StablePair,
199
+ leveragedAsset: stableCollAsset,
200
+ };
201
+ }
192
202
  return {
193
203
  leveragedType: LeverageType.None,
194
204
  leveragedAsset: '',
@@ -0,0 +1,6 @@
1
+ import { FluidUserPositionStructOutputStruct, FluidVaultDataStructOutputStruct } from '../types';
2
+ import { NetworkNumber, PositionBalances } from '../types/common';
3
+ /** Convert raw tokens, or raw 18-decimal shares with a human-readable token/share ratio. */
4
+ export declare const fluidTokenAmount: (amount: bigint, decimals: number, perShare?: string) => string;
5
+ /** The same token/share conversion used by the full Fluid user parsers, without prices or yield. */
6
+ export declare function parseFluidBalances(position: FluidUserPositionStructOutputStruct, vault: FluidVaultDataStructOutputStruct, network: NetworkNumber): PositionBalances;
@@ -0,0 +1,28 @@
1
+ import Dec from 'decimal.js';
2
+ import { getAssetInfoByAddress } from '@defisaver/tokens';
3
+ /** Convert raw tokens, or raw 18-decimal shares with a human-readable token/share ratio. */
4
+ export const fluidTokenAmount = (amount, decimals, perShare) => (new Dec(amount.toString()).div(new Dec(10).pow(perShare === undefined ? decimals : 18)).mul(perShare !== null && perShare !== void 0 ? perShare : 1).toString());
5
+ /** The same token/share conversion used by the full Fluid user parsers, without prices or yield. */
6
+ export function parseFluidBalances(position, vault, network) {
7
+ const type = Number(vault.vaultType);
8
+ if (![10000, 20000, 30000, 40000].includes(type))
9
+ throw new Error('Unsupported Fluid vault');
10
+ const side = (amount, tokens, ratios) => {
11
+ const balances = {};
12
+ tokens.forEach((address, i) => {
13
+ const token = getAssetInfoByAddress(address, network);
14
+ if (!Number.isFinite(token.decimals) || !token.symbol)
15
+ throw new Error('Fluid token metadata unavailable');
16
+ const perShare = ratios ? fluidTokenAmount(ratios[i], token.decimals) : undefined;
17
+ const value = fluidTokenAmount(amount, token.decimals, perShare);
18
+ balances[token.symbol] = new Dec(balances[token.symbol] || 0).add(value).toString();
19
+ });
20
+ return balances;
21
+ };
22
+ const smartSupply = type === 20000 || type === 40000;
23
+ const smartDebt = type === 30000 || type === 40000;
24
+ return {
25
+ collateral: side(position.supply, smartSupply ? [vault.supplyToken0, vault.supplyToken1] : [vault.supplyToken0], smartSupply ? [vault.dexSupplyData.token0PerSupplyShare, vault.dexSupplyData.token1PerSupplyShare] : undefined),
26
+ debt: side(position.borrow, smartDebt ? [vault.borrowToken0, vault.borrowToken1] : [vault.borrowToken0], smartDebt ? [vault.dexBorrowData.token0PerBorrowShare, vault.dexBorrowData.token1PerBorrowShare] : undefined),
27
+ };
28
+ }
@@ -11,6 +11,14 @@ export type SPYieldGainParameters = {
11
11
  };
12
12
  export declare const _getLiquityV2MarketData: (provider: Client, network: NetworkNumber, selectedMarket: LiquityV2MarketInfo) => Promise<LiquityV2MarketData>;
13
13
  export declare const getLiquityV2MarketData: (provider: EthereumProvider, network: NetworkNumber, selectedMarket: LiquityV2MarketInfo) => Promise<LiquityV2MarketData>;
14
+ export declare const nftContractCreationBlockMapping: {
15
+ liquityv2eth: number;
16
+ liquityv2wsteth: number;
17
+ liquityv2reth: number;
18
+ liquityv2ethlegacy: number;
19
+ liquityv2wstethlegacy: number;
20
+ liquityv2rethlegacy: number;
21
+ };
14
22
  export declare const _getLiquityV2UserTroveIds: (provider: PublicClient, network: NetworkNumber, selectedMarket: LiquityV2MarketInfo, troveNFTAddress: EthAddress, limitBlocksForEventFetching: boolean, account: EthAddress) => Promise<{
15
23
  troves: {
16
24
  troveId: string;
@@ -112,7 +112,7 @@ const getUserTroves = (provider_1, network_1, isLegacy_1, account_1, marketAddre
112
112
  return { troves: existingTroves.filter((trove) => trove.ownedByUser), nextFreeTroveIndex };
113
113
  return getUserTroves(provider, network, isLegacy, account, marketAddress, newStartIndex, newStartIndex + 100, existingTroves);
114
114
  });
115
- const nftContractCreationBlockMapping = {
115
+ export const nftContractCreationBlockMapping = {
116
116
  [LiquityV2Versions.LiquityV2Eth]: 22516079,
117
117
  [LiquityV2Versions.LiquityV2WstEth]: 22516099,
118
118
  [LiquityV2Versions.LiquityV2REth]: 22516118,
@@ -3,7 +3,7 @@ import { LlamaLendGlobalMarketData, LlamaLendMarketData, LlamaLendUserData } fro
3
3
  import { Blockish, EthAddress, EthereumProvider, NetworkNumber, PositionBalances } from '../types/common';
4
4
  export declare const _getLlamaLendGlobalData: (provider: Client, network: NetworkNumber, selectedMarket: LlamaLendMarketData) => Promise<LlamaLendGlobalMarketData>;
5
5
  export declare const getLlamaLendGlobalData: (provider: EthereumProvider, network: NetworkNumber, selectedMarket: LlamaLendMarketData) => Promise<LlamaLendGlobalMarketData>;
6
- export declare const _getLlamaLendAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress) => Promise<PositionBalances>;
6
+ export declare const _getLlamaLendAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress, includeDeposited?: boolean) => Promise<PositionBalances>;
7
7
  export declare const getLlamaLendAccountBalances: (provider: EthereumProvider, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, controllerAddress: EthAddress) => Promise<PositionBalances>;
8
8
  export declare const _getLlamaLendUserData: (provider: Client, network: NetworkNumber, address: EthAddress, selectedMarket: LlamaLendMarketData, marketData: LlamaLendGlobalMarketData) => Promise<LlamaLendUserData>;
9
9
  export declare const getLlamaLendUserData: (provider: EthereumProvider, network: NetworkNumber, address: EthAddress, selectedMarket: LlamaLendMarketData, marketData: LlamaLendGlobalMarketData) => Promise<LlamaLendUserData>;
@@ -153,7 +153,7 @@ const getStatusForUser = (bandRange, activeBand, debtSupplied, collSupplied, hea
153
153
  return LlamaLendStatus.SoftLiquidated; // or is fully soft liquidated
154
154
  return LlamaLendStatus.Nonexistant;
155
155
  };
156
- export const _getLlamaLendAccountBalances = (provider, network, block, addressMapping, address, controllerAddress) => __awaiter(void 0, void 0, void 0, function* () {
156
+ export const _getLlamaLendAccountBalances = (provider_1, network_1, block_1, addressMapping_1, address_1, controllerAddress_1, ...args_1) => __awaiter(void 0, [provider_1, network_1, block_1, addressMapping_1, address_1, controllerAddress_1, ...args_1], void 0, function* (provider, network, block, addressMapping, address, controllerAddress, includeDeposited = false) {
157
157
  let balances = {
158
158
  collateral: {},
159
159
  debt: {},
@@ -172,6 +172,11 @@ export const _getLlamaLendAccountBalances = (provider, network, block, addressMa
172
172
  [addressMapping ? getAssetInfo(wethToEth(selectedMarket.baseAsset), network).address.toLowerCase() : wethToEth(selectedMarket.baseAsset)]: data.debtAmount.toString(),
173
173
  },
174
174
  };
175
+ if (includeDeposited) {
176
+ balances.deposited = {
177
+ [addressMapping ? getAssetInfo(wethToEth(selectedMarket.baseAsset), network).address.toLowerCase() : wethToEth(selectedMarket.baseAsset)]: data.debtTokenCollateralAmount.toString(),
178
+ };
179
+ }
175
180
  return balances;
176
181
  });
177
182
  export const getLlamaLendAccountBalances = (provider, network, block, addressMapping, address, controllerAddress) => __awaiter(void 0, void 0, void 0, function* () { return _getLlamaLendAccountBalances(getViemProvider(provider, network), network, block, addressMapping, address, controllerAddress); });
@@ -11,7 +11,7 @@ export const calcShortLiqPrice = (assetPrice, borrowedUsd, borrowLimitUsd) => ne
11
11
  export const calcLeverageLiqPrice = (leverageType, assetPrice, borrowedUsd, borrowLimitUsd) => {
12
12
  if (leverageType === LeverageType.Short || leverageType === LeverageType.VolatilePairReverse)
13
13
  return calcShortLiqPrice(assetPrice, borrowedUsd, borrowLimitUsd);
14
- if (leverageType === LeverageType.Long || leverageType === LeverageType.VolatilePair)
14
+ if (leverageType === LeverageType.Long || leverageType === LeverageType.VolatilePair || leverageType === LeverageType.StablePair)
15
15
  return calcLongLiqPrice(assetPrice, borrowedUsd, borrowLimitUsd);
16
16
  console.error('invalid leverageType', leverageType);
17
17
  return '0';
@@ -33,11 +33,14 @@ export const isLeveragedPos = (usedAssets, dustLimit = 5) => {
33
33
  let supplyUnstable = 0;
34
34
  let longAsset = '';
35
35
  let shortAsset = '';
36
+ let stableCollAsset = '';
36
37
  Object.values(usedAssets).forEach(({ symbol, suppliedUsd, borrowedUsd, collateral, }) => {
37
38
  const isSupplied = (+suppliedUsd) > dustLimit; // ignore dust like <limit leftover supply
38
39
  const isBorrowed = (+borrowedUsd) > dustLimit; // ignore dust like <limit leftover supply
39
- if (isSupplied && STABLE_ASSETS.includes(symbol) && collateral)
40
+ if (isSupplied && STABLE_ASSETS.includes(symbol) && collateral) {
40
41
  supplyStable += 1;
42
+ stableCollAsset = symbol;
43
+ }
41
44
  if (isBorrowed && STABLE_ASSETS.includes(symbol))
42
45
  borrowStable += 1;
43
46
  if (isBorrowed && !STABLE_ASSETS.includes(symbol)) {
@@ -52,6 +55,7 @@ export const isLeveragedPos = (usedAssets, dustLimit = 5) => {
52
55
  const isLong = borrowStable > 0 && borrowUnstable === 0 && supplyUnstable === 1 && supplyStable === 0;
53
56
  const isShort = supplyStable > 0 && supplyUnstable === 0 && borrowUnstable === 1 && borrowStable === 0;
54
57
  const isVolatilePair = supplyUnstable === 1 && borrowUnstable === 1 && supplyStable === 0 && borrowStable === 0;
58
+ const isStablePair = supplyStable === 1 && borrowStable === 1 && supplyUnstable === 0 && borrowUnstable === 0;
55
59
  if (isLong) {
56
60
  return {
57
61
  leveragedType: LeverageType.Long,
@@ -70,6 +74,12 @@ export const isLeveragedPos = (usedAssets, dustLimit = 5) => {
70
74
  leveragedAsset: longAsset,
71
75
  };
72
76
  }
77
+ if (isStablePair) {
78
+ return {
79
+ leveragedType: LeverageType.StablePair,
80
+ leveragedAsset: stableCollAsset,
81
+ };
82
+ }
73
83
  return {
74
84
  leveragedType: LeverageType.None,
75
85
  leveragedAsset: '',
@@ -5,7 +5,7 @@ export declare function _getMorphoMidnightMarketData(provider: Client, network:
5
5
  export declare function getMorphoMidnightMarketData(provider: EthereumProvider, network: NetworkNumber, selectedMarket: MorphoMidnightMarketData): Promise<MorphoMidnightMarketInfo>;
6
6
  export declare function _getMorphoMidnightAccountData(provider: Client, network: NetworkNumber, account: EthAddress, selectedMarket: MorphoMidnightMarketData, marketInfo: MorphoMidnightMarketInfo): Promise<MorphoMidnightPositionData>;
7
7
  export declare function getMorphoMidnightAccountData(provider: EthereumProvider, network: NetworkNumber, account: EthAddress, selectedMarket: MorphoMidnightMarketData, marketInfo: MorphoMidnightMarketInfo): Promise<MorphoMidnightPositionData>;
8
- export declare const _getMorphoMidnightAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, selectedMarket: MorphoMidnightMarketData) => Promise<PositionBalances>;
8
+ export declare const _getMorphoMidnightAccountBalances: (provider: Client, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, selectedMarket: MorphoMidnightMarketData, includeCredit?: boolean) => Promise<PositionBalances>;
9
9
  export declare const getMorphoMidnightAccountBalances: (provider: EthereumProvider, network: NetworkNumber, block: Blockish, addressMapping: boolean, address: EthAddress, selectedMarket: MorphoMidnightMarketData) => Promise<PositionBalances>;
10
10
  export declare function getMorphoMidnightEarn(provider: Client, network: NetworkNumber, account: EthAddress, selectedMarket: MorphoMidnightMarketData, marketInfo: MorphoMidnightMarketInfo): Promise<{
11
11
  apy: string;
@@ -210,7 +210,7 @@ export function getMorphoMidnightAccountData(provider, network, account, selecte
210
210
  return _getMorphoMidnightAccountData(getViemProvider(provider, network), network, account, selectedMarket, marketInfo);
211
211
  });
212
212
  }
213
- export const _getMorphoMidnightAccountBalances = (provider, network, block, addressMapping, address, selectedMarket) => __awaiter(void 0, void 0, void 0, function* () {
213
+ export const _getMorphoMidnightAccountBalances = (provider_1, network_1, block_1, addressMapping_1, address_1, selectedMarket_1, ...args_1) => __awaiter(void 0, [provider_1, network_1, block_1, addressMapping_1, address_1, selectedMarket_1, ...args_1], void 0, function* (provider, network, block, addressMapping, address, selectedMarket, includeCredit = false) {
214
214
  const balances = { collateral: {}, debt: {} };
215
215
  if (!address)
216
216
  return balances;
@@ -230,6 +230,11 @@ export const _getMorphoMidnightAccountBalances = (provider, network, block, addr
230
230
  collateral[addressMapping ? collInfo.address.toLowerCase() : wethToEth(collInfo.symbol)] = assetAmountInEth(rawAmount, wethToEth(collInfo.symbol));
231
231
  });
232
232
  balances.collateral = collateral;
233
+ if (includeCredit) {
234
+ balances.deposited = {
235
+ [addressMapping ? loanTokenInfo.address.toLowerCase() : wethToEth(loanTokenInfo.symbol)]: assetAmountInEth(positionInfo.credit.toString(), wethToEth(loanTokenInfo.symbol)),
236
+ };
237
+ }
233
238
  return balances;
234
239
  });
235
240
  export const getMorphoMidnightAccountBalances = (provider, network, block, addressMapping, address, selectedMarket) => __awaiter(void 0, void 0, void 0, function* () { return _getMorphoMidnightAccountBalances(getViemProvider(provider, network), network, block, addressMapping, address, selectedMarket); });
@@ -11,3 +11,4 @@ export declare function getShifterPortfolioData(provider: EthereumProvider, netw
11
11
  markets: PortfolioMarketsData;
12
12
  }>;
13
13
  export * from './discovery';
14
+ export { getWalletLendingSummaries } from './lendingSummaries';
@@ -865,3 +865,4 @@ export function getShifterPortfolioData(provider_1, network_1, defaultProvider_1
865
865
  });
866
866
  }
867
867
  export * from './discovery';
868
+ export { getWalletLendingSummaries } from './lendingSummaries';
@@ -0,0 +1,7 @@
1
+ import { EthAddress, EthereumProvider, NetworkNumber } from '../types/common';
2
+ import { LendingSummaryOptions, WalletLendingSummaries } from '../types/lendingSummary';
3
+ /** Lending-only balances at one snapshot, valued with caller-supplied market prices.
4
+ * One shared client/limiter covers every wallet. Failed reads remain partial; cancellation
5
+ * discards results. Morpho Blue earn deposits, rewards and savings are excluded.
6
+ */
7
+ export declare function getWalletLendingSummaries(provider: EthereumProvider, network: NetworkNumber, walletAddresses: EthAddress[], options: LendingSummaryOptions): Promise<WalletLendingSummaries>;