From e2707750523a11581a5ec9ce68ba5847a66cc8d9 Mon Sep 17 00:00:00 2001 From: Mantas Date: Tue, 9 Jul 2024 15:36:06 +0300 Subject: [PATCH 1/2] add custom providers for tracking --- packages/api/src/index.ts | 17 +++++++++++++ packages/api/src/providers.ts | 46 +++++++++++++++++++++++++++++++++++ 2 files changed, 63 insertions(+) create mode 100644 packages/api/src/providers.ts diff --git a/packages/api/src/index.ts b/packages/api/src/index.ts index cd59e7f1..91100934 100644 --- a/packages/api/src/index.ts +++ b/packages/api/src/index.ts @@ -9,6 +9,7 @@ import * as winston from "winston"; import { RPCConfig } from "utils/dist/wsTypes"; import RPCManager from "./rpcManager"; import fs from "fs"; +import { JsonRpcEthCalls, ProvidersEthCallsStartTime, WssEthCalls } from "./providers"; const defaultLogger = () => { return winston.createLogger({ @@ -112,6 +113,22 @@ async function start() { } else { waitTime = 60_000; } + + // Print out eth calls statistics + const currentTime = new Date(); + console.log("statistics of eth_ calls", { + JsonRpcEthCalls: JsonRpcEthCalls, + WssEthCalls: WssEthCalls, + CurrentTime: currentTime.toISOString(), + StartTime: ProvidersEthCallsStartTime.toISOString(), + RunningFor: + (currentTime.getTime() - ProvidersEthCallsStartTime.getTime()) / + 1000 / + 60 + + " minutes", + NumJsonRpcProviders, + NumWssProviders, + }); } } start(); diff --git a/packages/api/src/providers.ts b/packages/api/src/providers.ts new file mode 100644 index 00000000..98067a90 --- /dev/null +++ b/packages/api/src/providers.ts @@ -0,0 +1,46 @@ +import { Networkish } from "@ethersproject/providers"; +import { WebSocketLike } from "@ethersproject/providers/lib/websocket-provider"; +import { providers } from "ethers"; +import { ConnectionInfo } from "ethers/lib/utils"; + +export const ProvidersEthCallsStartTime = new Date(); + +/** + * List of eth_ * method calls and their counts for all TrackedJsonRpcProvider + */ +export const JsonRpcEthCalls = new Map(); + +/** + * List of eth_ * method calls and their counts for all TrackedWebsocketsProvider + */ +export const WssEthCalls = new Map(); + +export class TrackedWebsocketsProvider extends providers.WebSocketProvider { + constructor(url: string | WebSocketLike, network?: Networkish) { + super(url, network); + } + + send(method: string, params?: Array): Promise { + if (!WssEthCalls.has(method)) { + WssEthCalls.set(method, 0); + } + WssEthCalls.set(method, WssEthCalls.get(method)! + 1); + + return super.send(method, params); + } +} + +export class TrackedJsonRpcProvider extends providers.StaticJsonRpcProvider { + constructor(url?: ConnectionInfo | string, network?: Networkish) { + super(url, network); + } + + send(method: string, params: Array): Promise { + if (!JsonRpcEthCalls.has(method)) { + JsonRpcEthCalls.set(method, 0); + } + JsonRpcEthCalls.set(method, JsonRpcEthCalls.get(method)! + 1); + + return super.send(method, params); + } +} From 8b9d26c1f8f01c81cda135597c25340b309682eb Mon Sep 17 00:00:00 2001 From: Mantas Date: Tue, 9 Jul 2024 16:10:03 +0300 Subject: [PATCH 2/2] add eth_calls tracking and logging --- packages/api/src/eventListener.ts | 5 +++-- packages/api/src/index.ts | 8 +++++++- packages/api/src/providers.ts | 5 +++++ packages/api/src/rpcManager.ts | 3 ++- packages/api/src/sdkInterface.ts | 5 ++++- 5 files changed, 21 insertions(+), 5 deletions(-) diff --git a/packages/api/src/eventListener.ts b/packages/api/src/eventListener.ts index 6589be2c..21b213f9 100644 --- a/packages/api/src/eventListener.ts +++ b/packages/api/src/eventListener.ts @@ -39,6 +39,7 @@ import { } from "utils/src/wsTypes"; import SturdyWebSocket from "sturdy-websocket"; import { Logger } from "winston"; +import { TrackedWebsocketsProvider } from "./providers"; /** * Class that listens to blockchain events on @@ -197,7 +198,7 @@ export default class EventListener extends IndexPriceInterface { // Attempt to establish a ws connection to new RPC this.logger.info("creating new websocket rpc provider"); - this.currentWSRpcProvider = new providers.WebSocketProvider(this.wsConn!); + this.currentWSRpcProvider = new TrackedWebsocketsProvider(this.wsConn!); // On provider error - retry after short cooldown this.currentWSRpcProvider.on("error", (error: Error) => () => { @@ -628,7 +629,7 @@ export default class EventListener extends IndexPriceInterface { * @param symbol order book symbol */ private addOrderBookEventHandlers(symbol: string) { - const provider = new providers.WebSocketProvider(this.wsRPC); + const provider = this.currentWSRpcProvider!; this.orderBookContracts[symbol] = new Contract( this.traderInterface.getOrderBookAddress(symbol), this.traderInterface.getABI("lob")!, diff --git a/packages/api/src/index.ts b/packages/api/src/index.ts index 91100934..125d5850 100644 --- a/packages/api/src/index.ts +++ b/packages/api/src/index.ts @@ -9,7 +9,13 @@ import * as winston from "winston"; import { RPCConfig } from "utils/dist/wsTypes"; import RPCManager from "./rpcManager"; import fs from "fs"; -import { JsonRpcEthCalls, ProvidersEthCallsStartTime, WssEthCalls } from "./providers"; +import { + JsonRpcEthCalls, + NumJsonRpcProviders, + NumWssProviders, + ProvidersEthCallsStartTime, + WssEthCalls, +} from "./providers"; const defaultLogger = () => { return winston.createLogger({ diff --git a/packages/api/src/providers.ts b/packages/api/src/providers.ts index 98067a90..517319b8 100644 --- a/packages/api/src/providers.ts +++ b/packages/api/src/providers.ts @@ -15,9 +15,13 @@ export const JsonRpcEthCalls = new Map(); */ export const WssEthCalls = new Map(); +export let NumJsonRpcProviders = 0; +export let NumWssProviders = 0; + export class TrackedWebsocketsProvider extends providers.WebSocketProvider { constructor(url: string | WebSocketLike, network?: Networkish) { super(url, network); + NumWssProviders++; } send(method: string, params?: Array): Promise { @@ -33,6 +37,7 @@ export class TrackedWebsocketsProvider extends providers.WebSocketProvider { export class TrackedJsonRpcProvider extends providers.StaticJsonRpcProvider { constructor(url?: ConnectionInfo | string, network?: Networkish) { super(url, network); + NumJsonRpcProviders++; } send(method: string, params: Array): Promise { diff --git a/packages/api/src/rpcManager.ts b/packages/api/src/rpcManager.ts index 219ac916..69b18ccb 100644 --- a/packages/api/src/rpcManager.ts +++ b/packages/api/src/rpcManager.ts @@ -1,5 +1,6 @@ import { JsonRpcProvider } from "@ethersproject/providers"; import { executeWithTimeout } from "utils"; +import { TrackedJsonRpcProvider } from "./providers"; export default class RPCManager { private healthy: Map = new Map(); @@ -54,7 +55,7 @@ export default class RPCManager { this.healthy.get(rpc) === undefined || (this.lastCheck.get(rpc) ?? 0) + this.CHECK_INTERVAL_MS < Date.now() ) { - const provider = new JsonRpcProvider(rpc); + const provider = new TrackedJsonRpcProvider(rpc); try { await executeWithTimeout(provider.detectNetwork(), this.NETWORK_READY_MS); this.healthy.set(rpc, true); diff --git a/packages/api/src/sdkInterface.ts b/packages/api/src/sdkInterface.ts index f23bb803..5a2b0995 100644 --- a/packages/api/src/sdkInterface.ts +++ b/packages/api/src/sdkInterface.ts @@ -19,6 +19,7 @@ import Observable from "./observable"; import type { RedisClientType } from "redis"; import { extractErrorMsg, constructRedis } from "utils"; import RPCManager from "./rpcManager"; +import { TrackedJsonRpcProvider } from "./providers"; export type OrderWithTraderAndId = Order & { orderId: string; trader: string }; @@ -48,7 +49,9 @@ export default class SDKInterface extends Observable { public async initialize(sdkConfig: NodeSDKConfig, rpcManager: RPCManager) { this.apiInterface = new TraderInterface(sdkConfig); this.rpcManager = rpcManager; - await this.apiInterface.createProxyInstance(); + await this.apiInterface.createProxyInstance( + new TrackedJsonRpcProvider(sdkConfig.nodeURL), + ); await this.broker.initialize(sdkConfig); const brokerAddress = await this.broker.getBrokerAddress(); if (!this.redisClient.isOpen) {