Bootstrap and Genesis
The genesis block is the trust anchor for every service that joins a network. It is not signed: it simply commits to the full validator set in its header, and that set must sign every block after genesis. Because nothing signs the genesis block, it must always be obtained from a trusted source. One of the network's operators is responsible for building it from the genesis configuration. On official networks, the validators are operated by separate entities from the network operator.
The genesis block is subsequently made available for official networks at
https://genesis.<network>.miden.io
which provides an easy method to obtain this data. This is directly supported by service bootstrap commands by passing
--network testnet or --network devnet. Bootstrap commands also support passing a file directly to cover custom
networks, or if the official URLs are not trusted.
Bootstrap Flow
- Official network
- Unofficial network
The genesis block is the chain's trust root: its header commits to the full validator set, which must sign every block after genesis. Each validator operator first prints their public key and sends it to the bootstrapping operator:
miden-validator pubkey --signing-key.kms-id <validator-N-kms-key-id>
The full validator set is part of the genesis configuration, as a required top-level validators list in
genesis.toml. A configuration file without validators is rejected; only the built-in development configuration (used
when no config file is supplied) falls back to the predefined, insecure development signing key.
validators = [
"<validator-1-public-key-hex>",
"<validator-2-public-key-hex>",
"<validator-3-public-key-hex>",
]
One operator then runs genesis with the genesis configuration. Building the genesis block requires no signing key:
miden-validator genesis \
--genesis-block-directory genesis-data \
--accounts-directory accounts \
--config genesis.toml
Upload genesis-data/genesis.dat so it is served at:
https://genesis.<network>.miden.io
Every validator operator — including the one that built the genesis block — seeds their own database from the genesis block:
miden-validator bootstrap \
--data-directory validator-1-data \
--genesis genesis-data/genesis.dat
Initialize the sequencer's node storage from the hosted genesis block:
miden-node bootstrap \
--data-directory node-data \
--network testnet
Initialize the network transaction builder from the same hosted genesis block:
miden-ntx-builder bootstrap \
--data-directory ntx-builder-data \
--network testnet
For devnet, use --network devnet instead. The --network flag is shorthand for downloading the genesis block from
https://genesis.<network>.miden.io.
Each validator operator's own KMS key ID must be used when that operator starts their validator for this network.
One operator builds the genesis block; no signing key is needed. The genesis header commits to the full validator
set, taken from the top-level validators list in genesis.toml. Each validator operator prints their public key with
miden-validator pubkey --signing-key.hex <validator-N-key-hex> and sends it to the bootstrapping operator, who lists
it in the genesis configuration. The validators list is required: a configuration file without it is rejected, and
only the built-in development configuration (used when no config file is supplied) falls back to the predefined,
insecure development signing key.
validators = [
"<validator-1-public-key-hex>",
"<validator-2-public-key-hex>",
"<validator-3-public-key-hex>",
]
miden-validator genesis \
--genesis-block-directory genesis-data \
--accounts-directory accounts \
--config genesis.toml
Distribute genesis-data/genesis.dat to the validator operators, who each seed their own database from it — including
the operator who built the genesis block:
miden-validator bootstrap \
--data-directory validator-1-data \
--genesis genesis-data/genesis.dat
For unofficial networks or pre-publication testing, distribute the genesis block file directly and initialize services from that file:
miden-node bootstrap \
--data-directory node-data \
--genesis genesis-data/genesis.dat
miden-ntx-builder bootstrap \
--data-directory ntx-builder-data \
--genesis genesis-data/genesis.dat
The key each validator operator starts their validator with must match the public key committed for them in the genesis
configuration's validators list.
Storage Key Ceremony
After genesis is built, every listed validator must join one offline DKG ceremony. The ceremony creates the shared public storage key and one distinct secret share per validator. No coordinator can derive those shares.
Each operator first registers a fresh DKG identity with the validator signing key committed in genesis. One coordinator uses every signed registration to prepare the common ceremony. Every operator then creates two public dealings, checks and signs the same full transcript, and completes both rounds locally. The DKG and database bootstrap may run in either order, but both must finish before the validator starts.
All listed validators must contribute to the ceremony even when the recovery threshold is lower. If any participant drops out or any transcript differs, discard the incomplete ceremony and start a new one with fresh identities and sessions. See storage key setup for the commands and file rules.
Bootstrap takes no transaction encryption key: that key is configured separately when the validator is started, and nothing cross-checks it against the genesis block. A validator started without one falls back to a publicly known insecure default, which after bootstrap means every submission on the network is encrypted to a key anyone can read. See Validator for how to provision it.