Performance guide
Ethereum RPC latency has more than one floor
A remote RPC provider can optimize routing and servers, but it cannot remove your physical network trip. A safe local cache can remove that trip for repeated reads.
Where the time goes
| Layer | Typical cause | Useful optimization |
|---|---|---|
| Client | Connection creation, JSON parsing, queueing | Keep-alive, batching, fixed concurrency |
| Network | Distance, TLS, congestion | Persistent WebSocket, closer region |
| Edge | Authentication and routing | Signed-token verification, in-memory state |
| Upstream | Node execution and provider queue | Coalescing, hedging, validated providers |
| Warm local | Loopback HTTP and cache lookup | Device-local memory |
Choose the right cache target
Static chain metadata and explicit finalized-block reads are the safest cache candidates. Latest balances, calls, gas data, receipts, and logs require shorter policies and head-aware invalidation. A fast cache that silently returns incorrect state is worse than a slower RPC.
Measure cold and warm separately
A benchmark should report cache status, valid Ethereum results, error rate, p50/p95/p99, and client wall time. Including one cold miss in a 100-call “warm p99” test makes the maximum upstream trip look like cache latency. Excluding cold misses without disclosing them is equally misleading.
RPC Relay proof: 300 explicit finalized-state warm reads measured 1.55ms p50 and 2.84ms p95 on the tested Mac. See the methodology and raw evidence.
Practical checklist
- Reuse connections or a WebSocket.
- Coalesce identical concurrent misses.
- Use explicit block tags when possible.
- Invalidate volatile data on canonical-head changes.
- Track fallback and stale responses explicitly.
- Benchmark at the concurrency your application actually uses.