Release notes
Major highlights
State design upgrade: Half-path
This version introduces a new approach to the state database: half-path. It replaces the previous approach, which we will call hash for these notes.
The goal of half-path is to improve the performance of the existing database without significant codebase changes. It is a middleware between the hash and full-path-based designs (which we are currently working on). It is mainly aimed at validators' performance (we observed a significant improvement in effectiveness) and, as a side effect, improving archive nodes' sync.
Major achievements
- Block processing time is faster by about 30 to 50% (depending on the hardware setup), but we observed that it improves low-end setups more, so the cost of hosting nodes using Nethermind software may decrease.
- The state database size is ~25% smaller (the previous approach is now close to 200 GB while the half-path is around 150 GB). This is only for the state database. After snap sync, the entire database will decrease by ~50 GB but still hover around 900 GB.
- State database growth is significantly reduced—the slower the database grows, the less maintenance around the node is needed.
We are still observing the exact numbers and applying some optimizations to make it as close as possible to "live pruning", but the database should grow about 10 to 20 times slower (to see the full effect, it may need 1 or 2 weeks—growth ratio will be dropping after that time). - Faster archive node sync. As half-path is not meant to optimize archive nodes, we observe that it is quicker than the previous implementation (8mln blocks processed about 30 to 40% faster, and the gap was only increasing—more tests around that are to be conducted).
- Smaller archive node database. As stated above, the major goal of the half-path wasn't to make the archive node smaller, but what was observed was 2.4 TB vs 1.7 TB at the 8mln blocks checkpoint—and the gap was getting bigger. We are now checking the final numbers.
Making the migration to the half-path hassle-free
- All newly synced nodes will use half-path as the default state design. If node operators want to use the previous approach, they can specify it with
--Init.StateDbKeyScheme Hash
. - All existing nodes that are synced with the old hash approach will remain on it.
Env variable equivalent of this flag is: NETHERMIND_INITCONFIG_STATEDBKEYSCHEME=HalfPath/Hash
Migration to half-path
- Full resync. This is the simplest yet most effective way to migrate. As Nethermind syncs quickly back to the head, it may take just 1-2 hours to get back on track.
- Full pruning. There is an option to migrate while staying online using the full pruning functionality. The downside of that approach is that pruning will take much longer to finish, and users will need to restart their nodes with
--Init.StateDbKeyScheme HalfPath
— without it, pruning will behave as before, so it will recreate the state with the previous database approach. To reduce slowdown, the user should increase the default full pruning memory budget to at least 8 GB:--Pruning.FullPruningMemoryBudgetMb 8000
.
Upgrading from previous versions
- From v1.25.4. The node will remain on the previous hash design. To migrate to half-path please see the migration instructions above. If the node operator does not want to migrate, it is completely fine to stay on the hash design, as it will still be fully supported.
- From v1.26.0-exp. The node will remain on the half-path design. No resync is needed between v1.26.0 and its pre-release versions—all optimizations and bugfixes are automatically applied.
Learn more
More details about the half-path and other state redesigns which we are still exploring, can be found here. Please also refer to #6331, which contains all of the changes around the half-path and more in-depth details about specific performance metrics.
Snap serving
We're excited to share that Nethermind now supports snap serving, a capability previously unique to Geth. This is a big step for the Ethereum ecosystem, offering redundancy and easing Geth's considerable responsibility in maintaining network health.
This achievement doesn't diminish Geth's critical role but reinforces our shared goal of a resilient Ethereum. We see this as an opportunity to distribute the workload, ensuring the network's strength through diversity.
This feature was previously present but required a change to the database layout for efficient performance. Nodes running on the old hash approach will not enable snap serving by default. Snap serving's performance is too low on this design and may affect the node's overall performance. If a node operator wants to enable it on hash design, there is an option --Sync.SnapServingEnabled true
, although we don't recommend it.
Important
During snap serving for other nodes, the overall performance of the node may be slightly worse. Please reach out to us on Discord with all observations so more optimizations can be discovered and applied. At the same time, it is advised to keep it enabled for the sake of network health.
Rootless and chiseled Docker image
This release introduces a new chiseled rootless Docker image for enhanced security.
These image tags have the -chiseled
suffix and run the Nethermind process on behalf of the non-root app
user with UID/GID of 64198
.
Snappy dependency removal
Nethermind no longer needs the Snappy (libsnappy-dev) to be installed on Linux.
Deprecated options
--Sync.FastBlocks
has been deprecated. It is advised to remove this option from your custom configs, environment variables, or flags passed to the client. See #6792 for more details.
Deprecated metrics
Multiple database and networking metrics are now deprecated and will be removed in the next release. These metrics follow the format:
nethermind_*_db_size
nethermind_*_db_reads
nethermind_*_db_writes
nethermind_*_disconnects
nethermind_*_received
nethermind_*_sent
They have been consolidated to labeled metrics:
nethermind_db_size{db=*}
nethermind_db_reads{db=*}
nethermind_db_writes{db=*}
nethermind_local_disconnects_total{reason=*}
nethermind_remote_disconnects_total{reason=*}
nethermind_incoming_p2p_messages{message=*}
nethermind_outgoing_p2p_messages{message=*}
Changelog
New features
- Perf/HalfPath state db key by @asdacap in #6331
- Feature/snapsync server by @asdacap in #6722
- Feature/debug get bad blocks by @kjazgar in #3838
- Add eth_blobGasPrice/eth_gasPrices; update eth_feeHistory by @flcl42 in #6563
- Add engine_getClientVersionV1 API support by @rjnrohit in #6814
- Introduce chiseled Docker image by @rubo in #6467
- Feat/native 4byte tracer by @natebeauregard in #6864
Optimism
Performance
- Speed up trie node traversal by @benaadams in #6436
- Return to NoGCRegion now runtime bug is fixed by @benaadams in #6381
- Reduce allocations of Gossip filter closures by @benaadams in #6495
- Optimize Jump Destination Analysis by @benaadams in #6502
- Reduce allocations in StorageRangesMessageSerializer by @benaadams in #6534
- Propagate pooled arrays to RlpStream by @benaadams in #6536
- Further Improve JumpDestAnalysis (x20 improvement) by @benaadams in #6554
- Avoid boxing in AccessLists by @benaadams in #6578
- Trie RlpStreams as structs by @benaadams in #6584
- Hunting allocations by @LukaszRozmej in #6601
- Hunting allocations 2 by @LukaszRozmej in #6604
- Hunting allocations 3 - introduce AccountStruct by @LukaszRozmej in #6605
- Exclude Tx Hashes when serving Blocks & apply network back pressure by @benaadams in #6636
- Allow retrieving memory traces that are unconstrained in size by @guidovranken in #6649
- Perf/fetch blockheader from peer on FCU if block so that it start beacon header sync. by @asdacap in #6650
- Perf/background task scheduler by @asdacap in #6655
- Improved single byte Rlp.DecodeByteArray by @benaadams in #6711
- Optimize RLP length calculation by @PaulusParssinen in #6729
- Faster Json RPC Dispatch by @benaadams in #6746
- Leaf value collector by @asdacap in #6795
- Perf/dont redownload downloaded code by @asdacap in #6873
Bug fixes and stability
- Fix/flush on snap finish by @asdacap in #6444
- Handling exceptions during signatures recovery by @MarekM25 in #6461
- Changed post-merge condition in MultiSyncModeSelector by @MarekM25 in #6433
- Parse BlockParameter correctly for eth_call by @benaadams in #6477
- fix byte length calculation by @tanishqjasoria in #6474
- Fix error on producing a block with multiple transaction for the same contract with block improvement by @asdacap in #6487
- Aligned GetRaw* endpoint with spec by @Demuirgos in #6494
- Increase Trie robustness for multi-readers by @benaadams in #6580
- Disconnect timed out connects by @benaadams in #6594
- fix ParityTraceActionConverter to output init on create by @LukaszRozmej in #6606
- Return BlockForRpc from debug_getBadBlocks by @flcl42 in #6612
- Fix TraceStore plugin by @LukaszRozmej in #6609
- Fix/disconnect p2p message by @ak88 in #6631
- Fix block processing hang after OldReceipts by @asdacap in #6637
- Cleanup rocksdb config and metrics by @asdacap in #6642
- Fix pruning missed nodes without caching db. by @asdacap in #6585
- Self-recovery of TxPool max capacity by @marcindsobczak in #6665
- Fix ShaMerkleTree for multithreaded access by @benaadams in #6687
- Failures > 4 for ping message alerts by @benaadams in #6704
- Update txPool worst value if removal unsuccessful by @benaadams in #6702
- Calculate Tx Hash if fast path not available by @benaadams in #6750
- Estimate when balance matches tx value too by @flcl42 in #6748
- Update rocksdb with the loading order fix by @flcl42 in #6735
- TxPool autorecover by @MarekM25 in #6789
- Bugfix/request receipts by @flcl42 in #6413
- Fix negative gas cost in debug_traceTransaction traces by @natebeauregard in #6831
- Fix/estimate gas #6390 by @ak88 in #6846
- Fix rpc module not returned on arbitrary error by @asdacap in #6842
Other changes
- Pass
readonly struct
BlockExecutionContext
viain
by @benaadams in #6469 - Json rpc more flexible string parameter parsing by @benaadams in #6486
- Fixing few typos in src/Nethermind by @fakefraud in #6508
- Do not throw IOException when file is already downloaded by @Arimionim in #6346
- Feature: Exposing Prometheus metrics to user-defined interface by @tgerring in #6528
- Update [README.md](http://readme.md/) by @oxbau in #6384
- Refactor TxReceipt to be extendable by plugins by @deffrian in #6463
- Enable Ansi color sequences for Cmd by @benaadams in #6615
- Fix typos by @vuittont60 in #6628
- Fix broken link to docs by @krauspt in #6681
- Make everything properly use ReceiptsConfig.StoreReceipts instead of … by @LukaszRozmej in #6776
- Revise validation errors by @ak88 in #6804
- Cleanup/remove effect of memory hint to write buffer and adjust some db parameters by @asdacap in #6767
- Deprecate FastBlock Flag by @obasekiosa in #6792
- Allow configuring last state to be kept by @asdacap in #6809
- Features/unified p2p message metrics by @asdacap in #6835
- Check for multiple cli arguments by @LukaszRozmej in #6861
New Contributors
- @fakefraud made their first contribution in #6508
- @Arimionim made their first contribution in #6346
- @tgerring made their first contribution in #6528
- @oxbau made their first contribution in #6384
- @vuittont60 made their first contribution in #6628
- @guidovranken made their first contribution in #6649
- @krauspt made their first contribution in #6681
- @PaulusParssinen made their first contribution in #6729
- @rjnrohit made their first contribution in #6814
- @obasekiosa made their first contribution in #6792
- @natebeauregard made their first contribution in #6831
Full Changelog: 1.25.4...1.26.0