From 34cf657ce5b9bd5bb57c5c797b06216d6e5c0e4d Mon Sep 17 00:00:00 2001 From: Metodi <38468321+metodi96@users.noreply.github.com> Date: Fri, 13 Dec 2024 08:49:29 +0200 Subject: [PATCH] Add Nolus lending pools for USDC, BTC and SOL (#1651) --- src/adaptors/nolus-protocol/index.js | 67 ++++++++++++++++++++++------ 1 file changed, 53 insertions(+), 14 deletions(-) diff --git a/src/adaptors/nolus-protocol/index.js b/src/adaptors/nolus-protocol/index.js index 1962eb6338..4e18e1038a 100644 --- a/src/adaptors/nolus-protocol/index.js +++ b/src/adaptors/nolus-protocol/index.js @@ -1,21 +1,42 @@ const utils = require('../utils') const _ = require('lodash') +const BigNumber = require('bignumber.js'); // Osmosis Noble USDC Protocol Contracts (OSMOSIS-OSMOSIS-USDC_NOBLE) pirin-1 -const osmosisNobleOracleAddr = 'nolus1vjlaegqa7ssm2ygf2nnew6smsj8ref9cmurerc7pzwxqjre2wzpqyez4w6' -const osmosisNobleLppAddr = 'nolus1ueytzwqyadm6r0z8ajse7g6gzum4w3vv04qazctf8ugqrrej6n4sq027cf' +const osmosisUsdcOracleAddr = 'nolus1vjlaegqa7ssm2ygf2nnew6smsj8ref9cmurerc7pzwxqjre2wzpqyez4w6' +const osmosisUsdcLppAddr = 'nolus1ueytzwqyadm6r0z8ajse7g6gzum4w3vv04qazctf8ugqrrej6n4sq027cf' -// Astroport Protocol Contracts (NEUTRON-ASTROPORT-USDC_AXELAR) pirin-1 -const astroportOracleAddr = 'nolus1jew4l5nq7m3xhkqzy8j7cc99083m5j8d9w004ayyv8xl3yv4h0dql2dd4e' -const astroportLppAddr = 'nolus1qqcr7exupnymvg6m63eqwu8pd4n5x6r5t3pyyxdy7r97rcgajmhqy3gn94' +// Osmosis stATOM Protocol Contracts (OSMOSIS-OSMOSIS-ST_ATOM) pirin-1 +//Note: APY is 0% atm, so not worth adding, but might in the future +//const osmosisStAtomOracleAddr = 'nolus1mtcv0vhpt94s82mcemj5sc3v94pq3k2g62yfa5p82npfnd3xqx8q2w8c5f' +//const osmosisStAtomLppAddr = 'nolus1jufcaqm6657xmfltdezzz85quz92rmtd88jk5x0hq9zqseem32ysjdm990' + +// Osmosis allBTC Protocol Contracts (OSMOSIS-OSMOSIS-ALL_BTC) pirin-1 +const osmosisAllBtcOracleAddr = 'nolus1y0nlrnw25mh2vxhaupamwca4wdvuxs26tq4tnxgjk8pw0gxevwfq5ry07c' +const osmosisAllBtcLppAddr = 'nolus1w2yz345pqheuk85f0rj687q6ny79vlj9sd6kxwwex696act6qgkqfz7jy3' + +// Osmosis allSOL Protocol Contracts (OSMOSIS-OSMOSIS-ALL_SOL) pirin-1 +const osmosisAllSolOracleAddr = 'nolus153kmhl85vavd03r9c7ardw4fgydge6kvvhrx5v2uvec4eyrlwthsejc6ce' +const osmosisAllSolLppAddr = 'nolus1qufnnuwj0dcerhkhuxefda6h5m24e64v2hfp9pac5lglwclxz9dsva77wm' + +// Osmosis AKT Protocol Contracts (OSMOSIS-OSMOSIS-AKT) pirin-1 +//Note: APY is 0% atm, so not worth adding, but might in the future +//const osmosisAktOracleAddr = 'nolus12sx0kr60rptp846z2wvuwyxn47spg55dcnzwrhl4f7nfdduzsrxq7rfetn' +//const osmosisAktLppAddr = 'nolus1lxr7f5xe02jq6cce4puk6540mtu9sg36at2dms5sk69wdtzdrg9qq0t67z' + +// Astroport USDC Protocol Contracts (NEUTRON-ASTROPORT-USDC_NOBLE) pirin-1 +const astroportUsdcOracleAddr = 'nolus1vhzdx9lqexuqc0wqd48c5hc437yzw7jy7ggum9k25yy2hz7eaatq0mepvn' +const astroportUsdcLppAddr = 'nolus17vsedux675vc44yu7et9m64ndxsy907v7sfgrk7tw3xnjtqemx3q6t3xw6' const contracts = [ - { lpp: osmosisNobleLppAddr, oracle: osmosisNobleOracleAddr }, - { lpp: astroportLppAddr, oracle: astroportOracleAddr } + { lpp: osmosisUsdcLppAddr, oracle: osmosisUsdcOracleAddr, symbol: 'USDC', meta: '', protocolInterest: 40}, + { lpp: osmosisAllBtcLppAddr, oracle: osmosisAllBtcOracleAddr, symbol: 'BTC', meta: '', protocolInterest: 15 }, + { lpp: osmosisAllSolLppAddr, oracle: osmosisAllSolOracleAddr, symbol: 'SOL', meta: '', protocolInterest: 40 }, + { lpp: astroportUsdcLppAddr, oracle: astroportUsdcOracleAddr, symbol: 'USDC', meta: '', protocolInterest: 40 } ] // nolus node rest api -const api = 'https://pirin-cl.nolus.network:1317' +const api = 'https://lcd.nolus.network' // ETL(extract transform load) rest api const etlAddress = 'https://etl-cl.nolus.network:8080' // api/max_ls_interest_7d/{lpp_address} @@ -37,12 +58,30 @@ const getApy = async () => { for (let i = 0; i < contracts.length; i++) { const c = contracts[i]; let lppTickerData = await queryContract(c.lpp, { 'lpn': [] }) - let oracleData = await queryContract(c.oracle, { 'currencies': {} }) - let currencyData = _.find(oracleData.data, (n) => n.ticker == lppTickerData.data) + let oracleCurrenciesData = await queryContract(c.oracle, { 'currencies': {} }) + let oraclePriceData = await queryContract(c.oracle, { 'stable_price': {'currency': lppTickerData.data} }) + let currencyData = _.find(oracleCurrenciesData.data, (n) => n.ticker == lppTickerData.data) let lppBalanceData = await queryContract(c.lpp, { 'lpp_balance': [] }) let dailyMaxLSInterest = await utils.getData(`${etlAddress}/${dailyMaxInterestEp}/${c.lpp}`) let dailyMaxLPRatio = await utils.getData(`${etlAddress}/${maxLpRatioEp}/${c.lpp}`) + // Calculate asset price with BigNumber + const amount = new BigNumber(oraclePriceData.data.amount.amount); + const amountQuote = new BigNumber(oraclePriceData.data.amount_quote.amount); + let price = amountQuote.div(amount); + + // Adjust price for decimal differences + const decimalsAdjustment = { + USDC: 1, + BTC: 100, // 8 - 6 = 2 decimal places difference, 10^2 = 100 + SOL: 1000 // 9 - 6 = 3 decimal places difference, 10^3 = 1000 + }; + price = price.times(decimalsAdjustment[c.symbol] || 1); // Default to 1 if symbol is not in the map + + // Calculate TVL in USD + const balance = new BigNumber(lppBalanceData.data.balance.amount); + const tvlUsd = balance.div(new BigNumber(10).pow(currencyData.decimal_digits)).times(price); + let merged = [] for (const date in dailyMaxLSInterest) { if (!!dailyMaxLPRatio[date]) { @@ -53,7 +92,7 @@ const getApy = async () => { } } - let avg = merged.reduce((acc, curr) => acc + (curr.mli - 40) * curr.mlr, 0) / merged.length + let avg = merged.reduce((acc, curr) => acc + (curr.mli - contracts[i].protocolInterest) * curr.mlr, 0) / merged.length let apr = avg / 10 let apy = (Math.pow((1 + (apr / 100 / 365)), 365) - 1) * 100 @@ -61,13 +100,13 @@ const getApy = async () => { pool: c.lpp, chain: 'Nolus', project: 'nolus-protocol', - symbol: 'USDC', - tvlUsd: Number(lppBalanceData.data.balance.amount) / Math.pow(10, currencyData.decimal_digits), + symbol: contracts[i].symbol, + tvlUsd: tvlUsd.toNumber(), apyBase: apy, // apyReward: null, TODO: add NLS rewards underlyingTokens: [currencyData.bank_symbol, currencyData.dex_symbol], // Array of underlying token addresses from a pool, eg here USDT address on ethereum // rewardTokens: ['0x7Fc66500c84A76Ad7e9c93437bFc5Ac33E2DDaE9'], TODO: add NLS rewards - poolMeta: lppTickerData.data.substr('USDC_'.length), + poolMeta: contracts[i].meta, }) }