Introducing the Kona-Node: A Rust-Powered Leap for the OP Stack

Today marks a thrilling milestone for the OP Stack ecosystem: the first public release of kona-node
, our modular, high-performance rollup node built entirely in Rust. If you're building scalable Layer 2 solutions on Ethereum, this is your cue to get excited.
In this post, we'll break down what makes kona-node
special, how it compares to the reference op-node
, and how you can start using it yourself.
What is the Kona Node?
Drawing from our docs at https://rollup.yoga, kona-node
is a spec-compliant implementation of an OP Stack rollup node. It's part of the broader Kona suite, which includes low-level types, portable no_std
components, and services optimized for security and performance.
Key highlights for kona-node
include Rust's inherent memory safety, minimal resource footprint, and support for multiple proof backends like FPVM, SP1, Risc0, and more. This design emphasizes customizability through composable crates, making it extensible for diverse verifiable environments.
With just ~8K lines of code, kona-node
delivers robust functionality, including fault proof capabilities. For context, the full Kona client clocks in at ~3K LoC, showcasing our focus on lean, efficient engineering.
How Does It Differ from op-node?
While op-node
(the original Go-based implementation) has been a reliable workhorse for Optimism's rollups, kona-node
brings a fresh perspective, leveraging open source Rust crates.
The kona-node
implementation repurposes the same no_std
rust crates used for the kona-proof
- a Rust fault proof implementation. This includes many other foundational crates as well including protocol types, rollup configurations as part of the Superchain registry, and hardforks.
Design-wise, kona-node
adopts an actor-based architecture via the RollupNodeService
trait, enabling message-passing concurrency with actors like DerivationActor
(for L2 payload derivation) and EngineActor
(for execution layer interactions). This modular setup enhances composability and extensibility, contrasting with op-node
's centralized event system structure.
The result is better developer legibility, resource efficiency, and quick integration of new features.
Running Kona-Node: Dive into Our Verbose Docs
Getting started is straightforward, thanks to detailed documentation at https://rollup.yoga. Our guides are packed with step-by-step instructions, covering everything from setup to advanced configurations.
Launch the node for the Base chain:
kona-node --chain base --port 8545
Install via Cargo:
cargo install kona-node
For deeper customization, check the flags for L2 chain IDs, P2P networking, or supervisor integration. Our docs include troubleshooting tips and best practices to ensure a smooth run.
Below is a screenshot of https://node.rollup.yoga, where we are running a live kona-node
against OP Sepolia with op-reth
. Go visit the site and see for yourself!

Composability as a First Class Citizen
kona-node
's composability shines through its modular crates, such as kona-derive
for derivation pipelines and extensible traits for integrating components like data sources and attribute builders. These allow seamless extension for custom rollups or provers (e.g., FPVM, SP1, Risc0).
Here's an example using kona-derive
, demonstrating how to compose a DerivationPipeline
using the PipelineBuilder
for L2 input derivation from L1 data:
// Construct the derivation pipeline dynamically.
let pipeline = PipelineBuilder::new()
.rollup_config(cfg)
.dap_source(dap)
.l2_chain_provider(l2_chain_provider)
.chain_provider(chain_provider)
.builder(attributes)
.origin(l1_origin)
.build();
The next snippet shows a simplified example of implementing the RollupNodeService
trait for a custom validator node, based on the kona-node-service
’s API. This demonstrates composing custom actors and pipelines:
use kona_node_service::{RollupNodeService, NodeActor, NodeMode, Pipeline};
use kona_derive::PipelineBuilder; // Example dependency
use std::sync::Arc;
// Define custom types (placeholders; implement as needed)
struct CustomDAWatcher; // Implements NodeActor
struct CustomDerivationPipeline; // Implements Pipeline + SignalReceiver
struct CustomDerivationActor; // Implements NodeActor
struct CustomEngineActor; // Implements NodeActor
// ... similarly for other actors
impl RollupNodeService for MyCustomNode {
type DataAvailabilityWatcher = CustomDAWatcher;
type DerivationPipeline = CustomDerivationPipeline;
type DerivationActor = CustomDerivationActor;
type EngineActor = CustomEngineActor;
// Define other associated types (e.g., NetworkActor, SupervisorExt, etc.)
fn mode(&self) -> NodeMode {
NodeMode::Validator
}
fn da_watcher_builder(&self) -> <Self::DataAvailabilityWatcher as NodeActor>::Builder {
// Return a builder for your custom DA watcher
CustomDAWatcher::builder(/* config */)
}
fn derivation_builder(&self) -> <Self::DerivationActor as NodeActor>::Builder {
// Compose with a custom pipeline builder
PipelineBuilder::new(/* rollup config */).build()
}
fn engine_builder(&self) -> <Self::EngineActor as NodeActor>::Builder {
CustomEngineActor::builder(/* L2 engine URL, etc. */)
}
// Implement other builder methods (e.g., network_builder, rpc_builder)
}
// Usage: Create and run the custom node
let custom_node = MyCustomNode { /* fields */ };
custom_node.run().await; // Assuming a run method; adapt per actual API
Since the node wiring and execution logic is already abstracted away, only the actor builders need to be defined. That way, the trait itself will use its abstractions to spin up the node.
Why This Matters
With kona-node
, we're pushing the OP Stack toward greater decentralization and efficiency. Further, since the rust crates are modular and published, they can be composed however users like. There’s no restriction on how to extend the rollup node yourself. Use, adapt, improve the kona-node
however you wish - as a library or an application.
Ready to try it? Head to https://rollup.yoga, run a node yourself, and come contribute to the kona repository!