Skip to content

fix eth transaction receipt cache - #7420

Open
sudo-shashank wants to merge 7 commits into
mainfrom
shashank/fix-cache-eth-tx-receipt
Open

fix eth transaction receipt cache#7420
sudo-shashank wants to merge 7 commits into
mainfrom
shashank/fix-cache-eth-tx-receipt

Conversation

@sudo-shashank

@sudo-shashank sudo-shashank commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Summary of changes

Changes introduced in this pull request:

  • Cache Not Found results for full searches. Limited searches that fail to find transaction receipts are not cached, since the receipt could still exist beyond the limit.
  • Drop non-finalized cache entries when the chain head changes (reorg-safe), Finalized receipts are immutable, so they're cached permanently.

Reference issue to close (if applicable)

Closes #7330

Other information and links

Change checklist

  • I have performed a self-review of my own code,
  • I have made corresponding changes to the documentation. All new code adheres to the team's documentation standards,
  • I have added tests that prove my fix is effective or that my feature works (if possible),
  • I have made sure the CHANGELOG is up-to-date. All user-facing changes should be reflected in this document.

Outside contributions

  • This pull request is based on an issue that a maintainer has accepted (see Before Opening a Pull Request).
  • I have read and agree to the CONTRIBUTING document.
  • I have read and agree to the AI Policy document. I understand that failure to comply with the guidelines will lead to rejection of the pull request.

Summary by CodeRabbit

  • Bug Fixes
    • Improved transaction receipt lookups as the blockchain head advances.
    • Prevented temporary “not found” results from being reused incorrectly.
    • Preserved finalized receipt results while refreshing non-finalized data when needed.
    • Maintained lookback limits when returning cached transaction receipts.

@coderabbitai

coderabbitai Bot commented Jul 29, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: fbcf6c98-99ea-4900-813c-20d6e99b037a

📥 Commits

Reviewing files that changed from the base of the PR and between 650a10d and 54797c9.

📒 Files selected for processing (1)
  • src/rpc/methods/eth.rs
🔗 Linked repositories identified

CodeRabbit considers these linked repositories for cross-repo context during reviews:

  • filecoin-project/lotus (manual)
🚧 Files skipped from review as they are similar to previous changes (1)
  • src/rpc/methods/eth.rs

Walkthrough

eth_getTransactionReceipt caching now tracks the computation head and receipt finality, invalidates mutable entries after head changes, avoids caching limited not-found results, and reapplies the lookback constraint on cached results.

Changes

Transaction receipt cache

Layer / File(s) Summary
Receipt cache record and finality
src/rpc/methods/eth.rs
CachedReceipt stores the optional receipt, computation head key, and finalization status derived from chain finality.
Receipt cache invalidation and filtering
src/rpc/methods/eth.rs
Mutable entries are evicted when the head changes, limited not-found results remain uncached, and cached receipts are filtered by the requested lookback limit.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Suggested reviewers: hanabi1224, eclesiomelojunior

Sequence Diagram(s)

sequenceDiagram
  participant eth_getTransactionReceipt
  participant cache_eth_transaction_receipt
  participant chain_lookup
  eth_getTransactionReceipt->>cache_eth_transaction_receipt: request receipt by tx_hash and limit
  cache_eth_transaction_receipt->>chain_lookup: compare head and compute receipt when needed
  chain_lookup-->>cache_eth_transaction_receipt: receipt or not found within limit
  cache_eth_transaction_receipt-->>eth_getTransactionReceipt: receipt filtered by finality and lookback
Loading
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title is concise and accurately reflects the main change to the Ethereum transaction receipt cache.
Linked Issues check ✅ Passed The changes address #7330 by reworking receipt cache behavior to improve hit rate and align caching with finality and head changes.
Out of Scope Changes check ✅ Passed The PR stays focused on eth_getTransactionReceipt cache behavior and does not introduce unrelated changes.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch shashank/fix-cache-eth-tx-receipt
✨ Simplify code
  • Create PR with simplified code
  • Commit simplified code in branch shashank/fix-cache-eth-tx-receipt

Comment @coderabbitai help to get the list of available commands.

@sudo-shashank sudo-shashank added the RPC requires calibnet RPC checks to run on CI label Jul 29, 2026

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🧹 Nitpick comments (1)
src/rpc/methods/eth.rs (1)

2966-2969: 🎯 Functional Correctness | 🔵 Trivial | ⚡ Quick win

is_finalized refetches the head instead of reusing the caller's head.

get_eth_transaction_receipt_with_cache already fetches head at line 2986 and passes head_key into the cache entry, but is_finalized independently calls ctx.chain_store().heaviest_tipset() again. If the chain advances between these two fetches, the stored head_key and the head used to compute finalized can come from different tipsets, which is a subtle inconsistency in the cached record. Passing the already-known head epoch into is_finalized avoids the redundant lookup and keeps the record internally consistent.

♻️ Proposed refactor
-fn is_finalized(ctx: &Ctx, receipt_epoch: ChainEpoch) -> bool {
-    let head_epoch = ctx.chain_store().heaviest_tipset().epoch();
-    receipt_epoch <= head_epoch - ctx.chain_config().policy.chain_finality
-}
+fn is_finalized(ctx: &Ctx, head_epoch: ChainEpoch, receipt_epoch: ChainEpoch) -> bool {
+    receipt_epoch <= head_epoch - ctx.chain_config().policy.chain_finality
+}

Then call it with the already-fetched head.epoch() at the call site instead of re-deriving it inside the closure.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/rpc/methods/eth.rs` around lines 2966 - 2969, Update is_finalized to
accept the caller’s already-fetched head epoch instead of reading
ctx.chain_store().heaviest_tipset() internally, and pass head.epoch() from
get_eth_transaction_receipt_with_cache when computing finalized. Preserve the
existing finality comparison and cache behavior while eliminating the second
head lookup.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/rpc/methods/eth.rs`:
- Around line 3016-3018: Update the receipt miss check near
eth_getTransactionReceiptLimited so it treats only positive limits as bounded,
matching max_lookback_epoch_inclusive; use the limit > 0 predicate instead of
checking limit.is_some(), ensuring Some(-1) remains unbounded and does not
return Uncacheable::NotFoundWithinLimit.
- Around line 2989-2995: Replace the separate CACHE.peek and CACHE.remove logic
in the stale-entry block with Cache::remove_if, using the existing !e.finalized
&& e.head_key != head_key predicate so the conditional removal is atomic.

---

Nitpick comments:
In `@src/rpc/methods/eth.rs`:
- Around line 2966-2969: Update is_finalized to accept the caller’s
already-fetched head epoch instead of reading
ctx.chain_store().heaviest_tipset() internally, and pass head.epoch() from
get_eth_transaction_receipt_with_cache when computing finalized. Preserve the
existing finality comparison and cache behavior while eliminating the second
head lookup.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository UI

Review profile: CHILL

Plan: Pro

Run ID: 0c915d64-6b9a-4157-985b-b47600e7329d

📥 Commits

Reviewing files that changed from the base of the PR and between c6e0744 and 0af886f.

📒 Files selected for processing (1)
  • src/rpc/methods/eth.rs
🔗 Linked repositories identified

CodeRabbit considers these linked repositories for cross-repo context during reviews:

  • filecoin-project/lotus (manual)

Comment thread src/rpc/methods/eth.rs Outdated
Comment thread src/rpc/methods/eth.rs Outdated
@sudo-shashank
sudo-shashank force-pushed the shashank/fix-cache-eth-tx-receipt branch from 369054b to fe066ba Compare July 29, 2026 13:42
@sudo-shashank
sudo-shashank force-pushed the shashank/fix-cache-eth-tx-receipt branch from fe066ba to 650a10d Compare July 29, 2026 13:48
@sudo-shashank
sudo-shashank marked this pull request as ready for review July 29, 2026 15:05
@sudo-shashank
sudo-shashank requested a review from a team as a code owner July 29, 2026 15:05
@sudo-shashank
sudo-shashank requested review from EclesioMeloJunior and hanabi1224 and removed request for a team July 29, 2026 15:05
@codecov

codecov Bot commented Jul 29, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 83.33333% with 6 lines in your changes missing coverage. Please review.
✅ Project coverage is 65.16%. Comparing base (256a920) to head (fc16ff5).
✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
src/rpc/methods/eth.rs 83.33% 3 Missing and 3 partials ⚠️
Additional details and impacted files
Files with missing lines Coverage Δ
src/rpc/methods/eth.rs 68.56% <83.33%> (+0.13%) ⬆️

... and 6 files with indirect coverage changes


Continue to review full report in Codecov by Harness.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 256a920...fc16ff5. Read the comment docs.

🚀 New features to boost your workflow:
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

RPC requires calibnet RPC checks to run on CI

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Investigate low cache hit rate for cache_eth_transaction_receipt

1 participant