@merkl/api 0.21.16 → 0.21.18

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 (27) hide show
  1. package/dist/database/api/.generated/drizzle/schema.d.ts +3 -3
  2. package/dist/database/api/.generated/drizzle/schema.js +1 -1
  3. package/dist/database/api/.generated/drizzle/schema.ts +1 -1
  4. package/dist/database/api/.generated/edge.js +5 -4
  5. package/dist/database/api/.generated/index-browser.js +2 -1
  6. package/dist/database/api/.generated/index.d.ts +2 -1
  7. package/dist/database/api/.generated/index.js +5 -4
  8. package/dist/database/api/.generated/package.json +1 -1
  9. package/dist/database/api/.generated/schema.prisma +1 -0
  10. package/dist/database/api/.generated/wasm.js +2 -1
  11. package/dist/src/eden/index.d.ts +6 -6
  12. package/dist/src/index.d.ts +2 -2
  13. package/dist/src/modules/v4/chain/chain.repository.d.ts +13 -3
  14. package/dist/src/modules/v4/chain/chain.repository.js +9 -3
  15. package/dist/src/modules/v4/chain/chain.service.d.ts +13 -1
  16. package/dist/src/modules/v4/chain/chain.service.js +6 -4
  17. package/dist/src/modules/v4/merklRoot/merklRoot.service.js +1 -1
  18. package/dist/src/modules/v4/price/price.controller.d.ts +2 -2
  19. package/dist/src/modules/v4/price/price.model.d.ts +2 -0
  20. package/dist/src/modules/v4/price/price.service.js +3 -2
  21. package/dist/src/modules/v4/reward/reward.service.js +1 -1
  22. package/dist/src/modules/v4/router.d.ts +2 -2
  23. package/dist/src/utils/prices/priceFetcherFactory.js +3 -0
  24. package/dist/src/utils/prices/services/OnChainCallService.d.ts +8 -0
  25. package/dist/src/utils/prices/services/OnChainCallService.js +38 -0
  26. package/dist/tsconfig.package.tsbuildinfo +1 -1
  27. package/package.json +1 -1
@@ -1,5 +1,5 @@
1
1
  {
2
- "name": "prisma-client-419016964ef3e36746ac9f349139831509fb50b2bea88e1ae7f856888042729c",
2
+ "name": "prisma-client-ceb673435ac7b0a8d136ed733f33a74af9a61f67dd386904f58de5597ef156f1",
3
3
  "main": "index.js",
4
4
  "types": "index.d.ts",
5
5
  "browser": "index-browser.js",
@@ -452,6 +452,7 @@ enum PriceSourceMethod {
452
452
  DEXSCREENER
453
453
  INDEXCOOP
454
454
  DEFILLAMA
455
+ ONCHAIN_CALL
455
456
  }
456
457
 
457
458
  enum CampaignManualOverride {
@@ -622,7 +622,8 @@ exports.PriceSourceMethod = exports.$Enums.PriceSourceMethod = {
622
622
  ERC4626: 'ERC4626',
623
623
  DEXSCREENER: 'DEXSCREENER',
624
624
  INDEXCOOP: 'INDEXCOOP',
625
- DEFILLAMA: 'DEFILLAMA'
625
+ DEFILLAMA: 'DEFILLAMA',
626
+ ONCHAIN_CALL: 'ONCHAIN_CALL'
626
627
  };
627
628
 
628
629
  exports.LoggedEntityType = exports.$Enums.LoggedEntityType = {
@@ -3204,7 +3204,7 @@ declare const eden: {
3204
3204
  }>>;
3205
3205
  post: (body: {
3206
3206
  symbol: string;
3207
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
3207
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
3208
3208
  args: {};
3209
3209
  }, options: {
3210
3210
  headers: {
@@ -3233,7 +3233,7 @@ declare const eden: {
3233
3233
  }>>;
3234
3234
  patch: (body: {
3235
3235
  symbol?: string | undefined;
3236
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
3236
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
3237
3237
  args?: {} | undefined;
3238
3238
  }, options: {
3239
3239
  headers: {
@@ -9443,7 +9443,7 @@ export declare const MerklApi: (domain: string | import("elysia").default<"", fa
9443
9443
  post: {
9444
9444
  body: {
9445
9445
  symbol: string;
9446
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
9446
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
9447
9447
  args: {};
9448
9448
  };
9449
9449
  params: {};
@@ -9464,7 +9464,7 @@ export declare const MerklApi: (domain: string | import("elysia").default<"", fa
9464
9464
  patch: {
9465
9465
  body: {
9466
9466
  symbol?: string | undefined;
9467
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
9467
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
9468
9468
  args?: {} | undefined;
9469
9469
  };
9470
9470
  params: {
@@ -15670,7 +15670,7 @@ export declare const MerklApi: (domain: string | import("elysia").default<"", fa
15670
15670
  }>>;
15671
15671
  post: (body: {
15672
15672
  symbol: string;
15673
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
15673
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
15674
15674
  args: {};
15675
15675
  }, options: {
15676
15676
  headers: {
@@ -15699,7 +15699,7 @@ export declare const MerklApi: (domain: string | import("elysia").default<"", fa
15699
15699
  }>>;
15700
15700
  patch: (body: {
15701
15701
  symbol?: string | undefined;
15702
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
15702
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
15703
15703
  args?: {} | undefined;
15704
15704
  }, options: {
15705
15705
  headers: {
@@ -3854,7 +3854,7 @@ declare const app: Elysia<"", false, {
3854
3854
  post: {
3855
3855
  body: {
3856
3856
  symbol: string;
3857
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
3857
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
3858
3858
  args: {};
3859
3859
  };
3860
3860
  params: {};
@@ -3875,7 +3875,7 @@ declare const app: Elysia<"", false, {
3875
3875
  patch: {
3876
3876
  body: {
3877
3877
  symbol?: string | undefined;
3878
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
3878
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
3879
3879
  args?: {} | undefined;
3880
3880
  };
3881
3881
  params: {
@@ -51,12 +51,22 @@ export declare class ChainRepository {
51
51
  id: number;
52
52
  icon: string;
53
53
  })[]>;
54
+ static findAll(): Promise<({
55
+ Explorer: {
56
+ url: string;
57
+ type: import("@db/api").$Enums.ExplorerType;
58
+ id: string;
59
+ chainId: number;
60
+ }[];
61
+ } & {
62
+ name: string;
63
+ id: number;
64
+ icon: string;
65
+ })[]>;
54
66
  static countMany(query: ChainSearchDto): Promise<number>;
55
67
  /** Returns all chainIds in the database
56
68
  */
57
- static readIds(): Promise<{
58
- id: number;
59
- }[]>;
69
+ static findManyIds(): Promise<number[]>;
60
70
  /**
61
71
  * Creates a new chain
62
72
  * @param template for chain creation
@@ -28,6 +28,12 @@ export class ChainRepository {
28
28
  ...args,
29
29
  });
30
30
  }
31
+ static async findAll() {
32
+ return await apiDbClient.chain.findMany({
33
+ include: { Explorer: { take: 5 } },
34
+ orderBy: { id: "asc" },
35
+ });
36
+ }
31
37
  static async countMany(query) {
32
38
  const args = ChainRepository.transformQueryToPrismaFilters(query);
33
39
  return apiDbClient.chain.count({
@@ -36,10 +42,10 @@ export class ChainRepository {
36
42
  }
37
43
  /** Returns all chainIds in the database
38
44
  */
39
- static async readIds() {
40
- return apiDbClient.chain.findMany({
45
+ static async findManyIds() {
46
+ return (await apiDbClient.chain.findMany({
41
47
  select: { id: true },
42
- });
48
+ })).map(({ id }) => id);
43
49
  }
44
50
  /**
45
51
  * Creates a new chain
@@ -12,6 +12,18 @@ export declare abstract class ChainService {
12
12
  id: number;
13
13
  icon: string;
14
14
  }) | null>;
15
+ static findAll(): Promise<({
16
+ Explorer: {
17
+ url: string;
18
+ type: import("@db/api").$Enums.ExplorerType;
19
+ id: string;
20
+ chainId: number;
21
+ }[];
22
+ } & {
23
+ name: string;
24
+ id: number;
25
+ icon: string;
26
+ })[]>;
15
27
  static findMany(query: ChainSearchDto): Promise<({
16
28
  Explorer: {
17
29
  url: string;
@@ -41,7 +53,7 @@ export declare abstract class ChainService {
41
53
  * @warning some chains may not be fully integrated yet
42
54
  * @returns an array of chainId
43
55
  */
44
- static getIds(): Promise<number[]>;
56
+ static findManyIds(): Promise<number[]>;
45
57
  /** List all chainIds which have a distribituor (i.e. which is fully integrated)
46
58
  * @returns an array of chainId
47
59
  */
@@ -6,6 +6,9 @@ export class ChainService {
6
6
  static async get(chainId) {
7
7
  return ChainRepository.read(chainId);
8
8
  }
9
+ static async findAll() {
10
+ return await CacheService.wrap(TTLPresets.MIN_10, ChainRepository.findAll);
11
+ }
9
12
  static async findMany(query) {
10
13
  // Bypass cache in test mode
11
14
  if (query.test)
@@ -22,15 +25,14 @@ export class ChainService {
22
25
  * @warning some chains may not be fully integrated yet
23
26
  * @returns an array of chainId
24
27
  */
25
- static async getIds() {
26
- const ids = await ChainRepository.readIds();
27
- return ids.map(({ id }) => id);
28
+ static async findManyIds() {
29
+ return ChainRepository.findManyIds();
28
30
  }
29
31
  /** List all chainIds which have a distribituor (i.e. which is fully integrated)
30
32
  * @returns an array of chainId
31
33
  */
32
34
  static async getSupportedIds() {
33
- const ids = await ChainService.getIds();
35
+ const ids = await ChainService.findManyIds();
34
36
  const supportedIds = [];
35
37
  for (const chainId of ids) {
36
38
  try {
@@ -29,7 +29,7 @@ export class MerklRootService {
29
29
  */
30
30
  static async fetchAll(chainIds) {
31
31
  return await CacheService.wrap(TTLPresets.MIN_1, async () => {
32
- let ids = chainIds ?? (await ChainService.getIds());
32
+ let ids = chainIds ?? (await ChainService.findManyIds());
33
33
  /** Fetch current Merkle Roots */
34
34
  const merkleRootsPromises = await Promise.allSettled(ids.map(chainId => MerklRootService.fetchFromCache(chainId)));
35
35
  /** Filter out unsuccessful chainIds */
@@ -105,7 +105,7 @@ export declare const PriceController: Elysia<"/prices", false, {
105
105
  post: {
106
106
  body: {
107
107
  symbol: string;
108
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
108
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
109
109
  args: {};
110
110
  };
111
111
  params: {};
@@ -126,7 +126,7 @@ export declare const PriceController: Elysia<"/prices", false, {
126
126
  patch: {
127
127
  body: {
128
128
  symbol?: string | undefined;
129
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
129
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
130
130
  args?: {} | undefined;
131
131
  };
132
132
  params: {
@@ -8,6 +8,7 @@ export declare const CreatePriceSourceDto: import("@sinclair/typebox").TObject<{
8
8
  DEXSCREENER: "DEXSCREENER";
9
9
  INDEXCOOP: "INDEXCOOP";
10
10
  DEFILLAMA: "DEFILLAMA";
11
+ ONCHAIN_CALL: "ONCHAIN_CALL";
11
12
  }>;
12
13
  args: import("@sinclair/typebox").TObject<{}>;
13
14
  }>;
@@ -21,6 +22,7 @@ export declare const UpdatePriceSourceDto: import("@sinclair/typebox").TObject<{
21
22
  DEXSCREENER: "DEXSCREENER";
22
23
  INDEXCOOP: "INDEXCOOP";
23
24
  DEFILLAMA: "DEFILLAMA";
25
+ ONCHAIN_CALL: "ONCHAIN_CALL";
24
26
  }>>;
25
27
  args: import("@sinclair/typebox").TOptional<import("@sinclair/typebox").TObject<{}>>;
26
28
  }>;
@@ -48,9 +48,10 @@ export class PriceService {
48
48
  }
49
49
  return price;
50
50
  }
51
- catch {
51
+ catch (e) {
52
+ console.error(e);
52
53
  await PriceRepository.deleteBySymbol(created.symbol);
53
- throw new UnableToFindPrice();
54
+ throw new UnableToFindPrice(e.toString());
54
55
  }
55
56
  }
56
57
  static async updatePriceSource(symbol, newPriceSource) {
@@ -229,7 +229,7 @@ export class RewardService {
229
229
  return rewards;
230
230
  }
231
231
  static async getUserRewardsByChain(user, withToken, chainFilter = [], connectedChainId = null, withTestTokens = false, claimableOnly = false) {
232
- const chains = await ChainService.findMany({});
232
+ const chains = await ChainService.findAll();
233
233
  let chainIds = !chainFilter || !chainFilter.length
234
234
  ? chains.map(({ id }) => id)
235
235
  : chains.map(({ id }) => id).filter(id => chainFilter.includes(id));
@@ -3724,7 +3724,7 @@ export declare const v4: Elysia<"/v4", false, {
3724
3724
  post: {
3725
3725
  body: {
3726
3726
  symbol: string;
3727
- method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA";
3727
+ method: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL";
3728
3728
  args: {};
3729
3729
  };
3730
3730
  params: {};
@@ -3745,7 +3745,7 @@ export declare const v4: Elysia<"/v4", false, {
3745
3745
  patch: {
3746
3746
  body: {
3747
3747
  symbol?: string | undefined;
3748
- method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | undefined;
3748
+ method?: "COINGECKO" | "CONSTANT" | "EQUAL_TO" | "ERC4626" | "DEXSCREENER" | "INDEXCOOP" | "DEFILLAMA" | "ONCHAIN_CALL" | undefined;
3749
3749
  args?: {} | undefined;
3750
3750
  };
3751
3751
  params: {
@@ -1,4 +1,5 @@
1
1
  import { PriceSourceMethod } from "@db/api";
2
+ import OnChainCall from "./services/OnChainCallService";
2
3
  import CoingeckoService from "./services/coinGeckoService";
3
4
  import DefillamaService from "./services/defillamaService";
4
5
  import DexScreenerService from "./services/dexScreenerService";
@@ -22,6 +23,8 @@ export default class PriceFetcherFactory {
22
23
  return DexScreenerService.instance;
23
24
  case PriceSourceMethod.INDEXCOOP:
24
25
  return IndexCoop.instance;
26
+ case PriceSourceMethod.ONCHAIN_CALL:
27
+ return OnChainCall.instance;
25
28
  default:
26
29
  throw new Error(`Price reader service not found for ${type}`);
27
30
  }
@@ -0,0 +1,8 @@
1
+ import { type PriceSource } from "@db/api";
2
+ import type PriceFetcher from "./priceFetcher";
3
+ import type { ResponsePriceType } from "./priceFetcher";
4
+ export default class OnChainCallService implements PriceFetcher {
5
+ static readonly instance: PriceFetcher;
6
+ private constructor();
7
+ getPrice(tokens: PriceSource[]): Promise<ResponsePriceType[]>;
8
+ }
@@ -0,0 +1,38 @@
1
+ import { PriceService } from "@/modules/v4/price/price.service";
2
+ import { PriceSourceMethod } from "@db/api";
3
+ import { BN2Number, ChainInteractionService } from "@sdk";
4
+ import { Contract } from "ethers";
5
+ import { log } from "../../logger";
6
+ export default class OnChainCallService {
7
+ static instance = new OnChainCallService();
8
+ constructor() { }
9
+ async getPrice(tokens) {
10
+ const pricePromises = tokens
11
+ .filter(tokenPriceSource => tokenPriceSource.method === PriceSourceMethod.ONCHAIN_CALL)
12
+ .map(async (token) => {
13
+ const args = token.args;
14
+ if (!args?.chainId || !args.address || !args.abi || !args.call) {
15
+ log.warn(`❌ ONCHAIN_CALL price source incorrectly implemented for ${token.symbol}`);
16
+ return undefined;
17
+ }
18
+ try {
19
+ const onChainCall = await new Contract(args.address, args.abi, ChainInteractionService(args.chainId).provider())[args.call]();
20
+ const multiplicator = BN2Number(onChainCall, args.decimals ?? 18);
21
+ const base = await PriceService.fetchPriceBySymbol(args.base);
22
+ const price = base * multiplicator;
23
+ // 2 returned tokens as stUSD and STUSD (business requirement)
24
+ const res = [
25
+ { token: token.symbol, rate: price },
26
+ { token: token.symbol.toUpperCase(), rate: price },
27
+ ];
28
+ return res;
29
+ }
30
+ catch (error) {
31
+ log.warn(`❌ ONCHAIN_CALL price source failed for ${token.symbol} with error: ${error}`);
32
+ return undefined;
33
+ }
34
+ });
35
+ const resolvedPrices = (await Promise.all(pricePromises)).filter(result => !!result);
36
+ return resolvedPrices.flat();
37
+ }
38
+ }