The Hyperledger suite of products has been developed over the years to become the multiple industry standard for enterprise blockchain utilization.
In this post we will cover how to run a four-validator private network on Hyperledger Besu. We'll start by setting up the dev-environment, install Besu, and use IBFT 2.0 (Proof-of-authority) to create the private network.
Set up environment
Install HomeBrew
$ sudo apt-get install build-essential curl file git $ /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/master/install.sh)" $ test -d ~/.linuxbrew && eval $(~/.linuxbrew/bin/brew shellenv) $ test -d /home/linuxbrew/.linuxbrew && eval $(/home/linuxbrew/.linuxbrew/bin/brew shellenv) $ test -r ~/.bash_profile && echo eval" ($(brew --prefix)/bin/brew shellenv)" >>~/.bash_profile $ echo "eval $($(brew --prefix)/bin/brew shellenv)" >>~/.profile
Install Java JDK
$ sudo apt install openjdk-11-jdk $ export JAVA_HOME=/usr/lib/jvm/java-8-openjdk-amd64 $ echo $JAVA_HOME $ export PATH=$PATH:$JAVA_HOME/bin $ echo $PATH $ java -version
Install Hyperledger Besu using Homebrew
$ brew tap hyperledger/besu $ brew install hyperledger/besu/besu
Create a Private Network using the IBFT 2.0
Create Directories
IBFT-Network/ ├── Node-1 │ ├── data ├── Node-2 │ ├── data ├── Node-3 │ ├── data └── Node-4 ├── data
Create a configuration file ibftConfigFile.json
{ "genesis": { "config": { "chainId": 2018, "muirglacierblock": 0, "ibft2": { "blockperiodseconds": 2, "epochlength": 30000, "requesttimeoutseconds": 4 } }, "nonce": "0x0", "timestamp": "0x58ee40ba", "gasLimit": "0x47b760", "difficulty": "0x1", "mixHash": "0x63746963616c2062797a616e74696e65206661756c7420746f6c6572616e6365", "coinbase": "0x0000000000000000000000000000000000000000", "alloc": { "fe3b557e8fb62b89f4916b721be55ceb828dbd73": { "privateKey": "8f2a55949038a9610f50fb23b5883af3b4ecb3c3bb792cbcefbd1542c692be63", "comment": "private key and this comment are ignored. In a real chain, the private key should NOT be stored", "balance": "0xad78ebc5ac6200000" }, "627306090abaB3A6e1400e9345bC60c78a8BEf57": { "privateKey": "c87509a1c067bbde78beb793e6fa76530b6382a4c0241e5e4a9ec0a0f44dc0d3", "comment": "private key and this comment are ignored. In a real chain, the private key should NOT be stored", "balance": "90000000000000000000000" }, "f17f52151EbEF6C7334FAD080c5704D77216b732": { "privateKey": "ae6ae8e5ccbfb04590405997ee2d52d2b330726137b875053c36d94e974d162f", "comment": "private key and this comment are ignored. In a real chain, the private key should NOT be stored", "balance": "90000000000000000000000" } } }, "blockchain": { "nodes": { "generate": true, "count": 4 } } }
Generate node keys and a genesis file
besu operator generate-blockchain-config --config-file=ibftConfigFile.json --to=networkFiles --private-key-file-name=key
Copy the genesis file, genesis.json
to the IBFT-Network
directory.
Copy the node private keys to the node directory. For each node, copy the key
files to the data
directory for each node.
IBFT-Network/ ├── genesis.json ├── Node-1 │ ├── data │ │ ├── key │ │ ├── key.pub ├── Node-2 │ ├── data │ │ ├── key │ │ ├── key.pub ├── Node-3 │ ├── data │ │ ├── key │ │ ├── key.pub ├── Node-4 │ ├── data │ │ ├── key │ │ ├── key.pub
Start Node-1
as the bootnode
besu --data-path=data --genesis-file=../genesis.json --rpc-http-enabled --rpc-http-api=ETH,NET,IBFT --host-allowlist="*" --rpc-http-cors-origins="all"
When the node starts, copy the enode URL
which we will use
to specify Node-1 as the bootnode for the next steps.
Start Node-2
besu --data-path=data --genesis-file=../genesis.json --bootnodes=--p2p-port=30304 --rpc-http-enabled --rpc-http-api=ETH,NET,IBFT --host-allowlist="*" --rpc-http-cors-origins="all" --rpc-http-port=8546
Start Node-3
besu --data-path=data --genesis-file=../genesis.json --bootnodes=--p2p-port=30305 --rpc-http-enabled --rpc-http-api=ETH,NET,IBFT --host-allowlist="*" --rpc-http-cors-origins="all" --rpc-http-port=8547
Start Node-4
besu --data-path=data --genesis-file=../genesis.json --bootnodes=--p2p-port=30306 --rpc-http-enabled --rpc-http-api=ETH,NET,IBFT --host-allowlist="*" --rpc-http-cors-origins="all" --rpc-http-port=8548
Confirm the Private Network is working
curl -X POST --data '{"jsonrpc":"2.0","method":"ibft_getValidatorsByBlockNumber","params":["latest"], "id":1}' localhost:8545
The result displays the four validators:
{ "jsonrpc" : "2.0", "id" : 1, "result" : [ "0x1e326b6da177ede2d3eb6d7247bd9f6901d40234", "0x4aaac297fefe4466ebcb0b23ab90c5f466b11556", "0xa267ead2e91e1673e0943b925176b51d9cd4f6d2", "0xe3e680bc0ff485d1d415a384721f19e0db65fea7" ] }
In these simple to follow steps you've created a private network that can send transactions over the Ethereum Network. To test this out, you can use this guide on sending transactions with MetaMask.
Besides its high-performance transaction processing capacity, with Hyperledger Besu entreprises can leverage more benefits including:
- Secure application (Dapp) development,
- Enterprise privacy and permissioning,
- Ether mining, & smart contract development.
Additionally, Besu also supports tools like Truffle
, Remix
,
Web3j
and JSON-RPC API methods such as eth
, web3
,
debug
, and miner
.