Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 22 additions & 4 deletions src/services/CoinGeckoPriceProvider.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
import axios, { AxiosRequestConfig } from 'axios';
import { inject, injectable } from 'inversify';
import axios from 'axios';
import { injectable } from 'inversify';
import { IPriceProvider, TokenInfo } from './IPriceProvider';
import { ContainerTypes } from '../containertypes';
import { IFirebaseService } from './FirebaseService';

/**
* Provides token price by using Coin Gecko API
Expand Down Expand Up @@ -30,6 +28,26 @@ export class CoinGeckoPriceProvider implements IPriceProvider {
return 0;
}

public async getPrices(symbol: string, currencies = ['usd']): Promise<Map<string, number>> {
const tokenSymbol = await this.getTokenId(symbol);
const prices = new Map<string, number>();
currencies.map((c) => prices.set(c, 0));

if (tokenSymbol) {
const url = `${CoinGeckoPriceProvider.BaseUrl}/simple/price?ids=${tokenSymbol}&vs_currencies=${currencies}`;
const result = await axios.get(url);

for (const [key, _] of prices) {
if (result.data[tokenSymbol]) {
const price = result.data[tokenSymbol][key];
prices.set(key, Number(price ?? 0));
}
}
}

return prices;
}

public async getPriceWithTimestamp(symbol: string, currency: string | undefined): Promise<TokenInfo> {
const price = await this.getPrice(symbol, currency);

Expand Down
4 changes: 4 additions & 0 deletions src/services/DiaDataPriceProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,10 @@ export class DiaDataPriceProvider implements IPriceProvider {
return 0;
}

public async getPrices(symbol: string, currencies: string[]): Promise<Map<string, number>> {
throw new Error('DIA Data API does not support multiple currencies in a single request.');
}

public async getPriceWithTimestamp(symbol: string): Promise<{ price: number; lastUpdated: number }> {
const price = await this.getPrice(symbol);

Expand Down
9 changes: 8 additions & 1 deletion src/services/IPriceProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,18 @@ export type TokenInfo = {
*/
export interface IPriceProvider {
/**
* Gets current token price in USD.
* Gets current token price in a given currency.
* @param tokenInfo Token information.
*/
getPrice(symbol: string, currency: string | undefined): Promise<number>;

/**
* Gets current token prices in a given list of currencies.
* @param symbol Token symbol.
* @param currencies
*/
getPrices(symbol: string, currencies: string[]): Promise<Map<string, number>>;

/**
* Gets current token price in USD with timestamp.
* @param tokenInfo Token price and timestamp.
Expand Down
4 changes: 4 additions & 0 deletions src/services/PriceProviderWithFailover.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,10 @@ export class PriceProviderWithFailover implements IPriceProvider {
return priceInfo.price;
}

public async getPrices(symbol: string, currencies: string[]): Promise<Map<string, number>> {
throw new Error('getPrices method is not implemented in PriceProviderWithFailover.');
}

public async getPriceWithTimestamp(symbol: string, currency = 'usd'): Promise<TokenInfo> {
Guard.ThrowIfUndefined('symbol', symbol);

Expand Down
12 changes: 6 additions & 6 deletions src/services/StatsService.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ const delay = (ms: number) => new Promise((resolve) => setTimeout(resolve, ms));
export class StatsService extends DappStakingV3IndexerBase implements IStatsService {
constructor(
@inject(ContainerTypes.ApiFactory) private _apiFactory: IApiFactory,
@inject(ContainerTypes.PriceProviderWithFailover) private _priceProvider: IPriceProvider,
@inject(ContainerTypes.PriceProvider) private _coinGeckoPriceProvider: IPriceProvider,
) {
super();
}
Expand Down Expand Up @@ -106,11 +106,11 @@ export class StatsService extends DappStakingV3IndexerBase implements IStatsServ
]);

const prices: number[] = [];
for (const currency of currencies) {
const price = await this._priceProvider.getPrice(tokenSymbol.toLowerCase(), currency);
prices.push(price);
await delay(1000); // To avoid hitting the API rate limit
}
const result = await this._coinGeckoPriceProvider.getPrices(tokenSymbol.toLowerCase(), currencies);
currencies.map((currency) => {
const price = result.get(currency.toLowerCase());
prices.push(price ?? 0);
});

const totalBalancesToExclude = this.getTotalBalanceToExclude(balancesToExclude);
const circulatingSupplyWei = totalSupply.sub(totalBalancesToExclude);
Expand Down