Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 104 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@

- **Dockerized Deployment**: Simplifies the process of setting up Morph nodes using Docker containers.
- **Network Support**: Provides configurations for both Mainnet and Hoodi testnet environments.
- **Execution Client Choice**: Run the node with either **geth** (`go-ethereum`) or **reth** (`morph-reth`) as the execution client.
- **Snapshot Synchronization**: Supports synchronizing node data from snapshots to expedite the setup process.

## Prerequisites
Expand Down Expand Up @@ -67,6 +68,33 @@ Before setting up a Morph node, ensure you have the following installed:
└── data // data directory from snapshot/node
```

- **Reth uses a different snapshot** (the `*-reth-*` rows in the snapshot
table) with a different execution-client layout. Its tarball contains a
`reth-data/` tree plus the same `data/` for the node. `static-nodes.json`
is not in the snapshot; the `quickstart-*-reth-*` / `setup-snapshot-data-reth`
helpers copy it from `geth-data/` into `reth-data/` for `--trusted-peers`.
For example, if the reth snapshot folder is named `snapshot-archive-reth-20260902-1`,
move the directories into the `MORPH_HOME` directories:
```
mv ${MORPH_HOME}/snapshot-archive-reth-20260902-1/reth-data/* ${MORPH_HOME}/reth-data
mv ${MORPH_HOME}/snapshot-archive-reth-20260902-1/data/* ${MORPH_HOME}/node-data/data
```
The folder structure will be like
```
└── ${MORPH_HOME}
├── reth-data // data directory for reth
│ ├── db // from snapshot/reth-data
│ ├── static_files // from snapshot/reth-data
│ ├── rocksdb // from snapshot/reth-data
│ ├── morph // from snapshot/reth-data
│ └── static-nodes.json // copied from geth-data, parsed into --trusted-peers
└── node-data // data directory for node
├── config
│ ├── config.toml
│ └── genesis.json
└── data // data directory from snapshot/node
```


5. **Run the Node**:

Expand All @@ -84,6 +112,71 @@ Before setting up a Morph node, ensure you have the following installed:

- This command will set up and run the node based on the configurations specified in your .env file.

### Running with reth instead of geth

The node can run with **reth** (`morph-reth`) as its execution client instead of
geth. Reth uses a **separate execution-client data directory** (`${MORPH_HOME}/reth-data`)
and, importantly, a **different snapshot** than geth (see the [Snapshot Information](#snapshot-information)
table — reth snapshots are the `*-reth-*` rows). The `morph-node` (derivation) side
is identical; only the execution client and its snapshot differ.

- Start a reth-backed node with Docker Compose:

```bash
make run-reth-node # mainnet
make run-hoodi-reth-node # hoodi
```

Stop / remove:

```bash
make stop-reth-node
make rm-reth-node
```

- Or use a one-command quickstart (downloads the reth snapshot, places the data, and runs):

```bash
make quickstart-mainnet-reth-node # mainnet, Docker
make quickstart-hoodi-reth-node # hoodi, Docker
```

- **Binary mode** (build `morph-reth` from source with `cargo`, then run the binaries directly):

```bash
make build-reth-all # builds morph-reth + morphnode into ./bin
make run-reth-node-binary # mainnet
make run-hoodi-reth-node-binary # hoodi
make stop-binary # stops geth/reth/morphnode
# or one-command: make quickstart-mainnet-reth-node-binary / quickstart-hoodi-reth-node-binary
```

`build-reth` clones `morph-reth` into `../morph-reth` and checks out a pinned
tag `v$(RETH_VERSION)` (default `1.3.0`, kept in sync with the image in
`docker-compose.reth.yml`) so the binary and Docker paths run the same version.
Bump it in one place with `make set-versions RETH_VERSION=1.4.0 ...` (rewrites the
compose image tag), or build a one-off with `make build-reth RETH_VERSION=1.4.0`.

`morph-reth` reads the boot nodes from `static-nodes.json` and passes them to
`--trusted-peers` (discovery is disabled). The snapshot does **not** contain
`static-nodes.json`, so the snapshot setup copies it from `${MORPH_HOME}/geth-data/static-nodes.json`
into `${MORPH_HOME}/reth-data/`. The reth launch command used by the entrypoint is:

```bash
morph-reth node \
--chain <mainnet|hoodi> \
--datadir $RETH_DATA_DIR \
--http --http.addr 0.0.0.0 --http.port 8545 --http.corsdomain '*' \
--http.api web3,eth,txpool,net,trace \
--ws --ws.addr 0.0.0.0 --ws.port 8546 --ws.origins '*' \
--ws.api web3,eth,txpool,net,trace \
--authrpc.addr 0.0.0.0 --authrpc.port 8551 --authrpc.jwtsecret /jwt-secret.txt \
--disable-discovery --nat none \
--metrics 0.0.0.0:6060 \
--log.file.directory $LOG_DIR --log.file.filter info \
--trusted-peers $TRUSTED_PEERS # parsed from static-nodes.json
```

### Running as a validator (batch verification mode)

There is no separate validator service anymore — every node self-verifies L1 batches. The
Expand Down Expand Up @@ -114,6 +207,17 @@ There is no separate validator container anymore — both paths run the same `mo

The table below provides the node snapshot data and corresponding download URLs. Ensure `DERIVATION_START_HEIGHT`, `L1_MSG_START_HEIGHT`, and `L2_BASE_HEIGHT` in `.env`/`.env_hoodi` match the selected snapshot.

> **geth vs reth snapshots:** rows whose name contains `reth` (e.g. `snapshot-archive-reth-*`)
> are for the **reth** execution client and must be used with the `*-reth-*` make targets;
> the other rows are **geth** snapshots. The two are not interchangeable. Set
> `MAINNET_SNAPSHOT_NAME`/`HOODI_SNAPSHOT_NAME` for geth and
> `MAINNET_RETH_SNAPSHOT_NAME`/`HOODI_RETH_SNAPSHOT_NAME` for reth in the env files.
>
> Because the two clients use different snapshots, the height variables are also split:
> the geth path uses `DERIVATION_START_HEIGHT`/`L1_MSG_START_HEIGHT`/`L2_BASE_HEIGHT`, and
> the reth path uses `RETH_DERIVATION_START_HEIGHT`/`RETH_L1_MSG_START_HEIGHT`/`RETH_L2_BASE_HEIGHT`.
> Ensure each set matches the height row of its selected snapshot.

**For mainnet** (reth is currently in an internal testing phase and is not yet recommended for production use):

| Snapshot Name | Derivation Start Height | L1 Msg Start Height | L2 Base Height |
Expand Down
6 changes: 6 additions & 0 deletions hoodi/reth-data/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
# Snapshot- and runtime-generated reth data. Only static-nodes.json (parsed into
# --trusted-peers) and this file are tracked; everything else is produced by the
# reth snapshot setup or by running the node.
*
!.gitignore
!static-nodes.json
5 changes: 5 additions & 0 deletions hoodi/reth-data/static-nodes.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
[
"enode://8efa3da017d3eeb9db761e17c10121ee3ee6d258045ac4fba42549552376547f818a31e933b9dd904528aaadc9b6b457e9d1970e3cbbad42d7a0171686cbd994@13.159.40.158:30303",
"enode://884f27d218751e1f64eec36f7a5bad2bd03006d0a73b9557e36bb90847db5cb8cc2f86cb88121cecaf8599779ec088a9670fec8ee8611885591a97b52064f171@18.177.181.171:30303",
"enode://cc0a69714111d69bb6f664c06d4d8a560019259ba9828ffd5714d465bc334652354b1660b6c058c50821f790d2f76a005bf0a3c74b55cce44b7e10180130fac3@13.230.212.70:30303"
]
6 changes: 6 additions & 0 deletions mainnet/reth-data/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
# Snapshot- and runtime-generated reth data. Only static-nodes.json (parsed into
# --trusted-peers) and this file are tracked; everything else is produced by the
# reth snapshot setup or by running the node.
*
!.gitignore
!static-nodes.json
5 changes: 5 additions & 0 deletions mainnet/reth-data/static-nodes.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
[
"enode://53496aab21ab73f261551d823340b417ecd2cf69652ceba670162b990429e75c4dd6eb622dd96978d65f70c9db9964b3f477886c0b62297a51266168d367bab2@52.193.82.123:30303",
"enode://58773a8b58e70cda8d39ed7500b56f176b22c5d4faab88348a0835f333f25ae3b3a45bf7f3e9fd08245d1ff57d38d01540571c0221be2404ce93568f8472c3a0@52.197.80.227:30303",
"enode://86faa94f8221ae100c6f3aebc2f79941431ce2178f1f4374a73511230846bc26df4c336139e766668f5ba8daea56fdce74f61ecc31a2cba3788e70a2d15f5258@18.177.252.130:30303"
]
15 changes: 15 additions & 0 deletions morph-node/.env
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,21 @@ JWT_SECRET_FILE=${MORPH_HOME}/jwt-secret.txt
GETH_ENTRYPOINT_FILE=./entrypoint-geth.sh
MAINNET_SNAPSHOT_NAME=snapshot-20260701-1

## Reth execution client (alternative to geth). Reth uses a SEPARATE snapshot
## (reth-data/ tree) and a separate data directory (${RETH_HOME}/reth-data),
## but shares the same network home dir and node-data with the geth flow.
RETH_HOME=${MORPH_HOME}
RETH_CHAIN=mainnet
RETH_ENTRYPOINT_FILE=./entrypoint-reth.sh
MAINNET_RETH_SNAPSHOT_NAME=snapshot-archive-reth-20260902-1
# Reth uses a SEPARATE snapshot from geth, so it needs its own heights. These must
# match MAINNET_RETH_SNAPSHOT_NAME above (see the README snapshot table). The reth
# compose/binary paths use these instead of the shared DERIVATION_*/L1_MSG_*/L2_BASE_*
# below (which track the geth snapshot).
RETH_DERIVATION_START_HEIGHT=25885664
RETH_L1_MSG_START_HEIGHT=25880870
RETH_L2_BASE_HEIGHT=26137782

## Environment variables for the node
L1_CHAIN_ID=1
L1_ETH_RPC=https://eth.drpc.org
Expand Down
15 changes: 15 additions & 0 deletions morph-node/.env_hoodi
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,21 @@ JWT_SECRET_FILE=${MORPH_HOME}/jwt-secret.txt
GETH_ENTRYPOINT_FILE=./entrypoint-geth.sh
HOODI_SNAPSHOT_NAME=snapshot-20260630-1

## Reth execution client (alternative to geth). Reth uses a SEPARATE snapshot
## (reth-data/ tree) and a separate data directory (${RETH_HOME}/reth-data),
## but shares the same network home dir and node-data with the geth flow.
RETH_HOME=${MORPH_HOME}
RETH_CHAIN=hoodi
RETH_ENTRYPOINT_FILE=./entrypoint-reth.sh
HOODI_RETH_SNAPSHOT_NAME=snapshot-archive-reth-20260901-1
# Reth uses a SEPARATE snapshot from geth, so it needs its own heights. These must
# match HOODI_RETH_SNAPSHOT_NAME above (see the README snapshot table). The reth
# compose/binary paths use these instead of the shared DERIVATION_*/L1_MSG_*/L2_BASE_*
# below (which track the geth snapshot).
RETH_DERIVATION_START_HEIGHT=3533250
RETH_L1_MSG_START_HEIGHT=3529538
RETH_L2_BASE_HEIGHT=8346700

## Environment variables for the node
L1_CHAIN_ID=560048
L1_ETH_RPC=${your_layer1_execution_client_rpc_url}
Expand Down
Loading