Skip to content

Fix receipt generate#252

Closed
curryxbo wants to merge 3 commits intomainfrom
fixReceiptGenerate
Closed

Fix receipt generate#252
curryxbo wants to merge 3 commits intomainfrom
fixReceiptGenerate

Conversation

@curryxbo
Copy link
Copy Markdown
Contributor

@curryxbo curryxbo commented Nov 20, 2025

1. Purpose or design rationale of this PR

...

2. PR title

Your PR title must follow conventional commits (as we are doing squash merge for each PR), so it must start with one of the following types:

  • build: Changes that affect the build system or external dependencies (example scopes: yarn, eslint, typescript)
  • ci: Changes to our CI configuration files and scripts (example scopes: vercel, github, cypress)
  • docs: Documentation-only changes
  • feat: A new feature
  • fix: A bug fix
  • perf: A code change that improves performance
  • refactor: A code change that doesn't fix a bug, or add a feature, or improves performance
  • style: Changes that do not affect the meaning of the code (white-space, formatting, missing semi-colons, etc)
  • test: Adding missing tests or correcting existing tests

3. Deployment tag versioning

Has the version in params/version.go been updated?

  • This PR doesn't involve a new deployment, git tag, docker image tag, and it doesn't affect traces
  • Yes

4. Breaking change label

Does this PR have the breaking-change label?

  • This PR is not a breaking change
  • Yes

Summary by CodeRabbit

  • Refactor
    • Widened fee token identifier to support larger values across receipts, traces, and transaction processing
    • Standardized JSON field names to camelCase (e.g., feeTokenID, feeRate, tokenScale) for consistent external serialization
    • Aligned in-memory and serialized representations so fee-related fields use the updated, widened numeric type for interoperability

✏️ Tip: You can customize this high-level summary in your review settings.

@curryxbo curryxbo requested a review from a team as a code owner November 20, 2025 12:27
@curryxbo curryxbo requested review from Web3Jumb0 and removed request for a team November 20, 2025 12:27
@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented Nov 20, 2025

Walkthrough

Widened the FeeTokenID field from *uint16 to *uint64 across storage, in-memory types, and JSON (de)serialization; also renamed several fee-related JSON tags from snake_case to camelCase. No control-flow or error-handling changes were introduced.

Changes

Cohort / File(s) Summary
Storage / Raw DB
core/rawdb/accessors_chain.go
storedReceiptRLP field FeeTokenID changed from *uint16 to *uint64.
Core types & storage models
core/types/receipt.go
Receipt.FeeTokenID changed from *uint16 to *uint64; storedReceiptRLP and v7StoredReceiptRLP updated likewise; fee-related JSON tags converted to camelCase (feeTokenID, feeRate, tokenScale); marshaling wrapper fields adjusted to hexutil types.
JSON (de)serialization (generated)
core/types/gen_receipt_json.go
Marshal/Unmarshal now use *hexutil.Uint64 as the intermediate JSON representation and convert to/from *uint64 for FeeTokenID.
State processing
core/state_processor.go
Cast FeeTokenID() result to uint64 when assigning to receipt to match widened pointer type.
Tracing & transaction data
core/types/l2trace.go, core/types/*
ExecutionResult.FeeTokenID and TransactionData.FeeTokenID changed from *uint16 to *uint64; NewTransactionData/AltFee path casts FeeTokenID() to uint64.
API args JSON tags
internal/ethapi/transaction_args.go
JSON tags for TransactionArgs fields changed from snake_case to camelCase (feeTokenID, feeLimit) — types unchanged.

Sequence Diagram(s)

(omitted — changes are type/serialization and do not alter control flow)

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • Review focus:
    • Nil handling and pointer casts between *uint64, *hexutil.Uint64, and previous *uint16.
    • Consistency of JSON tag renames across APIs, traces, and clients.
    • Storage/RLP compatibility and any migration considerations for persisted receipts.

Possibly related PRs

Suggested reviewers

  • Web3Jumb0
  • tomatoishealthy

Poem

🐰 From sixteen bits I took a hop,
To sixty-four I gave a drop.
CamelCase carrots, JSON bright,
Pointers stretched to fit the night. 🥕✨

Pre-merge checks and finishing touches

❌ Failed checks (1 inconclusive)
Check name Status Explanation Resolution
Title check ❓ Inconclusive The title 'Fix receipt generate' is vague and does not clearly convey what specific issue is being fixed or what the actual changes accomplish. Replace with a more descriptive title following Conventional Commits format, such as 'fix: update FeeTokenID type from uint16 to uint64 in receipt structs' to clearly indicate the nature of the fix.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch fixReceiptGenerate

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 golangci-lint (2.5.0)

Error: can't load config: unsupported version of the configuration: "" See https://golangci-lint.run/docs/product/migration-guide for migration instructions
The command is terminated due to an error: can't load config: unsupported version of the configuration: "" See https://golangci-lint.run/docs/product/migration-guide for migration instructions


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between adf5a14 and fa0330e.

📒 Files selected for processing (3)
  • core/rawdb/accessors_chain.go (1 hunks)
  • core/types/gen_receipt_json.go (4 hunks)
  • core/types/receipt.go (4 hunks)
🧰 Additional context used
🧠 Learnings (2)
📓 Common learnings
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.
📚 Learning: 2025-11-10T06:56:24.937Z
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.

Applied to files:

  • core/rawdb/accessors_chain.go
  • core/types/receipt.go
  • core/types/gen_receipt_json.go
🧬 Code graph analysis (2)
core/types/receipt.go (1)
common/hexutil/json.go (2)
  • Uint64 (275-275)
  • Big (155-155)
core/types/gen_receipt_json.go (1)
common/hexutil/json.go (3)
  • Uint64 (275-275)
  • Big (155-155)
  • Uint (339-339)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Analyze (go)
🔇 Additional comments (6)
core/types/receipt.go (2)

120-124: Storage encoding updated consistently.

The storedReceiptRLP struct correctly reflects the FeeTokenID type change to *uint64. The encoding/decoding logic in EncodeRLP (lines 339-354) and decode functions (lines 385-406) properly handle the updated type.


134-138: v7StoredReceiptRLP updated consistently.

The v7StoredReceiptRLP struct and its decoder (decodeV7StoredReceiptRLP, lines 408-429) correctly handle the FeeTokenID type change to *uint64.

core/types/gen_receipt_json.go (3)

36-36: JSON marshaling correctly updated for FeeTokenID.

The generated code properly handles marshaling of FeeTokenID from *uint64 to *hexutil.Uint64 for JSON encoding. The pointer cast at line 59 is consistent with the pattern used for other hexutil types throughout this generated file.

Also applies to: 59-59


86-86: JSON unmarshaling correctly updated for FeeTokenID.

The generated code properly handles unmarshaling of FeeTokenID from *hexutil.Uint64 back to *uint64. The pointer cast at line 152 follows the same pattern as other hexutil type conversions in this file.

Also applies to: 152-152


1-1: Auto-generated file correctly regenerated.

Verification confirms that gen_receipt_json.go was properly regenerated using the gencodec generator. The go:generate directive at core/types/receipt.go:34 is correctly configured and in place.

core/rawdb/accessors_chain.go (1)

622-622: The review comment premise is factually incorrect, but the underlying backward compatibility concern is valid for a different reason.

The git diff shows that FeeTokenID, FeeRate, TokenScale, and FeeLimit are new fields being added to storedReceiptRLP, not a type change from *uint16 to *uint64. The field did not previously exist in the storage struct.

However, the core concern remains valid: adding new fields to a serialized storage format without introducing a new version constant (like v8StoredReceiptRLP) may cause issues. Old receipts lacking these fields could fail to decode if the decoder doesn't account for them gracefully.

Additionally, duplicate storedReceiptRLP struct definitions exist in both core/types/receipt.go and core/rawdb/accessors_chain.go, which could lead to versioning mismatches if they diverge.

Comment thread core/types/receipt.go
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
core/types/l2trace.go (1)

60-62: Inconsistent JSON tag naming convention.

The ExecutionResult struct has mixed JSON tag naming: fee_token_id and token_scale use snake_case (lines 60, 62), while feeRate uses camelCase (line 61). For consistency and to align with the PR's goal of standardizing on camelCase, consider updating the snake_case tags.

Apply this diff to standardize on camelCase:

-	FeeTokenID  *uint64      `json:"fee_token_id,omitempty"`
+	FeeTokenID  *uint64      `json:"feeTokenID,omitempty"`
 	FeeRate     *hexutil.Big `json:"feeRate,omitempty"`
-	TokenScale  *hexutil.Big `json:"token_scale,omitempty"`
+	TokenScale  *hexutil.Big `json:"tokenScale,omitempty"`

Note: This is a breaking change for API consumers. Ensure this aligns with your versioning and compatibility requirements.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between fa0330e and 16a6063.

📒 Files selected for processing (2)
  • core/state_processor.go (1 hunks)
  • core/types/l2trace.go (1 hunks)
🧰 Additional context used
🧠 Learnings (2)
📓 Common learnings
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.
📚 Learning: 2025-11-10T06:56:24.937Z
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.

Applied to files:

  • core/state_processor.go
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Analyze (go)
🔇 Additional comments (1)
core/state_processor.go (1)

196-197: LGTM: Explicit cast correctly handles type widening.

The explicit cast to uint64 on line 196 appropriately handles the widening of FeeTokenID from uint16 to uint64, aligning with the updated Receipt.FeeTokenID type. The widening conversion is safe and prevents any data loss.

Comment thread core/types/l2trace.go Outdated
Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
internal/ethapi/transaction_args.go (1)

309-312: Add bounds validation: FeeTokenID narrowed from uint64 to uint16 without checking maximum value.

The API accepts FeeTokenID as a *hexutil.Uint64 (line 54), but it's cast to uint16 at lines 311 and 399 without bounds checking. Values exceeding 65535 will silently truncate to the lower 16 bits, potentially causing unexpected behavior or transaction routing to wrong fee tokens.

Fix by validating the value before narrowing:

 var feeTokenID uint16
 if args.FeeTokenID != nil {
+	if *args.FeeTokenID > math.MaxUint16 {
+		return types.Message{}, fmt.Errorf("feeTokenID exceeds maximum value of %d", math.MaxUint16)
+	}
 	feeTokenID = uint16(*args.FeeTokenID)
 }

Apply the same validation at line 399 where AltFeeTx is constructed.

♻️ Duplicate comments (1)
internal/ethapi/transaction_args.go (1)

399-399: Same truncation issue when constructing AltFeeTx.

Similar to the issue at lines 309-312, this line narrows *hexutil.Uint64 to uint16 without validation. Apply the same fix here to ensure consistency.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 16a6063 and 6bcad23.

📒 Files selected for processing (2)
  • core/types/l2trace.go (3 hunks)
  • internal/ethapi/transaction_args.go (1 hunks)
🧰 Additional context used
🧠 Learnings (2)
📓 Common learnings
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.
📚 Learning: 2025-11-10T06:56:24.937Z
Learnt from: Kukoomomo
Repo: morph-l2/go-ethereum PR: 205
File: core/token_gas.go:140-155
Timestamp: 2025-11-10T06:56:24.937Z
Learning: In the ERC20 fee implementation (core/token_gas.go), ERC20 transfer and balance check calls use math.MaxUint64 gas limit. This is intentional given that fee tokens are restricted to an allowlist (via IsTokenActive checks and AllowListSlot/AllowListEnabledSlot in rollup/rcfg/config.go), so only vetted contracts can be invoked. The team has chosen this approach understanding the tradeoffs versus adding fixed gas stipends.

Applied to files:

  • core/types/l2trace.go
🧬 Code graph analysis (1)
internal/ethapi/transaction_args.go (1)
common/hexutil/json.go (2)
  • Uint64 (275-275)
  • Big (155-155)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Analyze (go)
🔇 Additional comments (2)
core/types/l2trace.go (2)

141-141: Type consistency restored.

The TransactionData.FeeTokenID field is now consistently *uint64, matching ExecutionResult.FeeTokenID (line 60). This addresses the inconsistency flagged in the previous review.


199-203: Ignore FeeTokenID widening concern. The core Transaction, Message, and AltFeeTx types intentionally use uint16 for FeeTokenID (core/types/transaction.go 364, alt_fee_tx.go 38), with JSON serializers using uint64 externally. The cast in l2trace.go is safe and by design.

Comment thread core/types/l2trace.go
Comment thread internal/ethapi/transaction_args.go
@curryxbo curryxbo closed this Nov 21, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant