can someone help me understand the difference between trace_call
and debug_traceCall
? From what I've read, trace_call is to see the opcodes executed and the gas used for a transaction. debug_traceCall
seems to be something that's used when looking at a series of transactions over time. Is this correct and what is the purpose of understanding how a call would work in a specific block?... If that's even what debug_traceCall
even does
3 Answers
API methods trace_*
namespace was originally used in the openethereum client (which is currently unmaintained), some other clients such as erigon also provide this namespace.
While debug_*
namespace is available in go-ethereum and erigon clients.
Both APIs provide near-identical functionality to replay transaction opcode by opcode for a given state, however, they differ in request & response schema.
docs for trace_call: https://openethereum.github.io/JSONRPC-trace-module#trace_call
docs for debug_traceCall: https://geth.ethereum.org/docs/rpc/ns-debug#debug_tracecall
trace_call
is an API method that allows you to execute the given call and returns the number of possible traces for it. These traces include transactions that have been mined or hypothetical ones not yet mined. This method is used to provide detailed information regarding the fields of the transactions and functions called by a contract.
debug_traceCall
is an API method that allows you to perform a eth_call
on top of a given block using the final state of the parent block. It is used to debug and inspect call traces of transactions at run-time by setting certain debugging flags for transactions executing at the same or prior state. Debug API is the equivalent of OpenEthereum's Trace API.
Understanding how a call would work in a specific block allows you to understand the logic of your code at depth, how states have been changed and transactions are processed, and why transactions fail.
Function of these methods:
trace_call
& debug_traceCall
: These methods execute the given call and return a number of possible traces for it.
Differences
Here are some of the differences between these methods:
You can choose to trace only the main call (the top-level call) in
debug_traceCall
by setting theonlyTopCall
option totrue
. This avoids extra processing if only the top-level info is required (like getting the revert reason). However, this is not possible usingtrace_call
as you always get back the complete trace.You can replay a transaction in a particular block by providing the block hash in
debug_traceCall
but not intrace_call
. (However, both methods accept the block number in hex format and the tags likelatest
andearliest
).trace_call
is accessible through Erigon whiledebug_traceCall
is accessible through Geth.By using
trace_call
you can get the simple trace for a transaction (trace) and the state difference (stateDiff) in just one request by putting an array containingtrace
andstateDiff
options in trace_call's second parameter (["trace", "stateDiff"]
) but by usingdebug_traceCall
you can either get the traces usingcallTracer
or the state difference usingprestateTracer
in one request.
You can read more about it in the trace_call vs. debug_traceCall comparison guide by Alchemy.
Use cases
As for the use cases, these methods can be used for better understanding the flow of a transaction and for debugging purposes. The traces of a transaction are not shown in the transaction receipt, so they can only be extracted by using the trace
or debug
methods.
You can read more about it in the EVM Traces Guide by Alchemy.