TriportRPC

trace_replayBlockTransactions

POSThttps://api.triport.io/v1/eth

Re-executes every transaction in a block and returns a full execution trace — call graph, optional VM-level steps, and state changes — for each one.

Ethereumeth_tracepro (5 RPS) · business (15 RPS)

trace_replayBlockTransactions replays all transactions in a single block in order, against the state as it existed at that block, and returns one trace result per transaction. Unlike a plain receipt, the result can include the full internal call tree, a step-by-step virtual-machine trace, and the set of state slots each transaction read and wrote.

You choose how much detail to return with the traceTypes array. Request only what you need: vmTrace in particular produces very large payloads (one entry per executed opcode) and is the most expensive mode to compute. For most call-graph analysis, ["trace"] alone is enough.

Use this method for block-level forensics — reconstructing internal transfers, auditing MEV activity, or diffing state across a whole block — when per-transaction calls would be too chatty. This is a pro-tier method; requests authenticated with a lower tier are rejected with -32002.

Parameters

Positional params array: [block, traceTypes].

blockstringrequired
Block to replay. A hex block number ("0x1387f23"), a 32-byte block hash, or a tag: latest, earliest, pending, safe, finalized.
traceTypesstring[]required
Which traces to produce. Any combination of "trace" (internal call tree), "vmTrace" (per-opcode VM steps), and "stateDiff" (state read/write deltas). At least one is required.

Response

Response fields

result is an array with one entry per transaction in the block, in execution order. Each entry contains:

FieldTypeDescription
transactionHashstringHash of the replayed transaction.
outputstringHex-encoded return data of the top-level call.
traceobject[] | nullFlat list of call-tree frames. null unless "trace" was requested.
trace[].actionobjectThe call/create/suicide being performed (callType, from, to, gas, input, value).
trace[].resultobjectOutcome of the frame (gasUsed, output).
trace[].subtracesnumberNumber of direct child frames.
trace[].traceAddressnumber[]Path of this frame within the call tree.
vmTraceobject | nullPer-opcode VM execution. null unless "vmTrace" was requested.
vmTrace.ops[]object[]One entry per executed opcode (pc, cost, ex, sub).
stateDiffobject | nullPer-address state deltas keyed by address. null unless "stateDiff" was requested.
stateDiff.<addr>.balance / .nonce / .code / .storageobject | string"=" means unchanged; { "*": { "from", "to" } } describes a change; { "+": v } an addition.

Errors

CodeMeaningWhen it happens
-32002tier_insufficientThe API key's tier is below pro.
-32003rate_limitedRPS limit for your tier exceeded (5 RPS pro, 15 RPS business). Back off and retry.
-32602Invalid paramsMissing/malformed block, or traceTypes empty or containing an unknown type.
-32000Resource not foundThe requested block does not exist or is not yet available.

All errors use the shared JSON-RPC error envelope — see errors.md for the full structure and retry guidance.

Examples

JavaScript (fetch)

const res = await fetch("https://api.triport.io/v1/eth", {
  method: "POST",
  headers: {
    "Authorization": `Bearer ${process.env.TRIPORT_API_KEY}`,
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    jsonrpc: "2.0",
    id: 1,
    method: "trace_replayBlockTransactions",
    params: ["0x1387f23", ["trace", "stateDiff"]],
  }),
});


const { result } = await res.json();
console.log(`${result.length} transactions replayed`);

TypeScript SDK (@triport/sdk)

import { Triport } from "@triport/sdk";


const client = new Triport({ apiKey: process.env.TRIPORT_API_KEY! });


const traces = await client.eth.trace.replayBlockTransactions("0x1387f23", [
  "trace",
  "vmTrace",
  "stateDiff",
]);


for (const tx of traces) {
  console.log(tx.transactionHash, tx.trace?.length ?? 0, "frames");
}

Python (triport-sdk)

import os
from triport import Triport


client = Triport(api_key=os.environ["TRIPORT_API_KEY"])


traces = client.eth.trace.replay_block_transactions(
    "0x1387f23",
    ["trace", "state_diff"],
)


for tx in traces:
    print(tx["transactionHash"], len(tx.get("trace") or []), "frames")

Notes

  • Cost scales with what you ask for. vmTrace emits one record per opcode and can return megabytes for a busy block; request it only when you need opcode-level detail. ["trace"] is the cheapest useful mode.
  • Ordering. Results are returned in block execution order, so the array index aligns with each transaction's position in the block.
  • Related methods. To replay arbitrary transactions instead of a whole block, see trace_replayTransaction. For a single confirmed transaction's call tree, see trace_transaction. To filter traces across a block range by address, see trace_filter.