@gearbox-protocol/sdk 14.5.10 → 14.6.0-next.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (91) hide show
  1. package/dist/cjs/common-utils/utils/apy/bonus-apy-from-points.js +28 -0
  2. package/dist/cjs/common-utils/utils/apy/calculate-effective-borrow-rate.js +35 -0
  3. package/dist/cjs/common-utils/utils/apy/get-complex-apy-list.js +45 -0
  4. package/dist/cjs/common-utils/utils/apy/get-rate-with-fee.js +31 -0
  5. package/dist/cjs/common-utils/utils/apy/get-single-quota-borrow-rate.js +33 -0
  6. package/dist/cjs/common-utils/utils/apy/index.js +32 -0
  7. package/dist/cjs/common-utils/utils/apy/max-apy-formula.js +40 -0
  8. package/dist/cjs/common-utils/utils/index.js +5 -1
  9. package/dist/cjs/common-utils/utils/strategies/__test-utils.js +95 -0
  10. package/dist/cjs/common-utils/utils/strategies/availability/check-boolean.js +33 -0
  11. package/dist/cjs/common-utils/utils/strategies/availability/check-degen-nft.js +35 -0
  12. package/dist/cjs/common-utils/utils/strategies/availability/index.js +28 -0
  13. package/dist/cjs/common-utils/utils/strategies/availability/validate-open-account-pool-quota-status.js +40 -0
  14. package/dist/cjs/common-utils/utils/strategies/availability/validate-open-account-pool-status.js +76 -0
  15. package/dist/cjs/common-utils/utils/strategies/index.js +28 -0
  16. package/dist/cjs/common-utils/utils/strategies/leverage/calculate-loss-coefficient.js +31 -0
  17. package/dist/cjs/common-utils/utils/strategies/leverage/calculate-max-leverage-factor.js +45 -0
  18. package/dist/cjs/common-utils/utils/strategies/leverage/get-factor-from-leverage.js +31 -0
  19. package/dist/cjs/common-utils/utils/strategies/leverage/get-leverage-from-factor.js +31 -0
  20. package/dist/cjs/common-utils/utils/strategies/leverage/index.js +32 -0
  21. package/dist/cjs/common-utils/utils/strategies/leverage/max-leverage-threshold.js +42 -0
  22. package/dist/cjs/common-utils/utils/strategies/leverage/max-leverage.js +35 -0
  23. package/dist/cjs/common-utils/utils/strategies/sort-strategy-cms-by-availability/index.js +22 -0
  24. package/dist/cjs/common-utils/utils/strategies/sort-strategy-cms-by-availability/sort-strategy-cms-by-availability.js +64 -0
  25. package/dist/cjs/common-utils/utils/strategies/strategy-info/cm-availability-condition.js +63 -0
  26. package/dist/cjs/common-utils/utils/strategies/strategy-info/get-strategy-info.js +98 -0
  27. package/dist/cjs/common-utils/utils/strategies/strategy-info/get-strategy-max-apy.js +102 -0
  28. package/dist/cjs/common-utils/utils/strategies/strategy-info/index.js +30 -0
  29. package/dist/cjs/common-utils/utils/strategies/strategy-info/is-strategy-cm-disabled.js +33 -0
  30. package/dist/cjs/common-utils/utils/strategies/strategy-info/types.js +16 -0
  31. package/dist/esm/common-utils/utils/apy/bonus-apy-from-points.js +4 -0
  32. package/dist/esm/common-utils/utils/apy/calculate-effective-borrow-rate.js +11 -0
  33. package/dist/esm/common-utils/utils/apy/get-complex-apy-list.js +21 -0
  34. package/dist/esm/common-utils/utils/apy/get-rate-with-fee.js +7 -0
  35. package/dist/esm/common-utils/utils/apy/get-single-quota-borrow-rate.js +9 -0
  36. package/dist/esm/common-utils/utils/apy/index.js +6 -0
  37. package/dist/esm/common-utils/utils/apy/max-apy-formula.js +16 -0
  38. package/dist/esm/common-utils/utils/index.js +2 -0
  39. package/dist/esm/common-utils/utils/strategies/__test-utils.js +65 -0
  40. package/dist/esm/common-utils/utils/strategies/availability/check-boolean.js +9 -0
  41. package/dist/esm/common-utils/utils/strategies/availability/check-degen-nft.js +11 -0
  42. package/dist/esm/common-utils/utils/strategies/availability/index.js +4 -0
  43. package/dist/esm/common-utils/utils/strategies/availability/validate-open-account-pool-quota-status.js +16 -0
  44. package/dist/esm/common-utils/utils/strategies/availability/validate-open-account-pool-status.js +52 -0
  45. package/dist/esm/common-utils/utils/strategies/index.js +4 -0
  46. package/dist/esm/common-utils/utils/strategies/leverage/calculate-loss-coefficient.js +7 -0
  47. package/dist/esm/common-utils/utils/strategies/leverage/calculate-max-leverage-factor.js +21 -0
  48. package/dist/esm/common-utils/utils/strategies/leverage/get-factor-from-leverage.js +7 -0
  49. package/dist/esm/common-utils/utils/strategies/leverage/get-leverage-from-factor.js +7 -0
  50. package/dist/esm/common-utils/utils/strategies/leverage/index.js +6 -0
  51. package/dist/esm/common-utils/utils/strategies/leverage/max-leverage-threshold.js +18 -0
  52. package/dist/esm/common-utils/utils/strategies/leverage/max-leverage.js +11 -0
  53. package/dist/esm/common-utils/utils/strategies/sort-strategy-cms-by-availability/index.js +1 -0
  54. package/dist/esm/common-utils/utils/strategies/sort-strategy-cms-by-availability/sort-strategy-cms-by-availability.js +43 -0
  55. package/dist/esm/common-utils/utils/strategies/strategy-info/cm-availability-condition.js +43 -0
  56. package/dist/esm/common-utils/utils/strategies/strategy-info/get-strategy-info.js +74 -0
  57. package/dist/esm/common-utils/utils/strategies/strategy-info/get-strategy-max-apy.js +85 -0
  58. package/dist/esm/common-utils/utils/strategies/strategy-info/index.js +5 -0
  59. package/dist/esm/common-utils/utils/strategies/strategy-info/is-strategy-cm-disabled.js +9 -0
  60. package/dist/esm/common-utils/utils/strategies/strategy-info/types.js +0 -0
  61. package/dist/types/common-utils/utils/apy/bonus-apy-from-points.d.ts +4 -0
  62. package/dist/types/common-utils/utils/apy/calculate-effective-borrow-rate.d.ts +6 -0
  63. package/dist/types/common-utils/utils/apy/get-complex-apy-list.d.ts +5 -0
  64. package/dist/types/common-utils/utils/apy/get-rate-with-fee.d.ts +7 -0
  65. package/dist/types/common-utils/utils/apy/get-single-quota-borrow-rate.d.ts +9 -0
  66. package/dist/types/common-utils/utils/apy/index.d.ts +6 -0
  67. package/dist/types/common-utils/utils/apy/max-apy-formula.d.ts +6 -0
  68. package/dist/types/common-utils/utils/index.d.ts +2 -0
  69. package/dist/types/common-utils/utils/strategies/__test-utils.d.ts +11 -0
  70. package/dist/types/common-utils/utils/strategies/availability/check-boolean.d.ts +1 -0
  71. package/dist/types/common-utils/utils/strategies/availability/check-degen-nft.d.ts +5 -0
  72. package/dist/types/common-utils/utils/strategies/availability/index.d.ts +4 -0
  73. package/dist/types/common-utils/utils/strategies/availability/validate-open-account-pool-quota-status.d.ts +6 -0
  74. package/dist/types/common-utils/utils/strategies/availability/validate-open-account-pool-status.d.ts +24 -0
  75. package/dist/types/common-utils/utils/strategies/index.d.ts +4 -0
  76. package/dist/types/common-utils/utils/strategies/leverage/calculate-loss-coefficient.d.ts +1 -0
  77. package/dist/types/common-utils/utils/strategies/leverage/calculate-max-leverage-factor.d.ts +12 -0
  78. package/dist/types/common-utils/utils/strategies/leverage/get-factor-from-leverage.d.ts +4 -0
  79. package/dist/types/common-utils/utils/strategies/leverage/get-leverage-from-factor.d.ts +2 -0
  80. package/dist/types/common-utils/utils/strategies/leverage/index.d.ts +6 -0
  81. package/dist/types/common-utils/utils/strategies/leverage/max-leverage-threshold.d.ts +5 -0
  82. package/dist/types/common-utils/utils/strategies/leverage/max-leverage.d.ts +9 -0
  83. package/dist/types/common-utils/utils/strategies/sort-strategy-cms-by-availability/index.d.ts +1 -0
  84. package/dist/types/common-utils/utils/strategies/sort-strategy-cms-by-availability/sort-strategy-cms-by-availability.d.ts +13 -0
  85. package/dist/types/common-utils/utils/strategies/strategy-info/cm-availability-condition.d.ts +3 -0
  86. package/dist/types/common-utils/utils/strategies/strategy-info/get-strategy-info.d.ts +2 -0
  87. package/dist/types/common-utils/utils/strategies/strategy-info/get-strategy-max-apy.d.ts +13 -0
  88. package/dist/types/common-utils/utils/strategies/strategy-info/index.d.ts +5 -0
  89. package/dist/types/common-utils/utils/strategies/strategy-info/is-strategy-cm-disabled.d.ts +2 -0
  90. package/dist/types/common-utils/utils/strategies/strategy-info/types.d.ts +80 -0
  91. package/package.json +1 -1
@@ -0,0 +1,11 @@
1
+ function calculateEffectiveBorrowRate({
2
+ underlyingTokenAddress,
3
+ baseRateWithFee = 0,
4
+ apyList
5
+ }) {
6
+ const apy = underlyingTokenAddress ? apyList?.[underlyingTokenAddress] || 0 : 0;
7
+ return apy > 0 ? baseRateWithFee + apy : baseRateWithFee;
8
+ }
9
+ export {
10
+ calculateEffectiveBorrowRate
11
+ };
@@ -0,0 +1,21 @@
1
+ import { TypedObjectUtils } from "../../../sdk/index.js";
2
+ function getComplexAPYList(baseAPYList, extraCollateralAPYList, pool) {
3
+ if (!pool) return baseAPYList;
4
+ const poolExtraCollateralAPY = extraCollateralAPYList?.[pool];
5
+ if (!poolExtraCollateralAPY) return baseAPYList;
6
+ const baseCopy = { ...baseAPYList };
7
+ TypedObjectUtils.entries(poolExtraCollateralAPY).forEach(
8
+ ([token, extraAPY]) => {
9
+ const baseAPY = baseCopy[token];
10
+ if (extraAPY.type === "relative" && baseAPY !== void 0) {
11
+ baseCopy[token] = baseAPY + extraAPY.value;
12
+ } else if (extraAPY.type === "absolute") {
13
+ baseCopy[token] = extraAPY.value;
14
+ }
15
+ }
16
+ );
17
+ return baseCopy;
18
+ }
19
+ export {
20
+ getComplexAPYList
21
+ };
@@ -0,0 +1,7 @@
1
+ import { PERCENTAGE_FACTOR, toBigInt } from "../../../sdk/index.js";
2
+ function getRateWithFee(rate, feeInterest) {
3
+ return toBigInt(rate) * (BigInt(feeInterest) + PERCENTAGE_FACTOR) / PERCENTAGE_FACTOR;
4
+ }
5
+ export {
6
+ getRateWithFee
7
+ };
@@ -0,0 +1,9 @@
1
+ import { calcQuotaBorrowRate } from "../creditAccount/calc-quota-borrow-rate.js";
2
+ import { getRateWithFee } from "./get-rate-with-fee.js";
3
+ function getSingleQuotaBorrowRate(props) {
4
+ const qr = calcQuotaBorrowRate(props);
5
+ return getRateWithFee(qr, props.feeInterest);
6
+ }
7
+ export {
8
+ getSingleQuotaBorrowRate
9
+ };
@@ -0,0 +1,6 @@
1
+ export * from "./bonus-apy-from-points.js";
2
+ export * from "./calculate-effective-borrow-rate.js";
3
+ export * from "./get-complex-apy-list.js";
4
+ export * from "./get-rate-with-fee.js";
5
+ export * from "./get-single-quota-borrow-rate.js";
6
+ export * from "./max-apy-formula.js";
@@ -0,0 +1,16 @@
1
+ import { LEVERAGE_DECIMALS } from "../../../sdk/index.js";
2
+ import { getFactorFromLeverage } from "../strategies/leverage/index.js";
3
+ function maxAPYFormula({
4
+ apy,
5
+ leverage,
6
+ baseRateWithFee,
7
+ quotaRateWithFee
8
+ }) {
9
+ const collateralTerm = apy - quotaRateWithFee;
10
+ const leverageFactor = getFactorFromLeverage(leverage);
11
+ const debtTerm = (apy - baseRateWithFee - quotaRateWithFee) * Number(leverageFactor) / Number(LEVERAGE_DECIMALS);
12
+ return collateralTerm + Math.floor(debtTerm);
13
+ }
14
+ export {
15
+ maxAPYFormula
16
+ };
@@ -1,4 +1,6 @@
1
+ export * from "./apy/index.js";
1
2
  export * from "./assets-math.js";
2
3
  export * from "./bigint-math.js";
3
4
  export * from "./creditAccount/index.js";
4
5
  export * from "./price-math.js";
6
+ export * from "./strategies/index.js";
@@ -0,0 +1,65 @@
1
+ const mockToken1 = "0x1111111111111111111111111111111111111111";
2
+ const mockToken2 = "0x2222222222222222222222222222222222222222";
3
+ const mockUnderlyingToken = "0x9999999999999999999999999999999999999999";
4
+ const mockTokenData = {
5
+ [mockToken1]: { address: mockToken1, decimals: 18, title: "T1" },
6
+ [mockToken2]: { address: mockToken2, decimals: 18, title: "T2" },
7
+ [mockUnderlyingToken]: {
8
+ address: mockUnderlyingToken,
9
+ decimals: 18,
10
+ title: "UNDER"
11
+ }
12
+ };
13
+ function buildQuota(overrides) {
14
+ return {
15
+ rate: 0n,
16
+ quotaIncreaseFee: 0n,
17
+ totalQuoted: 0n,
18
+ limit: 0n,
19
+ isActive: true,
20
+ ...overrides
21
+ };
22
+ }
23
+ function buildPool(overrides = {}) {
24
+ const address = overrides.address ?? "0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";
25
+ return {
26
+ address,
27
+ totalDebtLimit: 0n,
28
+ totalBorrowed: 0n,
29
+ ...overrides
30
+ };
31
+ }
32
+ function buildCreditManager(overrides = {}) {
33
+ const address = overrides.address ?? "0xbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb";
34
+ const pool = overrides.pool ?? "0xcccccccccccccccccccccccccccccccccccccccc";
35
+ const underlyingToken = overrides.underlyingToken ?? mockUnderlyingToken;
36
+ const quotas = overrides.quotas ?? {};
37
+ return {
38
+ address,
39
+ underlyingToken,
40
+ pool,
41
+ chainId: 1,
42
+ baseBorrowRate: 0,
43
+ feeInterest: 0,
44
+ availableToBorrow: 0n,
45
+ minDebt: 0n,
46
+ maxDebt: 0n,
47
+ totalDebt: 0n,
48
+ totalDebtLimit: 0n,
49
+ isDegenMode: false,
50
+ degenNFT: "0x0000000000000000000000000000000000000000",
51
+ liquidationThresholds: {},
52
+ quotas,
53
+ collateralTokens: [],
54
+ ...overrides
55
+ };
56
+ }
57
+ export {
58
+ buildCreditManager,
59
+ buildPool,
60
+ buildQuota,
61
+ mockToken1,
62
+ mockToken2,
63
+ mockTokenData,
64
+ mockUnderlyingToken
65
+ };
@@ -0,0 +1,9 @@
1
+ function checkBoolean(a, b) {
2
+ if (a && b) return 0;
3
+ if (a) return -1;
4
+ if (b) return 1;
5
+ return 0;
6
+ }
7
+ export {
8
+ checkBoolean
9
+ };
@@ -0,0 +1,11 @@
1
+ import { ADDRESS_0X0 } from "../../../../sdk/index.js";
2
+ function checkDegenNFT(creditManager) {
3
+ const nftAddress = creditManager.isDegenMode ? creditManager.degenNFT : ADDRESS_0X0;
4
+ return {
5
+ nftAddress,
6
+ freeOfNFT: nftAddress === ADDRESS_0X0
7
+ };
8
+ }
9
+ export {
10
+ checkDegenNFT
11
+ };
@@ -0,0 +1,4 @@
1
+ export * from "./check-boolean.js";
2
+ export * from "./check-degen-nft.js";
3
+ export * from "./validate-open-account-pool-quota-status.js";
4
+ export * from "./validate-open-account-pool-status.js";
@@ -0,0 +1,16 @@
1
+ function validateOpenAccountPoolQuotaStatus(targetToken, creditManager, amountToBorrow) {
2
+ const quota = creditManager.quotas[targetToken];
3
+ if (quota) {
4
+ const realLimit = quota.isActive ? quota.limit : 0n;
5
+ const quotaLeft = realLimit - quota.totalQuoted;
6
+ if (quotaLeft < amountToBorrow)
7
+ return {
8
+ message: "insufficientQuota",
9
+ token: targetToken
10
+ };
11
+ }
12
+ return null;
13
+ }
14
+ export {
15
+ validateOpenAccountPoolQuotaStatus
16
+ };
@@ -0,0 +1,52 @@
1
+ import { BigIntMath } from "../../bigint-math.js";
2
+ import { validateOpenAccountPoolQuotaStatus } from "./validate-open-account-pool-quota-status.js";
3
+ function validateOpenAccountPoolStatus(props) {
4
+ const { debt, creditManager, pool, targetToken } = props;
5
+ const effectiveDebt = BigIntMath.max(creditManager.minDebt, debt);
6
+ const hasDebtLimit = creditManager.totalDebtLimit >= 0n;
7
+ const debtLimitLeft = BigIntMath.max(
8
+ creditManager.totalDebtLimit - creditManager.totalDebt,
9
+ 0n
10
+ );
11
+ const { totalDebtLimit = 0n, totalBorrowed = 0n } = pool || {};
12
+ const hasPoolDebtLimit = totalDebtLimit > 0n;
13
+ const poolDebtLimitLeft = totalDebtLimit - totalBorrowed;
14
+ const canOpenMinDebt = creditManager.minDebt <= debtLimitLeft && creditManager.minDebt <= poolDebtLimitLeft && creditManager.minDebt <= creditManager.availableToBorrow;
15
+ const minPositionSize = BigIntMath.min(
16
+ BigIntMath.min(debtLimitLeft, poolDebtLimitLeft),
17
+ creditManager.availableToBorrow
18
+ );
19
+ if (hasDebtLimit && effectiveDebt > debtLimitLeft) {
20
+ return {
21
+ message: "insufficientDebtLimit",
22
+ amount: debtLimitLeft,
23
+ solutionAmount: canOpenMinDebt ? minPositionSize : void 0
24
+ };
25
+ }
26
+ if (hasPoolDebtLimit && effectiveDebt > poolDebtLimitLeft) {
27
+ return {
28
+ message: "insufficientPoolDebtLimit",
29
+ amount: poolDebtLimitLeft,
30
+ solutionAmount: canOpenMinDebt ? minPositionSize : void 0
31
+ };
32
+ }
33
+ if (effectiveDebt > creditManager.availableToBorrow) {
34
+ return {
35
+ message: "insufficientPoolLiquidity",
36
+ amount: creditManager.availableToBorrow,
37
+ solutionAmount: canOpenMinDebt ? minPositionSize : void 0
38
+ };
39
+ }
40
+ if (targetToken !== null) {
41
+ const quotaError = validateOpenAccountPoolQuotaStatus(
42
+ targetToken,
43
+ creditManager,
44
+ effectiveDebt
45
+ );
46
+ if (quotaError) return quotaError;
47
+ }
48
+ return null;
49
+ }
50
+ export {
51
+ validateOpenAccountPoolStatus
52
+ };
@@ -0,0 +1,4 @@
1
+ export * from "./availability/index.js";
2
+ export * from "./leverage/index.js";
3
+ export * from "./sort-strategy-cms-by-availability/index.js";
4
+ export * from "./strategy-info/index.js";
@@ -0,0 +1,7 @@
1
+ import { SLIPPAGE_DECIMALS, toBigInt } from "../../../../sdk/index.js";
2
+ function calculateLossCoefficient(slippage, constantLoss = 30n) {
3
+ return 100n * SLIPPAGE_DECIMALS - toBigInt(slippage) - constantLoss;
4
+ }
5
+ export {
6
+ calculateLossCoefficient
7
+ };
@@ -0,0 +1,21 @@
1
+ import { PERCENTAGE_FACTOR } from "../../../../sdk/index.js";
2
+ import { BigIntMath } from "../../bigint-math.js";
3
+ import { calculateLossCoefficient } from "./calculate-loss-coefficient.js";
4
+ import { maxLeverage } from "./max-leverage.js";
5
+ const DEFAULT_LEVERAGE_CONSTANT_LOSS = 500n;
6
+ function calculateMaxLeverageFactor({
7
+ targetToken,
8
+ slippage,
9
+ creditManagers,
10
+ constantLoss = DEFAULT_LEVERAGE_CONSTANT_LOSS,
11
+ leverageLimit
12
+ }) {
13
+ const maxPossibleLeverage = maxLeverage(targetToken, creditManagers);
14
+ const coefficient = calculateLossCoefficient(slippage, constantLoss);
15
+ const maxLeverageValue = BigInt(maxPossibleLeverage) * coefficient / PERCENTAGE_FACTOR;
16
+ const r = leverageLimit !== void 0 ? BigIntMath.min(BigInt(leverageLimit), maxLeverageValue) : maxLeverageValue;
17
+ return r;
18
+ }
19
+ export {
20
+ calculateMaxLeverageFactor
21
+ };
@@ -0,0 +1,7 @@
1
+ import { LEVERAGE_DECIMALS } from "../../../../sdk/index.js";
2
+ function getFactorFromLeverage(leverage) {
3
+ return leverage - LEVERAGE_DECIMALS;
4
+ }
5
+ export {
6
+ getFactorFromLeverage
7
+ };
@@ -0,0 +1,7 @@
1
+ import { LEVERAGE_DECIMALS } from "../../../../sdk/index.js";
2
+ function getLeverageFromFactor(factor) {
3
+ return factor + LEVERAGE_DECIMALS;
4
+ }
5
+ export {
6
+ getLeverageFromFactor
7
+ };
@@ -0,0 +1,6 @@
1
+ export * from "./calculate-loss-coefficient.js";
2
+ export * from "./calculate-max-leverage-factor.js";
3
+ export * from "./get-factor-from-leverage.js";
4
+ export * from "./get-leverage-from-factor.js";
5
+ export * from "./max-leverage.js";
6
+ export * from "./max-leverage-threshold.js";
@@ -0,0 +1,18 @@
1
+ const EMPTY_ADDRESS = "";
2
+ function maxLeverageThreshold(lpToken, cms) {
3
+ const lpTokenLC = lpToken.toLowerCase();
4
+ const ltByCM = cms.map((cm2) => {
5
+ const lt2 = cm2.liquidationThresholds[lpTokenLC] || 0n;
6
+ return [cm2.address, lt2];
7
+ });
8
+ const sorted = ltByCM.sort(([, ltA], [, ltB]) => {
9
+ if (ltA > ltB) return -1;
10
+ if (ltB > ltA) return 1;
11
+ return 0;
12
+ });
13
+ const [cm = EMPTY_ADDRESS, lt = 0n] = sorted[0] || [];
14
+ return [lt, cm];
15
+ }
16
+ export {
17
+ maxLeverageThreshold
18
+ };
@@ -0,0 +1,11 @@
1
+ import { LEVERAGE_DECIMALS, PERCENTAGE_FACTOR } from "../../../../sdk/index.js";
2
+ import { getFactorFromLeverage } from "./get-factor-from-leverage.js";
3
+ import { maxLeverageThreshold } from "./max-leverage-threshold.js";
4
+ function maxLeverage(lpToken, cms, targetHF = PERCENTAGE_FACTOR) {
5
+ const [maxThreshold] = maxLeverageThreshold(lpToken, cms);
6
+ const maxLeverageValue = targetHF * LEVERAGE_DECIMALS / (targetHF - maxThreshold);
7
+ return getFactorFromLeverage(maxLeverageValue);
8
+ }
9
+ export {
10
+ maxLeverage
11
+ };
@@ -0,0 +1 @@
1
+ export * from "./sort-strategy-cms-by-availability.js";
@@ -0,0 +1,43 @@
1
+ import { amountAbcComparator } from "../../creditAccount/sort.js";
2
+ import {
3
+ cmAvailabilityCondition,
4
+ getStrategyMaxAPY
5
+ } from "../strategy-info/index.js";
6
+ function sortStrategyCMsByAvailability({
7
+ targetToken,
8
+ allCreditManagers,
9
+ apyListByNetwork,
10
+ pools,
11
+ slippage,
12
+ quotaReserve,
13
+ leverageLimit,
14
+ isStrategy
15
+ }) {
16
+ const list = [...allCreditManagers].sort((cmA, cmB) => {
17
+ const sort = cmAvailabilityCondition(targetToken, cmA, cmB, pools);
18
+ if (sort !== 0) return sort;
19
+ const apyA = getStrategyMaxAPY(
20
+ targetToken,
21
+ cmA,
22
+ apyListByNetwork,
23
+ slippage,
24
+ quotaReserve,
25
+ leverageLimit
26
+ );
27
+ const apyB = getStrategyMaxAPY(
28
+ targetToken,
29
+ cmB,
30
+ apyListByNetwork,
31
+ slippage,
32
+ quotaReserve,
33
+ leverageLimit
34
+ );
35
+ const sortAPY = isStrategy ? (apyB?.totalMaxApy || 0) - (apyA?.totalMaxApy || 0) : (apyA?.totalBorrowRate || 0) - (apyB?.totalBorrowRate || 0);
36
+ if (sortAPY !== 0) return sortAPY;
37
+ return amountAbcComparator(cmA.maxDebt, cmB.maxDebt);
38
+ });
39
+ return list;
40
+ }
41
+ export {
42
+ sortStrategyCMsByAvailability
43
+ };
@@ -0,0 +1,43 @@
1
+ import {
2
+ checkBoolean,
3
+ checkDegenNFT,
4
+ validateOpenAccountPoolStatus
5
+ } from "../availability/index.js";
6
+ function cmAvailabilityCondition(targetToken, cmA, cmB, pools) {
7
+ const aHasMinError = validateOpenAccountPoolStatus({
8
+ pool: pools?.[cmA.pool],
9
+ debt: cmA.minDebt,
10
+ creditManager: cmA,
11
+ targetToken
12
+ });
13
+ const bHasMinError = validateOpenAccountPoolStatus({
14
+ pool: pools?.[cmB.pool],
15
+ debt: cmB.minDebt,
16
+ creditManager: cmB,
17
+ targetToken
18
+ });
19
+ const minSort = checkBoolean(!aHasMinError, !bHasMinError);
20
+ if (minSort !== 0) return minSort;
21
+ const { freeOfNFT: aFreeOfNFT } = checkDegenNFT(cmA);
22
+ const { freeOfNFT: bFreeOfNFT } = checkDegenNFT(cmB);
23
+ const nftSort = checkBoolean(aFreeOfNFT, bFreeOfNFT);
24
+ if (nftSort !== 0) return nftSort;
25
+ const aHasMaxError = validateOpenAccountPoolStatus({
26
+ pool: pools?.[cmA.pool],
27
+ debt: cmA.maxDebt,
28
+ creditManager: cmA,
29
+ targetToken
30
+ });
31
+ const bHasMaxError = validateOpenAccountPoolStatus({
32
+ pool: pools?.[cmB.pool],
33
+ debt: cmB.maxDebt,
34
+ creditManager: cmB,
35
+ targetToken
36
+ });
37
+ const maxSort = checkBoolean(!aHasMaxError, !bHasMaxError);
38
+ if (maxSort !== 0) return maxSort;
39
+ return 0;
40
+ }
41
+ export {
42
+ cmAvailabilityCondition
43
+ };
@@ -0,0 +1,74 @@
1
+ import { PriceUtils } from "../../price-math.js";
2
+ import { getFactorFromLeverage } from "../leverage/index.js";
3
+ import { sortStrategyCMsByAvailability } from "../sort-strategy-cms-by-availability/index.js";
4
+ import { getStrategyMaxAPY } from "./get-strategy-max-apy.js";
5
+ import { isStrategyCMDisabled } from "./is-strategy-cm-disabled.js";
6
+ const EMPTY_ADDRESS = "";
7
+ const EMPTY_CHAIN_ID = 0;
8
+ function getStrategyInfo({
9
+ strategy,
10
+ creditManagers,
11
+ sdkStateByChain,
12
+ apyListByNetwork,
13
+ quotaReserve,
14
+ slippage,
15
+ allPricesByChain
16
+ }) {
17
+ const strategyCMs = creditManagers?.[strategy.chainId]?.[strategy.id] || {};
18
+ const strategyCMsList = Object.values(strategyCMs);
19
+ if (strategyCMsList.length === 0) return void 0;
20
+ const openableCMsList = strategyCMsList.filter(
21
+ (cm) => !isStrategyCMDisabled(cm, cm.quotas[strategy.tokenOutAddress])
22
+ );
23
+ const currentSdkState = sdkStateByChain?.[strategy.chainId];
24
+ const pools = currentSdkState?.pools;
25
+ const tokensList = currentSdkState?.tokens?.tokenDataList;
26
+ const targetTokenAddress = strategy.tokenOutAddress;
27
+ const minCreditManager = sortStrategyCMsByAvailability({
28
+ targetToken: targetTokenAddress,
29
+ allCreditManagers: openableCMsList.length > 0 ? openableCMsList : strategyCMsList,
30
+ apyListByNetwork,
31
+ slippage,
32
+ quotaReserve,
33
+ pools,
34
+ leverageLimit: strategy.maxLeverage,
35
+ isStrategy: true
36
+ })?.[0] || strategyCMsList[0];
37
+ const { underlyingToken = EMPTY_ADDRESS, availableToBorrow = 0n } = minCreditManager || {};
38
+ const {
39
+ bonusAPY,
40
+ totalMaxApy = 0,
41
+ maxLeverage = 0n,
42
+ baseBorrowRate = 0,
43
+ quotaRateMin = 0n
44
+ } = getStrategyMaxAPY(
45
+ targetTokenAddress,
46
+ minCreditManager,
47
+ apyListByNetwork,
48
+ slippage,
49
+ quotaReserve,
50
+ strategy.maxLeverage
51
+ ) || {};
52
+ const prices = allPricesByChain?.[minCreditManager?.chainId ?? EMPTY_CHAIN_ID]?.prices?.[minCreditManager?.pool || EMPTY_ADDRESS];
53
+ const underlyingPrice = prices?.[underlyingToken] || 0n;
54
+ const underlyingDecimals = tokensList?.[underlyingToken]?.decimals || 18;
55
+ const availableToBorrowMoney = PriceUtils.calcTotalPrice(
56
+ underlyingPrice,
57
+ availableToBorrow,
58
+ underlyingDecimals
59
+ );
60
+ const r = BigInt(baseBorrowRate) * getFactorFromLeverage(maxLeverage) / maxLeverage;
61
+ const qr = quotaRateMin;
62
+ const totalBorrowRate = Number(r + qr);
63
+ return {
64
+ maxLeverage,
65
+ maxAPY: totalMaxApy,
66
+ bonusAPY,
67
+ totalBorrowRate,
68
+ availableToBorrowMoney,
69
+ minCreditManager
70
+ };
71
+ }
72
+ export {
73
+ getStrategyInfo
74
+ };
@@ -0,0 +1,85 @@
1
+ import {
2
+ LEVERAGE_DECIMALS,
3
+ PERCENTAGE_FACTOR,
4
+ toBigInt
5
+ } from "../../../../sdk/index.js";
6
+ import { BONUS_APY_FROM_POINTS } from "../../apy/bonus-apy-from-points.js";
7
+ import { calculateEffectiveBorrowRate } from "../../apy/calculate-effective-borrow-rate.js";
8
+ import { getComplexAPYList } from "../../apy/get-complex-apy-list.js";
9
+ import { getSingleQuotaBorrowRate } from "../../apy/get-single-quota-borrow-rate.js";
10
+ import { maxAPYFormula } from "../../apy/max-apy-formula.js";
11
+ import {
12
+ calculateMaxLeverageFactor,
13
+ getLeverageFromFactor
14
+ } from "../leverage/index.js";
15
+ function getStrategyMaxAPY(targetToken, cm, apyListByNetwork, slippage, quotaReserve, leverageLimit) {
16
+ if (!cm) return void 0;
17
+ const apyRecord = getComplexAPYList(
18
+ apyListByNetwork?.[cm.chainId]?.apyList,
19
+ apyListByNetwork?.[cm.chainId]?.extraCollateralAPYList,
20
+ cm.pool
21
+ );
22
+ const baseRateWithFee = calculateEffectiveBorrowRate({
23
+ underlyingTokenAddress: cm.underlyingToken,
24
+ baseRateWithFee: cm.baseBorrowRate,
25
+ apyList: apyRecord
26
+ });
27
+ const lt = cm.liquidationThresholds[targetToken] || 0n;
28
+ const feeInterest = cm.feeInterest;
29
+ const tokenQuota = cm.quotas[targetToken] || {
30
+ token: targetToken,
31
+ rate: 0n,
32
+ quotaIncreaseFee: 0n,
33
+ totalQuoted: 0n,
34
+ limit: 0n,
35
+ isActive: true
36
+ };
37
+ const qRate = (tokenQuota?.rate || 0n) * lt / PERCENTAGE_FACTOR;
38
+ const qRate_reserve = qRate * (PERCENTAGE_FACTOR + toBigInt(quotaReserve)) / PERCENTAGE_FACTOR;
39
+ const quotaRateWithFee = getSingleQuotaBorrowRate({
40
+ quotaRates: {
41
+ [targetToken]: {
42
+ ...tokenQuota,
43
+ rate: qRate_reserve
44
+ }
45
+ },
46
+ feeInterest,
47
+ quotas: {
48
+ [targetToken]: {
49
+ token: targetToken,
50
+ balance: 1n
51
+ }
52
+ }
53
+ });
54
+ const leverage = getLeverageFromFactor(
55
+ calculateMaxLeverageFactor({
56
+ targetToken,
57
+ creditManagers: [cm],
58
+ slippage,
59
+ leverageLimit
60
+ })
61
+ );
62
+ const apy = apyRecord?.[targetToken] || 0;
63
+ const maxAPY = apyRecord ? maxAPYFormula({
64
+ apy,
65
+ leverage,
66
+ baseRateWithFee,
67
+ quotaRateWithFee: Number(quotaRateWithFee)
68
+ }) : void 0;
69
+ const bonusAPY = BONUS_APY_FROM_POINTS[targetToken];
70
+ const bonusAPYTotal = BigInt(bonusAPY?.value || 0) * leverage / LEVERAGE_DECIMALS;
71
+ const totalMaxApy = (maxAPY || 0) + Number(bonusAPYTotal);
72
+ const totalBorrowRate = baseRateWithFee + Number(quotaRateWithFee);
73
+ return {
74
+ totalMaxApy,
75
+ bonusAPY,
76
+ maxAPY: maxAPY || 0,
77
+ maxLeverage: leverage,
78
+ quotaRateMin: quotaRateWithFee,
79
+ baseBorrowRate: baseRateWithFee,
80
+ totalBorrowRate
81
+ };
82
+ }
83
+ export {
84
+ getStrategyMaxAPY
85
+ };
@@ -0,0 +1,5 @@
1
+ export * from "./cm-availability-condition.js";
2
+ export * from "./get-strategy-info.js";
3
+ export * from "./get-strategy-max-apy.js";
4
+ export * from "./is-strategy-cm-disabled.js";
5
+ export * from "./types.js";
@@ -0,0 +1,9 @@
1
+ function isStrategyCMDisabled(cm, quota) {
2
+ if (!quota) return true;
3
+ const realLimit = quota.isActive ? quota.limit : 0n;
4
+ const quotaLeft = realLimit - quota.totalQuoted;
5
+ return cm.availableToBorrow < cm.minDebt || quotaLeft < cm.minDebt;
6
+ }
7
+ export {
8
+ isStrategyCMDisabled
9
+ };
@@ -0,0 +1,4 @@
1
+ import type { Address } from "viem";
2
+ export declare const BONUS_APY_FROM_POINTS: Record<Address, {
3
+ value: number;
4
+ } | undefined>;
@@ -0,0 +1,6 @@
1
+ import type { Address } from "viem";
2
+ export declare function calculateEffectiveBorrowRate({ underlyingTokenAddress, baseRateWithFee, apyList, }: {
3
+ underlyingTokenAddress: Address | undefined;
4
+ baseRateWithFee?: number;
5
+ apyList: Record<Address, number> | undefined;
6
+ }): number;
@@ -0,0 +1,5 @@
1
+ import type { Address } from "viem";
2
+ export declare function getComplexAPYList<T extends Address | undefined = undefined>(baseAPYList: Record<Address, number> | undefined, extraCollateralAPYList: Record<Address, Record<Address, {
3
+ type: "relative" | "absolute";
4
+ value: number;
5
+ }>> | undefined, pool: T | undefined): Record<Address, number> | undefined;
@@ -0,0 +1,7 @@
1
+ /**
2
+ * Adds fee interest to a rate
3
+ * @param rate
4
+ * @param feeInterest = in PERCENTAGE_FACTOR
5
+ * @returns
6
+ */
7
+ export declare function getRateWithFee(rate: number | bigint, feeInterest: number): bigint;
@@ -0,0 +1,9 @@
1
+ import type { CalcQuotaBorrowRateProps } from "../creditAccount/calc-quota-borrow-rate.js";
2
+ export interface GetSingleQuotaBorrowRateRate extends CalcQuotaBorrowRateProps {
3
+ feeInterest: number;
4
+ }
5
+ /**
6
+ * Under the hood sums up rates for all given quotas and then multiplies them by 1+feeInterest,
7
+ * but it is expected that the ONLY quota will be passed
8
+ */
9
+ export declare function getSingleQuotaBorrowRate(props: GetSingleQuotaBorrowRateRate): bigint;