DEV Community

Jerome Barton
Jerome Barton

Posted on

How Block Explorers Reconstruct Transaction Histories

Block explorers reconstruct transaction histories by indexing blocks, receipts, logs, and execution traces, then decoding those records into address- and protocol-level events.

Why a transaction history has to be rebuilt

An Ethereum Network node can answer questions about a transaction hash, block, receipt, or log filter, but it does not provide a canonical “show me every transaction involving this address” query. An explorer therefore walks through blocks, stores the results in searchable tables, and adds meaning afterward.

The transaction supplies the sender, recipient, calldata, value, nonce, and position. Its receipt supplies the execution status, gas used, block placement, and logs that survived execution. A history page is an indexed interpretation of those pieces, not a record stored on-chain as a ready-made timeline.

Way one: index transactions and event logs

The efficient method is to scan ordinary transactions and receipts, then use emitted events as the explorer’s main evidence.

  1. Store each block, transaction, and receipt with its block hash and transaction index.
  2. Read receipt logs in execution order and filter them by contract address and topics.
  3. Decode calldata and event data with the relevant contract ABI, turning hexadecimal values into token transfers, approvals, swaps, or governance actions.

This works especially well for ERC-20 activity. A Transfer event identifies the token contract, sender, recipient, and amount; indexed parameters become searchable topics, while the remaining values sit in ABI-encoded data. The explorer can then attach token symbols and decimals from contract metadata.

The limitation is equally important: a log records what a contract deliberately emitted, not every operation the EVM performed. A native ETH transfer may produce no event. A non-standard token may omit the expected event. Logs created inside a reverted call disappear with that call. A router transaction can therefore contain a useful sequence of token movements while still hiding the exact call path that produced them.

That is why a Frax Swap transaction can appear as several token movements rather than one simple “swap” row.

The same decoding pattern applies when examining Frax Swap activity.

Way two: trace the execution

Tracing reconstructs the call tree by replaying a transaction through an execution client. Instead of relying only on emitted events, the explorer asks which contract called which other contract, with what value, gas, calldata, and result.

A trace can expose a router calling a pool, the pool calling a token contract, and a nested call failing before the outer transaction reports failure. It can also reveal native-value transfers that have no ERC-20-style event. This makes traces valuable for internal transactions, contract creation, proxy routing, and debugging an apparent mismatch between balances and logs.

Tracing costs more than log indexing. It requires tracing support from the node and, for old transactions, access to the historical state needed to replay them. Providers may prune that state, restrict trace methods, or return different shapes depending on client and configuration. Trace output is reconstructed execution data; the block, transaction, receipt, and logs remain the primary consensus records.

Where the line falls

Use logs when the question is “which assets or protocol events were recorded?” Use traces when the question is “what call sequence caused this result?”

For an Automated Market Maker, logs usually give the cleanest user-facing answer: tokens in, tokens out, pool address, and amounts. A Balancer Protocol transaction, for example, may pass through a Vault and several pool balances; the logs can summarize those movements, while a trace explains the nested route and any intermediate calls.

The two methods are complementary, but they are not interchangeable. A log-only explorer is fast and scalable, yet can miss silent native transfers and unusual contracts. A trace-first explorer is richer, yet slower, more expensive, and dependent on historical replay.

What to build on

A reliable indexer keeps both layers. Use transactions, receipts, and logs for the canonical searchable history; add traces when the event record cannot answer the user’s question. Key records by chain ID, block hash, transaction index, and log index rather than timestamp alone. Decode with the ABI valid for that contract at that block, and rescan a small range when a chain reorganization replaces blocks.

The practical verdict is simple: logs tell you what contracts announced, while traces tell you how execution got there. A block explorer reconstructs trustworthy histories by knowing which of those two answers the application actually needs.</

Top comments (0)