Skip to content

Commit

Permalink
Merge pull request #317 from dappradar/injective-DeFi-integration
Browse files Browse the repository at this point in the history
injective chain integration
  • Loading branch information
mantasfam authored Nov 7, 2024
2 parents 2c3451c + 67c8f75 commit b7af952
Show file tree
Hide file tree
Showing 11 changed files with 249 additions and 1 deletion.
1 change: 1 addition & 0 deletions .env.dev
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ TONCENTER_API_KEY=
SKALE-EUROPA_NODE_URL=https://mainnet.skalenodes.com/v1/elated-tan-skat
ETHERLINK_NODE_URL=https://node.mainnet.etherlink.com
BLAST_NODE_URL=https://blastl2-mainnet.public.blastapi.io
INJECTIVE_NODE_URL=https://injective-rpc.publicnode.com:443
##======================== LOGSTASH ========================
LOGSTASH_PORT=
LOGSTASH_HOST=
Expand Down
1 change: 1 addition & 0 deletions src/app.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -72,5 +72,6 @@ nodeUrls['BAHAMUT_NODE_URL'] = process.env['BAHAMUT_NODE_URL'];
nodeUrls['SKALE-EUROPA_NODE_URL'] = process.env['SKALE-EUROPA_NODE_URL'];
nodeUrls['ETHERLINK_NODE_URL'] = process.env['ETHERLINK_NODE_URL'];
nodeUrls['BLAST_NODE_URL'] = process.env['BLAST_NODE_URL'];
nodeUrls['INJECTIVE_NODE_URL'] = process.env['INJECTIVE_NODE_URL'];

export { config, nodeUrls };
6 changes: 5 additions & 1 deletion src/factory/factory.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -75,7 +75,11 @@ export class FactoryService {
});
}

const balances = basicUtil.checkZeroBalance(tvlData.balances);
let balances = basicUtil.checkZeroBalance(tvlData.balances);
balances = Object.keys(balances).reduce((acc, key) => {
acc[key.toLowerCase()] = balances[key];
return acc;
}, {} as { [key: string]: string });
return { balances, poolBalances: tvlData.poolBalances };
}

Expand Down
21 changes: 21 additions & 0 deletions src/factory/providers/injective/astroport/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import formatter from '../../../../util/formatter';
import { ITvlParams, ITvlReturn } from '../../../../interfaces/ITvl';
import cosmosDex from '../../../../util/calculators/cosmosDex';

const ASTROPORT_FACTORY_ADDRESS = 'inj19aenkaj6qhymmt746av8ck4r8euthq3zmxr2r6';

async function tvl(params: ITvlParams): Promise<Partial<ITvlReturn>> {
const { block, chain, provider, web3 } = params;
const balances = await cosmosDex.getTvl(
ASTROPORT_FACTORY_ADDRESS,
block,
chain,
provider,
web3,
);

formatter.convertBalancesToFixed(balances);
return { balances };
}

export { tvl };
27 changes: 27 additions & 0 deletions src/factory/providers/injective/black-panther/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import formatter from '../../../../util/formatter';
import { ITvlParams, ITvlReturn } from '../../../../interfaces/ITvl';
import BigNumber from 'bignumber.js';

const USDT_ADDRESS = 'peggy0xdAC17F958D2ee523a2206206994597C13D831ec7';
const FARM_ADDRESSES = [
'inj1yjnm0d6lxpuk8a4eulnf80gcx954zcf8rq2sfp',
'inj1lw5pd768ghux6dsux24tnqxlqz5pln6kk9rd6c',
];
const METHOD = 'total_vaults_in_usdt';

async function tvl(params: ITvlParams): Promise<Partial<ITvlReturn>> {
const { block, chain, provider, web3 } = params;
const balances = {};

let farmBalance = await web3.eth.call(FARM_ADDRESSES[0], METHOD);
balances[USDT_ADDRESS] = farmBalance;
farmBalance = await web3.eth.call(FARM_ADDRESSES[1], METHOD);
balances[USDT_ADDRESS] = BigNumber(balances[USDT_ADDRESS] || 0).plus(
farmBalance,
);

formatter.convertBalancesToFixed(balances);
return { balances };
}

export { tvl };
32 changes: 32 additions & 0 deletions src/factory/providers/injective/neptune-finance/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import formatter from '../../../../util/formatter';
import { ITvlParams, ITvlReturn } from '../../../../interfaces/ITvl';

const MARKET_ADDRESS = 'inj1nc7gjkf2mhp34a6gquhurg8qahnw5kxs5u3s4u';
const CW20_TOKEN_ADDRESSES = [
'inj18luqttqyckgpddndh8hvaq25d5nfwjc78m56lc',
'inj1rmzufd7h09sqfrre5dtvu5d09ta7c0t4jzkr2f',
'inj1kehk5nvreklhylx22p3x0yjydfsz9fv3fvg5xt',
'inj1cy9hes20vww2yr6crvs75gxy5hpycya2hmjg9s',
'inj1dafy7fv7qczzatd98dv8hekx6ssckrflswpjaz',
'inj16jf4qkcarp3lan4wl2qkrelf4kduvvujwg0780',
'inj1fzquxxxam59z6fzewy2hvvreeh3m04x83zg4vv',
];

async function tvl(params: ITvlParams): Promise<Partial<ITvlReturn>> {
const { block, chain, provider, web3 } = params;
let balances = {};

const marketBalances = await web3.eth.getAccountBalances(MARKET_ADDRESS);
balances = formatter.sum([balances, marketBalances]);

const marketCw20TokenBalances = await web3.eth.getAccountCw20TokenBalances(
MARKET_ADDRESS,
CW20_TOKEN_ADDRESSES,
);
balances = formatter.sum([balances, marketCw20TokenBalances]);

formatter.convertBalancesToFixed(balances);
return { balances };
}

export { tvl };
21 changes: 21 additions & 0 deletions src/factory/providers/injective/white-whale/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import formatter from '../../../../util/formatter';
import { ITvlParams, ITvlReturn } from '../../../../interfaces/ITvl';
import cosmosDex from '../../../../util/calculators/cosmosDex';

const ASTROPORT_FACTORY_ADDRESS = 'inj1x22q8lfhz7qcvtzs0dakhgx2th64l79kfye5lk';

async function tvl(params: ITvlParams): Promise<Partial<ITvlReturn>> {
const { block, chain, provider, web3 } = params;
const balances = await cosmosDex.getTvl(
ASTROPORT_FACTORY_ADDRESS,
block,
chain,
provider,
web3,
);

formatter.convertBalancesToFixed(balances);
return { balances };
}

export { tvl };
73 changes: 73 additions & 0 deletions src/util/calculators/cosmosDex.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import BigNumber from 'bignumber.js';

/**
* Gets TVL of comonly used cosmos DEX clone
*
* @param factoryAddress - The address of factory
* @param block - The block number for which data is requested
* @param chain - EVM chain name (providers parent folder name)
* @param provider - the provider folder name
* @param web3 - The Web3 object
* @returns The standard balances object
*
*/
async function getTvl(
factoryAddress: string,
block: number,
chain: string,
provider: string,
web3: any,
): Promise<{ [key: string]: string }> {
const limit = 30;
let pairs = [];
let iterationPairs = [];

do {
const start_after = pairs.length
? pairs[pairs.length - 1].asset_infos
: undefined;

const query = {
limit,
...(start_after && { start_after }),
};

iterationPairs = await web3.eth
.call(factoryAddress, 'pairs', query)
.then((response) => response['pairs']);

pairs = pairs.concat(iterationPairs);
} while (iterationPairs.length > 0);

const balances = {};

for (const pair of pairs) {
const poolData = await web3.eth.call(pair.contract_addr, 'pool', {});

if (poolData.assets[0].amount !== '0')
try {
balances[poolData.assets[0].info.native_token.denom] = BigNumber(
balances[poolData.assets[0].info.native_token.denom] || 0,
).plus(poolData.assets[0].amount);
} catch {
balances[poolData.assets[0].info.token.contract_addr] = BigNumber(
balances[poolData.assets[0].info.token.contract_addr] || 0,
).plus(poolData.assets[0].amount);
}
if (poolData.assets[1].amount !== '0')
try {
balances[poolData.assets[1].info.native_token.denom] = BigNumber(
balances[poolData.assets[1].info.native_token.denom] || 0,
).plus(poolData.assets[1].amount);
} catch {
balances[poolData.assets[1].info.token.contract_addr] = BigNumber(
balances[poolData.assets[1].info.token.contract_addr] || 0,
).plus(poolData.assets[1].amount);
}
}
return balances;
}

export default {
getTvl,
};
60 changes: 60 additions & 0 deletions src/web3Provider/injective.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
import { Injectable } from '@nestjs/common';
import axios from 'axios';
import Bottleneck from 'bottleneck';
import { nodeUrls } from '../app.config';

const url = nodeUrls.INJECTIVE_NODE_URL;

const limiter = new Bottleneck({
minTime: 100, // 10 request per second
});

@Injectable()
export class Injective {
async call(address: string, method, params = {}): Promise<any> {
let data = {
[method]: params,
};
data = Buffer.from(JSON.stringify(data)).toString('base64');

const response = await limiter
.schedule(() =>
axios.get(`${url}/cosmwasm/wasm/v1/contract/${address}/smart/${data}`),
)
.then((response) => response.data.data);

return response;
}

async getAccountBalances(
address: string,
): Promise<{ [key: string]: string }> {
const balances = {};

const response = await axios
.get(`${url}/cosmos/bank/v1beta1/balances/${address}`)
.then((response) => response.data);
for (const balance of response.balances) {
balances[balance.denom] = balance.amount;
}

return balances;
}

async getAccountCw20TokenBalances(
address: string,
cw20TokenAddresses: string[],
): Promise<{ [key: string]: string }> {
const balances = {};

await Promise.all(
cw20TokenAddresses.map(async (token) => {
balances[token] = await this.call(token, 'balance', { address }).then(
(response) => response['balance'],
);
}),
);

return balances;
}
}
2 changes: 2 additions & 0 deletions src/web3Provider/web3Provider.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { Tezos } from './tezos';
import { Wax } from './wax';
import { Aptos } from './aptos';
import { Ton } from './ton';
import { Injective } from './injective';

@Module({
exports: [Web3ProviderService],
Expand All @@ -20,6 +21,7 @@ import { Ton } from './ton';
Solana,
Stacks,
Tezos,
Injective,
Wax,
Aptos,
Ton,
Expand Down
6 changes: 6 additions & 0 deletions src/web3Provider/web3Provider.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import Web3 from 'web3';
import { Wax } from './wax';
import { Aptos } from './aptos';
import { Ton } from './ton';
import { Injective } from './injective';

const webSocketConfig = {
timeout: 60000,
Expand Down Expand Up @@ -40,6 +41,7 @@ export class Web3ProviderService {
private readonly wax: Wax,
private readonly aptos: Aptos,
private readonly ton: Ton,
private readonly injective: Injective,
) {}

async getWeb3(chain = 'ethereum') {
Expand Down Expand Up @@ -97,6 +99,10 @@ export class Web3ProviderService {
web3 = { eth: this.ton };
break;
}
case 'injective': {
web3 = { eth: this.injective };
break;
}
default: {
if (node_url.startsWith('ws')) {
web3 = new Web3(
Expand Down

0 comments on commit b7af952

Please sign in to comment.