From 67a0003a5a1814e02d56bac9d2417ebb6eda6068 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Fri, 23 May 2025 16:34:33 +0300 Subject: [PATCH 01/19] adds custom config for traceTransaction endpoint Signed-off-by: Konstantina Blazhukova --- packages/relay/src/index.ts | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/packages/relay/src/index.ts b/packages/relay/src/index.ts index f08ef6ae55..c223df457b 100644 --- a/packages/relay/src/index.ts +++ b/packages/relay/src/index.ts @@ -10,9 +10,9 @@ import { IContractCallRequest, IGetLogsParams, INewFilterParams, - ITracerConfig, ITransactionReceipt, RequestDetails, + TransactionTracerConfig, } from './lib/types'; export { JsonRpcError, predefined, MirrorNodeClientError, WebSocketError }; @@ -22,8 +22,7 @@ export { Relay } from './lib/relay'; export interface Debug { traceTransaction: ( transactionIdOrHash: string, - tracer: TracerType, - tracerConfig: ITracerConfig, + tracerObject: TransactionTracerConfig, requestDetails: RequestDetails, ) => Promise; From c05924f179c0c3ecee2d25d644e8f8d795049dea Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Fri, 23 May 2025 16:36:13 +0300 Subject: [PATCH 02/19] improves validation for debug traceTransaction Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 27 +++++++++++++++++++-------- packages/relay/src/lib/types/debug.ts | 9 ++++++++- packages/relay/src/utils.ts | 25 ------------------------- 3 files changed, 27 insertions(+), 34 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 217305d335..869b1346ce 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -24,6 +24,7 @@ import { ParamType, RequestDetails, TraceBlockByNumberTxResult, + TransactionTracerConfig, } from './types'; /** @@ -106,14 +107,16 @@ export class DebugImpl implements Debug { @rpcMethod @rpcParamValidationRules({ 0: { type: ParamType.TRANSACTION_HASH_OR_ID, required: true }, - 1: { type: ParamType.COMBINED_TRACER_TYPE, required: false }, - 2: { type: ParamType.TRACER_CONFIG, required: false }, + 1: { type: ParamType.TRACER_CONFIG_WRAPPER, required: true }, }) +<<<<<<< HEAD @cache(CacheService.getInstance(CACHE_LEVEL.L1)) +======= + @rpcParamLayoutConfig(RPC_LAYOUT.custom((params) => [params[0], params[1]])) +>>>>>>> e4ea585c (improves validation for debug traceTransaction) async traceTransaction( transactionIdOrHash: string, - tracer: TracerType, - tracerConfig: ITracerConfig, + tracerObject: TransactionTracerConfig, requestDetails: RequestDetails, ): Promise { if (this.logger.isLevelEnabled('trace')) { @@ -121,10 +124,18 @@ export class DebugImpl implements Debug { } try { DebugImpl.requireDebugAPIEnabled(); - if (tracer === TracerType.CallTracer) { - return await this.callTracer(transactionIdOrHash, tracerConfig as ICallTracerConfig, requestDetails); - } else if (tracer === TracerType.OpcodeLogger) { - return await this.callOpcodeLogger(transactionIdOrHash, tracerConfig as IOpcodeLoggerConfig, requestDetails); + if (tracerObject.tracer === TracerType.CallTracer) { + return await this.callTracer( + transactionIdOrHash, + tracerObject.tracerConfig as ICallTracerConfig, + requestDetails, + ); + } else if (tracerObject.tracer === TracerType.OpcodeLogger) { + return await this.callOpcodeLogger( + transactionIdOrHash, + tracerObject.tracerConfig as IOpcodeLoggerConfig, + requestDetails, + ); } } catch (e) { throw this.common.genericErrorHandler(e); diff --git a/packages/relay/src/lib/types/debug.ts b/packages/relay/src/lib/types/debug.ts index b4c69733ff..608b5c77dd 100644 --- a/packages/relay/src/lib/types/debug.ts +++ b/packages/relay/src/lib/types/debug.ts @@ -1,7 +1,7 @@ // SPDX-License-Identifier: Apache-2.0 import { TracerType } from '../constants'; -import { ICallTracerConfig } from './ITracerConfig'; +import { ICallTracerConfig, IOpcodeLoggerConfig } from './ITracerConfig'; /** * Configuration object for block tracing operations. @@ -13,6 +13,13 @@ export interface BlockTracerConfig { tracerConfig?: ICallTracerConfig; } +export interface TransactionTracerConfig { + /** The type of tracer to use for block tracing. */ + tracer: TracerType; + /** Optional configuration for the call tracer. */ + tracerConfig?: ICallTracerConfig | IOpcodeLoggerConfig; +} + /** * Represents the state of an entity during a trace operation. */ diff --git a/packages/relay/src/utils.ts b/packages/relay/src/utils.ts index cfe211f9e0..12bd3df28f 100644 --- a/packages/relay/src/utils.ts +++ b/packages/relay/src/utils.ts @@ -174,31 +174,6 @@ export class Utils { public static arrangeRpcParams(method: Function, rpcParams: any[] = [], requestDetails: RequestDetails): any[] { const layout = method[RPC_PARAM_LAYOUT_KEY]; - if (method.name === 'traceTransaction') { - const transactionIdOrHash = rpcParams[0]; - let tracer: TracerType = TracerType.OpcodeLogger; - let tracerConfig: ITracerConfig = {}; - - // Second param can be either a TracerType string, or an object for TracerConfig or TracerConfigWrapper - if (TYPES.tracerType.test(rpcParams[1])) { - tracer = rpcParams[1]; - if (TYPES.tracerConfig.test(rpcParams[2])) { - tracerConfig = rpcParams[2]; - } - } else if (TYPES.tracerConfig.test(rpcParams[1])) { - tracerConfig = rpcParams[1]; - } else if (TYPES.tracerConfigWrapper.test(rpcParams[1])) { - if (TYPES.tracerType.test(rpcParams[1].tracer)) { - tracer = rpcParams[1].tracer; - } - if (TYPES.tracerConfig.test(rpcParams[1].tracerConfig)) { - tracerConfig = rpcParams[1].tracerConfig; - } - } - - return [transactionIdOrHash, tracer, tracerConfig, requestDetails]; - } - // Method only needs requestDetails if (layout === RPC_LAYOUT.REQUEST_DETAILS_ONLY) { return [requestDetails]; From 0c0376c4b73c6bd151b9bb9aeb892538638cec23 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Fri, 23 May 2025 16:36:54 +0300 Subject: [PATCH 03/19] removes unused variables Signed-off-by: Konstantina Blazhukova --- packages/relay/src/index.ts | 2 -- packages/relay/src/utils.ts | 5 ++--- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/packages/relay/src/index.ts b/packages/relay/src/index.ts index c223df457b..a13d24165e 100644 --- a/packages/relay/src/index.ts +++ b/packages/relay/src/index.ts @@ -1,6 +1,4 @@ // SPDX-License-Identifier: Apache-2.0 - -import { TracerType } from './lib/constants'; import { JsonRpcError, predefined } from './lib/errors/JsonRpcError'; import { MirrorNodeClientError } from './lib/errors/MirrorNodeClientError'; import WebSocketError from './lib/errors/WebSocketError'; diff --git a/packages/relay/src/utils.ts b/packages/relay/src/utils.ts index 12bd3df28f..ba091526e2 100644 --- a/packages/relay/src/utils.ts +++ b/packages/relay/src/utils.ts @@ -8,10 +8,9 @@ import createHash from 'keccak'; import { Logger } from 'pino'; import { hexToASCII, prepend0x, strip0x } from './formatters'; -import constants, { TracerType } from './lib/constants'; +import constants from './lib/constants'; import { RPC_LAYOUT, RPC_PARAM_LAYOUT_KEY } from './lib/decorators'; -import { ITracerConfig, RequestDetails } from './lib/types'; -import { TYPES } from './lib/validators'; +import { RequestDetails } from './lib/types'; export class Utils { public static readonly IP_ADDRESS_REGEX = /\b((25[0-5]|(2[0-4]|1\d|[1-9]|)\d)(\.(?!$)|$)){4}\b/g; From acc27948a7410f26aaef85c4d574c18f0ff55ab3 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Wed, 4 Jun 2025 14:37:33 +0300 Subject: [PATCH 04/19] covers edge cases for tracer config wrapper Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 29 ++++++++++--------- .../relay/src/lib/validators/objectTypes.ts | 22 +++++++++++++- 2 files changed, 37 insertions(+), 14 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 869b1346ce..80e6f95810 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -107,7 +107,7 @@ export class DebugImpl implements Debug { @rpcMethod @rpcParamValidationRules({ 0: { type: ParamType.TRANSACTION_HASH_OR_ID, required: true }, - 1: { type: ParamType.TRACER_CONFIG_WRAPPER, required: true }, + 1: { type: ParamType.TRACER_CONFIG_WRAPPER, required: false }, }) <<<<<<< HEAD @cache(CacheService.getInstance(CACHE_LEVEL.L1)) @@ -122,21 +122,24 @@ export class DebugImpl implements Debug { if (this.logger.isLevelEnabled('trace')) { this.logger.trace(`${requestDetails.formattedRequestId} traceTransaction(${transactionIdOrHash})`); } + + // we currently do not support prestate tracer + if (tracerObject?.tracer === TracerType.PrestateTracer) { + throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); + } + + //we use a wrapper since we accept a transaction where a second param with tracer/tracerConfig may not be provided + //and we will still default to opcodeLogger + const wrapper = tracerObject ?? {}; + const tracer = wrapper.tracer ?? TracerType.OpcodeLogger; + const tracerConfig = wrapper.tracerConfig ?? {}; + try { DebugImpl.requireDebugAPIEnabled(); - if (tracerObject.tracer === TracerType.CallTracer) { - return await this.callTracer( - transactionIdOrHash, - tracerObject.tracerConfig as ICallTracerConfig, - requestDetails, - ); - } else if (tracerObject.tracer === TracerType.OpcodeLogger) { - return await this.callOpcodeLogger( - transactionIdOrHash, - tracerObject.tracerConfig as IOpcodeLoggerConfig, - requestDetails, - ); + if (tracer === TracerType.CallTracer) { + return await this.callTracer(transactionIdOrHash, tracerConfig as ICallTracerConfig, requestDetails); } + return await this.callOpcodeLogger(transactionIdOrHash, tracerConfig as IOpcodeLoggerConfig, requestDetails); } catch (e) { throw this.common.genericErrorHandler(e); } diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index 6fab78c66a..96c640efa8 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -1,6 +1,6 @@ // SPDX-License-Identifier: Apache-2.0 -import { Validator } from '.'; +import { TracerType } from '../constants'; import { predefined } from '../errors/JsonRpcError'; import { ICallTracerConfig, @@ -9,6 +9,7 @@ import { IOpcodeLoggerConfig, ITracerConfigWrapper, } from '../types'; +import { Validator } from '.'; export const OBJECTS_VALIDATIONS: { [key: string]: IObjectSchema } = { blockHashObject: { @@ -305,4 +306,23 @@ export class TracerConfigWrapper extends DefaultValidation constructor(config: any) { super(OBJECTS_VALIDATIONS.tracerConfigWrapper, config); } + + validate() { + const valid = super.validate(); + + const { tracer, tracerConfig } = this.object; + + if ( + tracerConfig && + (tracerConfig as ICallTracerConfig).onlyTopCall !== undefined && + tracer !== TracerType.CallTracer + ) { + throw predefined.INVALID_PARAMETER( + 1, + `'tracerConfig' for ${this.name()} onlyTopCall is only valid when tracer=${TracerType.CallTracer}`, + ); + } + + return valid; + } } From 2baa95e0d3a4a0198fe04cf28ec9d7f1e617de25 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Wed, 4 Jun 2025 16:52:58 +0300 Subject: [PATCH 05/19] fixes unit tests Signed-off-by: Konstantina Blazhukova --- packages/relay/tests/lib/debug.spec.ts | 40 +++++++++----------------- packages/relay/tests/lib/utils.spec.ts | 9 +++--- 2 files changed, 18 insertions(+), 31 deletions(-) diff --git a/packages/relay/tests/lib/debug.spec.ts b/packages/relay/tests/lib/debug.spec.ts index d2d8a68a78..9fefc682bd 100644 --- a/packages/relay/tests/lib/debug.spec.ts +++ b/packages/relay/tests/lib/debug.spec.ts @@ -360,12 +360,8 @@ describe('Debug API Test Suite', async function () { withOverriddenEnvsInMochaTest({ DEBUG_API_ENABLED: true }, () => { it('should successfully debug a transaction', async function () { - const traceTransaction = await debugService.traceTransaction( - transactionHash, - callTracer, - tracerConfigFalse, - requestDetails, - ); + const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; + const traceTransaction = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); expect(traceTransaction).to.exist; }); @@ -394,12 +390,8 @@ describe('Debug API Test Suite', async function () { ], }; - const result = await debugService.traceTransaction( - transactionHash, - callTracer, - tracerConfigFalse, - requestDetails, - ); + const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; + const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); expect(result).to.deep.equal(expectedResult); }); @@ -416,12 +408,9 @@ describe('Debug API Test Suite', async function () { output: '0x2', calls: undefined, }; - const result = await debugService.traceTransaction( - transactionHash, - callTracer, - tracerConfigTrue, - requestDetails, - ); + + const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigTrue }; + const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); expect(result).to.deep.equal(expectedResult); }); @@ -429,12 +418,8 @@ describe('Debug API Test Suite', async function () { it('Should return empty array if no actions found', async function () { restMock.onGet(CONTARCTS_RESULTS_ACTIONS).reply(200, JSON.stringify({ actions: [] })); - const result = await debugService.traceTransaction( - transactionHash, - callTracer, - tracerConfigFalse, - requestDetails, - ); + const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; + const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); expect(result).to.be.null; }); @@ -472,7 +457,8 @@ describe('Debug API Test Suite', async function () { })), }; - const result = await debugService.traceTransaction(transactionHash, opcodeLogger, config, requestDetails); + const tracerObject = { tracer: opcodeLogger, tracerConfig: config }; + const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); expect(result).to.deep.equal(expectedResult); }); @@ -506,10 +492,10 @@ describe('Debug API Test Suite', async function () { `Failed to retrieve contract results for transaction ${nonExistentTransactionHash}`, ); + const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigTrue }; await RelayAssertions.assertRejection(expectedError, debugService.traceTransaction, true, debugService, [ nonExistentTransactionHash, - callTracer, - tracerConfigTrue, + tracerObject, requestDetails, ]); }); diff --git a/packages/relay/tests/lib/utils.spec.ts b/packages/relay/tests/lib/utils.spec.ts index d3ea954e6c..c98d40df83 100644 --- a/packages/relay/tests/lib/utils.spec.ts +++ b/packages/relay/tests/lib/utils.spec.ts @@ -255,13 +255,12 @@ describe('Utils', () => { ['should handle traceTransaction with only transaction hash', [], TracerType.OpcodeLogger, {}], [ 'should handle traceTransaction with tracer type as second parameter', - [TracerType.CallTracer], + [{ tracer: TracerType.CallTracer }], TracerType.CallTracer, - {}, ], [ 'should handle traceTransaction with tracer type and config', - [TracerType.CallTracer, tracerConfig], + [{ tracer: TracerType.CallTracer, tracerConfig: tracerConfig }], TracerType.CallTracer, tracerConfig, ], @@ -312,7 +311,9 @@ describe('Utils', () => { [transactionHash, ...(params as any[])], requestDetails, ); - expect(result).to.deep.equal([transactionHash, expectedTracer, expectedConfig, requestDetails]); + const tracerObject = { tracer: expectedTracer, tracerConfig: expectedConfig }; + + expect(result).to.deep.equal([transactionHash, tracerObject, requestDetails]); }); }); }); From df829023b5cbfc085e15256fbe10fffecea658e8 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Wed, 4 Jun 2025 17:07:20 +0300 Subject: [PATCH 06/19] adds clarification for validate method Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/validators/objectTypes.ts | 2 ++ 1 file changed, 2 insertions(+) diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index 96c640efa8..f4e2f38c7b 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -312,6 +312,8 @@ export class TracerConfigWrapper extends DefaultValidation const { tracer, tracerConfig } = this.object; + // we want to accept ICallTracerConfig only if the tracer is callTracer + // this config is not valid for opcodeLogger if ( tracerConfig && (tracerConfig as ICallTracerConfig).onlyTopCall !== undefined && From 4760a0d38c463838fa04f60585ae8a3344042658 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Wed, 4 Jun 2025 17:40:02 +0300 Subject: [PATCH 07/19] removes redundant variable initialization Signed-off-by: Konstantina Blazhukova --- packages/relay/tests/lib/debug.spec.ts | 34 +++++++++++++++++--------- 1 file changed, 23 insertions(+), 11 deletions(-) diff --git a/packages/relay/tests/lib/debug.spec.ts b/packages/relay/tests/lib/debug.spec.ts index 9fefc682bd..b4513807cc 100644 --- a/packages/relay/tests/lib/debug.spec.ts +++ b/packages/relay/tests/lib/debug.spec.ts @@ -50,6 +50,8 @@ describe('Debug API Test Suite', async function () { const tracerConfigFalse = { onlyTopCall: false }; const callTracer: TracerType = TracerType.CallTracer; const opcodeLogger: TracerType = TracerType.OpcodeLogger; + const tracerObjectCallTracerFalse = { tracer: callTracer, tracerConfig: tracerConfigFalse }; + const tracerObjectCallTracerTrue = { tracer: callTracer, tracerConfig: tracerConfigTrue }; const CONTRACTS_RESULTS_OPCODES = `contracts/results/${transactionHash}/opcodes`; const CONTARCTS_RESULTS_ACTIONS = `contracts/results/${transactionHash}/actions`; const CONTRACTS_RESULTS_BY_HASH = `contracts/results/${transactionHash}`; @@ -360,8 +362,11 @@ describe('Debug API Test Suite', async function () { withOverriddenEnvsInMochaTest({ DEBUG_API_ENABLED: true }, () => { it('should successfully debug a transaction', async function () { - const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; - const traceTransaction = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); + const traceTransaction = await debugService.traceTransaction( + transactionHash, + tracerObjectCallTracerFalse, + requestDetails, + ); expect(traceTransaction).to.exist; }); @@ -390,8 +395,11 @@ describe('Debug API Test Suite', async function () { ], }; - const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; - const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); + const result = await debugService.traceTransaction( + transactionHash, + tracerObjectCallTracerFalse, + requestDetails, + ); expect(result).to.deep.equal(expectedResult); }); @@ -408,9 +416,11 @@ describe('Debug API Test Suite', async function () { output: '0x2', calls: undefined, }; - - const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigTrue }; - const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); + const result = await debugService.traceTransaction( + transactionHash, + tracerObjectCallTracerTrue, + requestDetails, + ); expect(result).to.deep.equal(expectedResult); }); @@ -418,8 +428,11 @@ describe('Debug API Test Suite', async function () { it('Should return empty array if no actions found', async function () { restMock.onGet(CONTARCTS_RESULTS_ACTIONS).reply(200, JSON.stringify({ actions: [] })); - const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigFalse }; - const result = await debugService.traceTransaction(transactionHash, tracerObject, requestDetails); + const result = await debugService.traceTransaction( + transactionHash, + tracerObjectCallTracerFalse, + requestDetails, + ); expect(result).to.be.null; }); @@ -492,10 +505,9 @@ describe('Debug API Test Suite', async function () { `Failed to retrieve contract results for transaction ${nonExistentTransactionHash}`, ); - const tracerObject = { tracer: callTracer, tracerConfig: tracerConfigTrue }; await RelayAssertions.assertRejection(expectedError, debugService.traceTransaction, true, debugService, [ nonExistentTransactionHash, - tracerObject, + tracerObjectCallTracerTrue, requestDetails, ]); }); From e7859f99a54c6c93597e64d3c703a72992aa07f2 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 9 Jun 2025 11:02:33 +0300 Subject: [PATCH 08/19] simplifies code in traceTransaction Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 80e6f95810..cf18fa680d 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -130,9 +130,8 @@ export class DebugImpl implements Debug { //we use a wrapper since we accept a transaction where a second param with tracer/tracerConfig may not be provided //and we will still default to opcodeLogger - const wrapper = tracerObject ?? {}; - const tracer = wrapper.tracer ?? TracerType.OpcodeLogger; - const tracerConfig = wrapper.tracerConfig ?? {}; + const tracer = tracerObject?.tracer ?? TracerType.OpcodeLogger; + const tracerConfig = tracerObject?.tracerConfig ?? {}; try { DebugImpl.requireDebugAPIEnabled(); From c61a686597dcf7947450026acfc772fbc07a4c6f Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 9 Jun 2025 11:03:03 +0300 Subject: [PATCH 09/19] removes unused variable Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index cf18fa680d..e9635e5b81 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -19,7 +19,6 @@ import { EntityTraceStateMap, ICallTracerConfig, IOpcodeLoggerConfig, - ITracerConfig, MirrorNodeContractResult, ParamType, RequestDetails, From 33b6d419099a05c8dad37f67fbcb46309f72aa78 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 9 Jun 2025 14:35:13 +0300 Subject: [PATCH 10/19] improves validation Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 5 --- .../relay/src/lib/validators/objectTypes.ts | 33 +++++++++++++++---- 2 files changed, 26 insertions(+), 12 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index e9635e5b81..6c1101d893 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -122,11 +122,6 @@ export class DebugImpl implements Debug { this.logger.trace(`${requestDetails.formattedRequestId} traceTransaction(${transactionIdOrHash})`); } - // we currently do not support prestate tracer - if (tracerObject?.tracer === TracerType.PrestateTracer) { - throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); - } - //we use a wrapper since we accept a transaction where a second param with tracer/tracerConfig may not be provided //and we will still default to opcodeLogger const tracer = tracerObject?.tracer ?? TracerType.OpcodeLogger; diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index f4e2f38c7b..592aa8afda 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -312,19 +312,38 @@ export class TracerConfigWrapper extends DefaultValidation const { tracer, tracerConfig } = this.object; + // currently we don't support prestate tracer for traceTransaction + if (tracer === TracerType.PrestateTracer) { + throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); + } + + if (!tracerConfig) { + return valid; + } + + const keys = Object.keys(tracerConfig ?? {}); + + const callTracerKeys = ['onlyTopCall']; + const opcodeLoggerKeys = ['enableMemory', 'disableStack', 'disableStorage']; + + const hasCallTracerKeys = keys.some((k) => callTracerKeys.includes(k)); // we want to accept ICallTracerConfig only if the tracer is callTracer - // this config is not valid for opcodeLogger - if ( - tracerConfig && - (tracerConfig as ICallTracerConfig).onlyTopCall !== undefined && - tracer !== TracerType.CallTracer - ) { + // this config is not valid for opcodeLogger and vice versa + // accept only IOpcodeLoggerConfig with opcodeLogger tracer + if (hasCallTracerKeys && tracer !== TracerType.CallTracer) { throw predefined.INVALID_PARAMETER( 1, - `'tracerConfig' for ${this.name()} onlyTopCall is only valid when tracer=${TracerType.CallTracer}`, + `callTracer 'tracerConfig' for ${this.name()} is only valid when tracer=${TracerType.CallTracer}`, ); } + const hasOpcodeLoggerKeys = keys.some((k) => opcodeLoggerKeys.includes(k)); + if (hasOpcodeLoggerKeys && tracer !== TracerType.OpcodeLogger) { + throw predefined.INVALID_PARAMETER( + 1, + `opcodeLogger 'tracerConfig' for ${this.name()} is only valid when tracer=${TracerType.OpcodeLogger}`, + ); + } return valid; } } From 7425fb7867e3ac46cf41186afc5229db4fc6ff56 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 9 Jun 2025 15:40:45 +0300 Subject: [PATCH 11/19] improves utils tests for traceTransaction Signed-off-by: Konstantina Blazhukova --- packages/relay/tests/lib/utils.spec.ts | 82 ++++++++------------------ 1 file changed, 24 insertions(+), 58 deletions(-) diff --git a/packages/relay/tests/lib/utils.spec.ts b/packages/relay/tests/lib/utils.spec.ts index c98d40df83..02401cd0ae 100644 --- a/packages/relay/tests/lib/utils.spec.ts +++ b/packages/relay/tests/lib/utils.spec.ts @@ -252,68 +252,34 @@ describe('Utils', () => { // Define test cases as [testName, params, expectedTracer, expectedConfig] const testCases = [ - ['should handle traceTransaction with only transaction hash', [], TracerType.OpcodeLogger, {}], - [ - 'should handle traceTransaction with tracer type as second parameter', - [{ tracer: TracerType.CallTracer }], - TracerType.CallTracer, - ], - [ - 'should handle traceTransaction with tracer type and config', - [{ tracer: TracerType.CallTracer, tracerConfig: tracerConfig }], - TracerType.CallTracer, - tracerConfig, - ], - [ - 'should handle traceTransaction with tracerConfig as second parameter', - [tracerConfig], - TracerType.OpcodeLogger, - tracerConfig, - ], - [ - 'should handle traceTransaction with tracerConfigWrapper as second parameter', - [ - { - tracer: TracerType.CallTracer, - tracerConfig: tracerConfig, - }, - ], - TracerType.CallTracer, - tracerConfig, - ], - [ - 'should handle traceTransaction with partial tracerConfigWrapper (only tracer)', - [ - { - tracer: TracerType.CallTracer, - }, - ], - TracerType.CallTracer, - {}, - ], - [ - 'should handle traceTransaction with partial tracerConfigWrapper (only tracerConfig)', - [ - { - tracerConfig, - }, - ], - TracerType.OpcodeLogger, - tracerConfig, - ], + { + name: 'should handle traceTransaction with only transaction hash', + params: [], + expected: [transactionHash, requestDetails], + }, + { + name: 'should handle traceTransaction with tracerConfigWrapper as second parameter', + params: [{ tracer: TracerType.CallTracer, tracerConfig: tracerConfig }], + expected: [transactionHash, { tracer: TracerType.CallTracer, tracerConfig: tracerConfig }, requestDetails], + }, + { + name: 'should handle traceTransaction with partial tracerConfigWrapper (only tracer)', + params: [{ tracer: TracerType.CallTracer }], + expected: [transactionHash, { tracer: TracerType.CallTracer }, requestDetails], + }, + { + name: 'should handle traceTransaction with empty tracerConfig', + params: [{ tracer: TracerType.CallTracer, tracerConfig: {} }], + expected: [transactionHash, { tracer: TracerType.CallTracer, tracerConfig: {} }, requestDetails], + }, ]; // Loop through test cases and create tests - testCases.forEach(([testName, params, expectedTracer, expectedConfig]) => { - it(testName as string, () => { - const result = Utils.arrangeRpcParams( - traceTransactionMethod, - [transactionHash, ...(params as any[])], - requestDetails, - ); - const tracerObject = { tracer: expectedTracer, tracerConfig: expectedConfig }; + testCases.forEach(({ name, params, expected }) => { + it(name, () => { + const result = Utils.arrangeRpcParams(traceTransactionMethod, [transactionHash, ...params], requestDetails); - expect(result).to.deep.equal([transactionHash, tracerObject, requestDetails]); + expect(result).to.deep.equal(expected); }); }); }); From 285645f7e72ded02b466b38ec9f0306d5ce24c09 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Fri, 13 Jun 2025 16:25:19 +0300 Subject: [PATCH 12/19] improves types Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/types/debug.ts | 19 ++++++++----------- 1 file changed, 8 insertions(+), 11 deletions(-) diff --git a/packages/relay/src/lib/types/debug.ts b/packages/relay/src/lib/types/debug.ts index 608b5c77dd..ff3bbe7235 100644 --- a/packages/relay/src/lib/types/debug.ts +++ b/packages/relay/src/lib/types/debug.ts @@ -1,24 +1,21 @@ // SPDX-License-Identifier: Apache-2.0 import { TracerType } from '../constants'; -import { ICallTracerConfig, IOpcodeLoggerConfig } from './ITracerConfig'; +import { ICallTracerConfig, ITracerConfig } from './ITracerConfig'; /** * Configuration object for block tracing operations. */ -export interface BlockTracerConfig { - /** The type of tracer to use for block tracing. */ +interface TracerConfig { + /** The type of tracer to use for tracing. */ tracer: TracerType; - /** Optional configuration for the call tracer. */ - tracerConfig?: ICallTracerConfig; + /** Optional configuration for the tracer. */ + tracerConfig?: T; } -export interface TransactionTracerConfig { - /** The type of tracer to use for block tracing. */ - tracer: TracerType; - /** Optional configuration for the call tracer. */ - tracerConfig?: ICallTracerConfig | IOpcodeLoggerConfig; -} +// Public exports +export type BlockTracerConfig = TracerConfig; +export type TransactionTracerConfig = TracerConfig; /** * Represents the state of an entity during a trace operation. From 9af9904e5f7c8c1620e1023fd799ea71f095ce73 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Fri, 13 Jun 2025 16:48:15 +0300 Subject: [PATCH 13/19] removes conflict marker and improve traceTransaction Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 3 --- packages/relay/src/lib/validators/objectTypes.ts | 10 +++++----- 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 6c1101d893..1a5a66ae87 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -108,11 +108,8 @@ export class DebugImpl implements Debug { 0: { type: ParamType.TRANSACTION_HASH_OR_ID, required: true }, 1: { type: ParamType.TRACER_CONFIG_WRAPPER, required: false }, }) -<<<<<<< HEAD @cache(CacheService.getInstance(CACHE_LEVEL.L1)) -======= @rpcParamLayoutConfig(RPC_LAYOUT.custom((params) => [params[0], params[1]])) ->>>>>>> e4ea585c (improves validation for debug traceTransaction) async traceTransaction( transactionIdOrHash: string, tracerObject: TransactionTracerConfig, diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index 592aa8afda..542bb94a00 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -321,12 +321,13 @@ export class TracerConfigWrapper extends DefaultValidation return valid; } - const keys = Object.keys(tracerConfig ?? {}); + const callTracerKeys = Object.keys(OBJECTS_VALIDATIONS.callTracerConfig.properties); + const opcodeLoggerKeys = Object.keys(OBJECTS_VALIDATIONS.opcodeLoggerConfig.properties); - const callTracerKeys = ['onlyTopCall']; - const opcodeLoggerKeys = ['enableMemory', 'disableStack', 'disableStorage']; + const configKeys = Object.keys(tracerConfig); + const hasCallTracerKeys = configKeys.some((k) => callTracerKeys.includes(k)); + const hasOpcodeLoggerKeys = configKeys.some((k) => opcodeLoggerKeys.includes(k)); - const hasCallTracerKeys = keys.some((k) => callTracerKeys.includes(k)); // we want to accept ICallTracerConfig only if the tracer is callTracer // this config is not valid for opcodeLogger and vice versa // accept only IOpcodeLoggerConfig with opcodeLogger tracer @@ -337,7 +338,6 @@ export class TracerConfigWrapper extends DefaultValidation ); } - const hasOpcodeLoggerKeys = keys.some((k) => opcodeLoggerKeys.includes(k)); if (hasOpcodeLoggerKeys && tracer !== TracerType.OpcodeLogger) { throw predefined.INVALID_PARAMETER( 1, From a962ce7ad3b1cecb20096ff400bc0ecacbfb6a09 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 16 Jun 2025 14:22:44 +0300 Subject: [PATCH 14/19] moves prestate tracer check Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/validators/objectTypes.ts | 5 ----- 1 file changed, 5 deletions(-) diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index 542bb94a00..761f2e84aa 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -312,11 +312,6 @@ export class TracerConfigWrapper extends DefaultValidation const { tracer, tracerConfig } = this.object; - // currently we don't support prestate tracer for traceTransaction - if (tracer === TracerType.PrestateTracer) { - throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); - } - if (!tracerConfig) { return valid; } From cb71bc7925833dedfc21ac153908ec2ea9f8c415 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 16 Jun 2025 14:23:21 +0300 Subject: [PATCH 15/19] fixes tests Signed-off-by: Konstantina Blazhukova --- .../server/tests/integration/server.spec.ts | 70 ++++++------------- 1 file changed, 22 insertions(+), 48 deletions(-) diff --git a/packages/server/tests/integration/server.spec.ts b/packages/server/tests/integration/server.spec.ts index 0c3d38d346..42d7513935 100644 --- a/packages/server/tests/integration/server.spec.ts +++ b/packages/server/tests/integration/server.spec.ts @@ -2464,7 +2464,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, TracerType.CallTracer, { onlyTopCall: true }], + params: [contractHash1, { tracer: TracerType.CallTracer, tracerConfig: { onlyTopCall: true } }], id: 1, }), ).to.not.throw; @@ -2477,8 +2477,10 @@ describe('RPC Server', function () { method: 'debug_traceTransaction', params: [ contractHash1, - TracerType.OpcodeLogger, - { disableStack: false, disableStorage: false, enableMemory: true }, + { + tracer: TracerType.OpcodeLogger, + tracerConfig: { disableStack: false, disableStorage: false, enableMemory: true }, + }, ], id: 1, }), @@ -2501,7 +2503,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, TracerType.CallTracer], + params: [contractHash1, { tracer: TracerType.CallTracer }], id: '2', }), ).to.not.throw; @@ -2512,7 +2514,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, TracerType.CallTracer, {}], + params: [contractHash1, { tracer: TracerType.CallTracer, tracerConfig: {} }], id: '2', }), ).to.not.throw; @@ -2529,39 +2531,6 @@ describe('RPC Server', function () { ).to.not.throw; }); - it('should execute with unknown property in TracerConfig', async () => { - expect( - await testClient.post('/', { - jsonrpc: '2.0', - method: 'debug_traceTransaction', - params: [contractHash1, { disableMemory: true, disableStack: true }], - id: '2', - }), - ).to.not.throw; - }); - - it('should execute with unknown property in TracerConfigWrapper.tracerConfig', async () => { - expect( - await testClient.post('/', { - jsonrpc: '2.0', - method: 'debug_traceTransaction', - params: [contractHash1, { tracerConfig: { disableMemory: true, disableStorage: true } }], - id: '2', - }), - ).to.not.throw; - }); - - it('should execute with empty TracerConfigWrapper.tracerConfig', async function () { - expect( - await testClient.post('/', { - jsonrpc: '2.0', - method: 'debug_traceTransaction', - params: [contractHash1, { tracerConfig: {} }], - id: '2', - }), - ).to.not.throw; - }); - it('should fail with missing transaction hash', async () => { try { await testClient.post('/', { @@ -2582,7 +2551,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: ['invalidHash', TracerType.OpcodeLogger], + params: ['invalidHash', { tracer: TracerType.OpcodeLogger }], id: '2', }); @@ -2610,7 +2579,7 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 1: The value passed is not valid: invalidTracerType. ${Validator.TYPES.tracerType.error} OR ${Validator.TYPES.tracerConfig.error} OR ${Validator.TYPES.tracerConfigWrapper.error}`, + `Invalid parameter 1: Expected TracerConfigWrapper which contains a valid TracerType and/or TracerConfig, value: invalidTracerType`, ); } }); @@ -2620,7 +2589,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, TracerType.CallTracer, { invalidConfig: true }], + params: [contractHash1, { tracer: TracerType.CallTracer, tracerConfig: { invalidConfig: true } }], id: '2', }); @@ -2629,7 +2598,7 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 2: ${Validator.TYPES.tracerConfig.error}, value: ${JSON.stringify({ + `Invalid parameter 'tracerConfig' for TracerConfigWrapper: Expected TracerConfig, value: ${JSON.stringify({ invalidConfig: true, })}`, ); @@ -2994,12 +2963,17 @@ describe('RPC Server', function () { }); it('should execute with valid block number and PrestateTracer', async () => { - const response = await testClient.post('/', { - jsonrpc: '2.0', - method: 'debug_traceBlockByNumber', - params: [blockNumberHex, { tracer: TracerType.PrestateTracer }], - id: '2', - }); + let response; + try { + response = await testClient.post('/', { + jsonrpc: '2.0', + method: 'debug_traceBlockByNumber', + params: [blockNumberHex, { tracer: TracerType.PrestateTracer }], + id: '2', + }); + } catch (error: any) { + console.log('Errrooor ----->', error.response.data); + } BaseTest.defaultResponseChecks(response); expect(response.data.result).to.be.an('array'); From 3d6ebc41e1050ee8272b1539e830f17e6f46620f Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 16 Jun 2025 14:23:54 +0300 Subject: [PATCH 16/19] removes unused variable Signed-off-by: Konstantina Blazhukova --- packages/server/tests/integration/server.spec.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/server/tests/integration/server.spec.ts b/packages/server/tests/integration/server.spec.ts index 42d7513935..877fbee8a3 100644 --- a/packages/server/tests/integration/server.spec.ts +++ b/packages/server/tests/integration/server.spec.ts @@ -11,7 +11,6 @@ import { DebugImpl } from '@hashgraph/json-rpc-relay/dist/lib/debug'; import { CacheService } from '@hashgraph/json-rpc-relay/dist/lib/services/cacheService/cacheService'; import { Validator } from '@hashgraph/json-rpc-relay/dist/lib/validators'; import * as Constants from '@hashgraph/json-rpc-relay/dist/lib/validators'; -import { JsonRpcError } from '@hashgraph/json-rpc-relay/src'; import { CommonService } from '@hashgraph/json-rpc-relay/src/lib/services'; import Axios, { AxiosInstance } from 'axios'; import { expect } from 'chai'; From bcaf7690ff71ab260feb73257ba9ee1be949909e Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 16 Jun 2025 16:14:08 +0300 Subject: [PATCH 17/19] fixes all integration tests Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 8 ++- .../relay/src/lib/validators/objectTypes.ts | 2 +- .../server/tests/integration/server.spec.ts | 50 ++++++++++++------- 3 files changed, 39 insertions(+), 21 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 1a5a66ae87..846340617c 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -108,13 +108,17 @@ export class DebugImpl implements Debug { 0: { type: ParamType.TRANSACTION_HASH_OR_ID, required: true }, 1: { type: ParamType.TRACER_CONFIG_WRAPPER, required: false }, }) - @cache(CacheService.getInstance(CACHE_LEVEL.L1)) @rpcParamLayoutConfig(RPC_LAYOUT.custom((params) => [params[0], params[1]])) + @cache(CacheService.getInstance(CACHE_LEVEL.L1)) async traceTransaction( transactionIdOrHash: string, tracerObject: TransactionTracerConfig, requestDetails: RequestDetails, ): Promise { + if (tracerObject?.tracer === TracerType.PrestateTracer) { + throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); + } + if (this.logger.isLevelEnabled('trace')) { this.logger.trace(`${requestDetails.formattedRequestId} traceTransaction(${transactionIdOrHash})`); } @@ -165,6 +169,8 @@ export class DebugImpl implements Debug { tracerObject: BlockTracerConfig, requestDetails: RequestDetails, ): Promise { + this.logger.info(`blockNumber: ${blockNumber}`); + this.logger.info(`tracerObject: ${JSON.stringify(tracerObject)}`); if (this.logger.isLevelEnabled('trace')) { this.logger.trace( `${ diff --git a/packages/relay/src/lib/validators/objectTypes.ts b/packages/relay/src/lib/validators/objectTypes.ts index 761f2e84aa..34ae1f06cd 100644 --- a/packages/relay/src/lib/validators/objectTypes.ts +++ b/packages/relay/src/lib/validators/objectTypes.ts @@ -326,7 +326,7 @@ export class TracerConfigWrapper extends DefaultValidation // we want to accept ICallTracerConfig only if the tracer is callTracer // this config is not valid for opcodeLogger and vice versa // accept only IOpcodeLoggerConfig with opcodeLogger tracer - if (hasCallTracerKeys && tracer !== TracerType.CallTracer) { + if (hasCallTracerKeys && tracer === TracerType.OpcodeLogger) { throw predefined.INVALID_PARAMETER( 1, `callTracer 'tracerConfig' for ${this.name()} is only valid when tracer=${TracerType.CallTracer}`, diff --git a/packages/server/tests/integration/server.spec.ts b/packages/server/tests/integration/server.spec.ts index 877fbee8a3..5111f74d08 100644 --- a/packages/server/tests/integration/server.spec.ts +++ b/packages/server/tests/integration/server.spec.ts @@ -2609,7 +2609,10 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, { enableMemory: 'must be a boolean' }], + params: [ + contractHash1, + { tracer: TracerType.OpcodeLogger, tracerConfig: { enableMemory: 'must be a boolean' } }, + ], id: '2', }); @@ -2618,7 +2621,9 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 'enableMemory' for OpcodeLoggerConfig: ${Validator.TYPES.boolean.error}, value: must be a boolean`, + `Invalid parameter 'tracerConfig' for TracerConfigWrapper: Expected TracerConfig, value: ${JSON.stringify({ + enableMemory: 'must be a boolean', + })}`, ); } }); @@ -2628,7 +2633,10 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, { disableStack: 'must be a boolean' }], + params: [ + contractHash1, + { tracer: TracerType.OpcodeLogger, tracerConfig: { disableStack: 'must be a boolean' } }, + ], id: '2', }); @@ -2637,7 +2645,9 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 'disableStack' for OpcodeLoggerConfig: ${Validator.TYPES.boolean.error}, value: must be a boolean`, + `Invalid parameter 'tracerConfig' for TracerConfigWrapper: Expected TracerConfig, value: ${JSON.stringify({ + disableStack: 'must be a boolean', + })}`, ); } }); @@ -2647,7 +2657,10 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, { disableStorage: 'must be a boolean' }], + params: [ + contractHash1, + { tracer: TracerType.OpcodeLogger, tracerConfig: { disableStorage: 'must be a boolean' } }, + ], id: '2', }); @@ -2656,7 +2669,9 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 'disableStorage' for OpcodeLoggerConfig: ${Validator.TYPES.boolean.error}, value: must be a boolean`, + `Invalid parameter 'tracerConfig' for TracerConfigWrapper: Expected TracerConfig, value: ${JSON.stringify({ + disableStorage: 'must be a boolean', + })}`, ); } }); @@ -2704,7 +2719,7 @@ describe('RPC Server', function () { await testClient.post('/', { jsonrpc: '2.0', method: 'debug_traceTransaction', - params: [contractHash1, TracerType.CallTracer, { invalidProperty: true }], + params: [contractHash1, { tracer: TracerType.CallTracer, tracerConfig: { invalidProperty: true } }], id: '2', }); @@ -2713,7 +2728,9 @@ describe('RPC Server', function () { BaseTest.invalidParamError( error.response, Validator.ERROR_CODE, - `Invalid parameter 2: ${Validator.TYPES.tracerConfig.error}, value: ${JSON.stringify({ + `Invalid parameter 'tracerConfig' for TracerConfigWrapper: ${ + Validator.TYPES.tracerConfig.error + }, value: ${JSON.stringify({ invalidProperty: true, })}`, ); @@ -2962,17 +2979,12 @@ describe('RPC Server', function () { }); it('should execute with valid block number and PrestateTracer', async () => { - let response; - try { - response = await testClient.post('/', { - jsonrpc: '2.0', - method: 'debug_traceBlockByNumber', - params: [blockNumberHex, { tracer: TracerType.PrestateTracer }], - id: '2', - }); - } catch (error: any) { - console.log('Errrooor ----->', error.response.data); - } + const response = await testClient.post('/', { + jsonrpc: '2.0', + method: 'debug_traceBlockByNumber', + params: [blockNumberHex, { tracer: TracerType.PrestateTracer }], + id: '2', + }); BaseTest.defaultResponseChecks(response); expect(response.data.result).to.be.an('array'); From c7f493b0e5c296c1c25ffcc1010f45294fd3a180 Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Mon, 16 Jun 2025 16:16:56 +0300 Subject: [PATCH 18/19] updates openrpc Signed-off-by: Konstantina Blazhukova --- docs/openrpc.json | 20 +------------------- 1 file changed, 1 insertion(+), 19 deletions(-) diff --git a/docs/openrpc.json b/docs/openrpc.json index 338a49173e..54f7e205e9 100644 --- a/docs/openrpc.json +++ b/docs/openrpc.json @@ -1064,29 +1064,11 @@ }, "description": "The hash of the transaction to trace." }, - { - "name": "tracer", - "required": false, - "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/TracerType" - }, - { - "$ref": "#/components/schemas/TracerConfig" - }, - { - "$ref": "#/components/schemas/TracerConfigWrapper" - } - ] - }, - "description": "Specifies the type of tracer or configuration object for the tracer." - }, { "name": "tracerConfig", "required": false, "schema": { - "$ref": "#/components/schemas/TracerConfig" + "$ref": "#/components/schemas/TracerConfigWrapper" }, "description": "Configuration object for the tracer." } From 77d55dc758c5d567d9423fcc559b1f7f1e333ced Mon Sep 17 00:00:00 2001 From: Konstantina Blazhukova Date: Tue, 17 Jun 2025 13:29:54 +0300 Subject: [PATCH 19/19] changes error type thrown for prestatetracer in traceTransction Signed-off-by: Konstantina Blazhukova --- packages/relay/src/lib/debug.ts | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/packages/relay/src/lib/debug.ts b/packages/relay/src/lib/debug.ts index 846340617c..6f8006711a 100644 --- a/packages/relay/src/lib/debug.ts +++ b/packages/relay/src/lib/debug.ts @@ -116,7 +116,7 @@ export class DebugImpl implements Debug { requestDetails: RequestDetails, ): Promise { if (tracerObject?.tracer === TracerType.PrestateTracer) { - throw predefined.INTERNAL_ERROR('Prestate tracer is not yet supported on debug_traceTransaction'); + throw predefined.INVALID_PARAMETER(1, 'Prestate tracer is not yet supported on debug_traceTransaction'); } if (this.logger.isLevelEnabled('trace')) { @@ -169,8 +169,6 @@ export class DebugImpl implements Debug { tracerObject: BlockTracerConfig, requestDetails: RequestDetails, ): Promise { - this.logger.info(`blockNumber: ${blockNumber}`); - this.logger.info(`tracerObject: ${JSON.stringify(tracerObject)}`); if (this.logger.isLevelEnabled('trace')) { this.logger.trace( `${