Skip to content

rpc: fix testing build block v1 according Hive Test#20592

Open
lupin012 wants to merge 8 commits intomainfrom
lupin012/fix_testing_buildBlockV1
Open

rpc: fix testing build block v1 according Hive Test#20592
lupin012 wants to merge 8 commits intomainfrom
lupin012/fix_testing_buildBlockV1

Conversation

@lupin012
Copy link
Copy Markdown
Contributor

@lupin012 lupin012 commented Apr 15, 2026

This PR fixes the following Hive test failures:

  • testing_buildBlockV1/build-block-empty-transactions
  • testing_buildBlockV1/build-block-invalid-transaction
  • testing_buildBlockV1/build-block-with-transactions

Note:
The test testing_buildBlockV1/build-block-from-mempool currently still fails; this is expected as it will be updated to a speconly type, following the changes in:
execution-apis PR #783.

Changes vs main

  • Explicit transaction list support in testing_buildBlockV1
    In main the endpoint returns an error if a non-empty transaction list is passed. This branch implements the full flow: raw transactions are decoded, the sender is recovered via the chain signer, and nonces are validated sequentially per sender against the current state.
    Three modes: null → mempool, [] → empty block, [...] → exact transaction list with strict nonce check.

  • execution/builder/parameters.go — added CustomTxnProvider txnprovider.TxnProvider: allows injecting an alternative transaction source without exposing the concrete type to the builder.

  • execution/engineapi/testing_api.go

    • testingImpl now holds logger and db (kv.TemporalRoDB) to read account nonces from state.
    • staticTxnProvider (private) — yields the fixed transaction list exactly once, then returns nil.
    • The testing namespace is now wired into jsonrpc.APIList via node/eth/backend.go, consistent with all other namespaces.

    Tests — full coverage: input validation, busy execution paths, happy path (mempool and explicit list), nonce too high/low, multi-sender nonce tracking, fork-specific parameter propagation (Withdrawals, ParentBeaconBlockRoot) to assembleParams.

lupin012 and others added 6 commits April 15, 2026 17:50
Move staticTxnProvider from txnprovider (public API) into the
testing_ namespace where it belongs. Replace Parameters.OverrideTxns
with Parameters.CustomProvider (txnprovider.TxnProvider interface)
so the builder is opaque to the provider implementation.

- builder.Parameters: OverrideTxns *[]types.Transaction → CustomProvider TxnProvider
- builder.Build: drop NewStaticTxnProvider call, just assign param.CustomProvider
- engineapi/testing_api: add local staticTxnProvider, create it after tx decode
- txnprovider/provider.go: remove NewStaticTxnProvider (reverted to main)
- txnprovider/shutter/pool_test.go: restore EmptyTxnProvider (reverted to main)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Remove GetAccountNonce from ExecModule (execmodule/getters.go) — it
  was added solely for the testing_ namespace
- Remove accountNonceGetter interface and nonceGetter field from
  testingImpl; replace with a private getAccountNonce method that uses
  t.db and t.logger directly
- Add logger and db params to NewTestingImpl / NewTestingRPCEntry;
  pass s.logger and s.chainDB from backend.go
- Move case "testing" into jsonrpc.APIList switch (same pattern as
  other namespaces); add testingEntry *rpc.API param to APIList
- Restructure "nonce too low" test: simulate via two txs with the same
  nonce from the same sender (no db required)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Remove redundant `if len(*transactions) > 0` guard in decodeTxnProvider
  (range over empty slice is already a no-op)
- staticTxnProvider.ProvideTxns: nil out txns slice after consume to
  allow GC of decoded transactions once the builder has taken them
- TestStaticTxnProvider: replace ECDSA key generation with a simple
  stub transaction — atomic consumed semantics don't require a real tx
- Extract nilGetAssembledBlock as a package-level var shared by
  TestBuildBlockV1AssembleParamsVersion and TestBuildBlockV1MultipleSendersNonce
- Add TestBuildBlockV1AssembleParamsVersion: verifies fork-specific fields
  (ParentBeaconBlockRoot, Withdrawals) are correctly propagated to assembleParams
- Add TestBuildBlockV1MultipleSendersNonce: covers per-sender nonce tracking
  with interleaved transactions from two different senders
- Add TestStaticTxnProvider: direct unit test of ProvideTxns atomic behaviour

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@lupin012 lupin012 added the RPC label Apr 15, 2026
@lupin012 lupin012 marked this pull request as ready for review April 18, 2026 21:20
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Fixes Hive failures for testing_buildBlockV1 by adding explicit transaction list support, wiring the testing_ namespace through the standard JSON-RPC API registry, and aligning payload JSON output with expectations.

Changes:

  • Implement explicit transaction-list flow in testing_buildBlockV1 (decode txs, recover senders, strict per-sender sequential nonce validation) and plumb it into the builder via a CustomTxnProvider.
  • Wire testing_ into jsonrpc.APIList and pass the entry from node/eth/backend.go (with a prominent production warning when enabled).
  • Adjust Engine API JSON encoding for blockAccessList to omit empty values; expand/adjust tests around the new behaviors.

Reviewed changes

Copilot reviewed 9 out of 9 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
rpc/jsonrpc/daemon.go Adds optional testing API entry wiring to the centralized API list and logs a warning when enabled.
node/eth/backend.go Constructs/passes testing_ RPC entry into APIList instead of manually appending.
execution/engineapi/testing_api.go Implements explicit tx list decoding + nonce checks, DB-backed nonce reads, staticTxnProvider, and blockValue/extraData handling tweaks.
execution/engineapi/testing_api_test.go Adds coverage for invalid tx bytes, nonce too high/low, multi-sender tracking, params propagation, and staticTxnProvider.
execution/engineapi/engine_types/jsonrpc.go Makes blockAccessList omit empty values in JSON.
execution/builder/parameters.go Adds CustomTxnProvider to allow overriding the transaction source.
execution/builder/builder.go Uses CustomTxnProvider when provided, otherwise defaults to the builder’s injected provider.
cmd/rpcdaemon/main.go Updates APIList call signature (passes nil testing entry).
cmd/mcp/main.go Updates APIList call signature (passes nil testing entry).

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +117 to +123
if _, seen := expectedNonce[sender]; !seen {
stateNonce, err := t.getAccountNonce(ctx, sender.Value())
if err != nil {
return nil, err
}
expectedNonce[sender] = stateNonce
}
Copy link

Copilot AI Apr 19, 2026

Choose a reason for hiding this comment

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

decodeTxnProvider calls getAccountNonce the first time it sees each sender, and getAccountNonce opens a new temporal DB transaction + SharedDomains every time. For large explicit tx lists with many senders this adds significant overhead. Consider opening the temporal tx/SharedDomains/state.Reader once per BuildBlockV1 call (or once per decodeTxnProvider call) and reading all needed nonces from that single reader, caching them in expectedNonce.

Copilot uses AI. Check for mistakes.
Comment on lines +127 to +136
return nil, &rpc.CustomError{
Code: rpc.ErrCodeDefault,
Message: fmt.Sprintf("nonce too high: address %v, tx: %d state: %d", sender.Value(), got, want),
}
}
if got < want {
return nil, &rpc.CustomError{
Code: rpc.ErrCodeDefault,
Message: fmt.Sprintf("nonce too low: address %v, tx: %d state: %d", sender.Value(), got, want),
}
Copy link

Copilot AI Apr 19, 2026

Choose a reason for hiding this comment

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

Nonce mismatches are treated as rpc.CustomError with ErrCodeDefault (-32000). Since this is a request/parameter validation failure (like the decode/sender recovery paths just above), returning rpc.InvalidParamsError (or at least using -32602) would be more consistent and easier for clients/tests to classify as an input error.

Suggested change
return nil, &rpc.CustomError{
Code: rpc.ErrCodeDefault,
Message: fmt.Sprintf("nonce too high: address %v, tx: %d state: %d", sender.Value(), got, want),
}
}
if got < want {
return nil, &rpc.CustomError{
Code: rpc.ErrCodeDefault,
Message: fmt.Sprintf("nonce too low: address %v, tx: %d state: %d", sender.Value(), got, want),
}
return nil, &rpc.InvalidParamsError{Message: fmt.Sprintf("nonce too high: address %v, tx: %d state: %d", sender.Value(), got, want)}
}
if got < want {
return nil, &rpc.InvalidParamsError{Message: fmt.Sprintf("nonce too low: address %v, tx: %d state: %d", sender.Value(), got, want)}

Copilot uses AI. Check for mistakes.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants