Skip to content

Getting Started with Erigon on Ubuntu

Note: This article has been updated from Turbo-Geth (old name) to Erigon (new name)

Erigon is an Ethereum client that was originally a fork of the popular Go-Ethereum (Geth) client. It has since seen significant re-writing of the database structure, data model, and sync process enabling node operators to run “Full Archive” without needing > 4TB of storage. Work is even being done to test HDD sync (as opposed to SSD).


In this article I’m going to walk through a step by step setup of how to download, build, and execute Erigon as a service using Supervisor. I’m going to assume you’re running Ubuntu but other Linux distros should work fine/similarly. It may be possible to run on Windows, however, building and running as a service on Windows is an entirely different can of worms that I won’t get into here. If you’d rather use Systemd as opposed to Supervisor, there are other sources available.

At the time of this writing my Erigon installation consumes ~1.8TB of storage at block #14,270,062

I’m going to assume that you’re root for the duration of the setup. If you are using sudo with these commands, I recommend simply entering root environment with sudo -i otherwise you will have issues with go not being in your path.


The essentials: build-essential, supervisor, wget, and git

apt-get install -y build-essential supervisor wget git

Go Language

At the time of this writing/update the most recent Go Language version is 1.17.6. Check here.

tar -C /usr/local -xzf go1.17.7.linux-amd64.tar.gz

Now you have two choices: Make go available to all user accounts, or just add it to your path:
All Users:

ln -s /usr/local/go/bin/go /usr/local/bin/go

Just to your own profile:

echo 'export PATH=$PATH:/usr/local/go/bin' >> ~/.profile
. ~/.profile

A note about updating Go

Whenever you update Go to a new language I recommend deleting the /usr/local/go folder, and re-extracting the new version in its place. Leaving the old folder and extracing on top of it can lead to unexpected behavior with old files. Especially true when updating from 1.15 to 1.16, etc.

Isolated erigon user

Ideally we don’t want our Erigon process running as root so I’m going to create a new user account for the service to run under.

useradd -m -s /bin/bash erigon

Building Erigon

We’re going to create a “github” folder under opt where we download the repo and make, and also a “erigon” folder where we hold the binaries we build. Note that I will checkout the stable branch here!

cd /opt
mkdir erigon
mkdir github && cd github
git clone
cd erigon
git checkout stable
cp -r ./build/bin /opt/erigon/

Setting up the Services

Unlike Go-Ethereum (geth), Erigon has a separate RPC service called rpcdaemon that we also need to setup. I will setup both as Supervisor services.

First, let’s create a data directory for Erigon to work with, as the default sucks (~/.local/share/erigon). You can change this to whatever you want. I personally have a secondary SSD attached to /data so I’m going to use that. I’m also going to make the erigon user the owner of the new folder.

mkdir -p /data/erigon/datadir
chown -R erigon:erigon /data/erigon

erigon service

Next let’s create our service… use your favorite editor and create the following file:

vi /etc/supervisor/conf.d/erigon.conf

command=bash -c '/opt/erigon/bin/erigon --datadir="/data/erigon/datadir" --private.api.addr=""'

Breaking this down section by section, we’re telling Supervisor to create a service called erigon which will run the erigon executable, specifying the datadir. By default the erigon executable is going to listen only on which is fine if you run the rpcdaemon on the same system. Or you can set it to like I have done above to listen on all interfaces. Be careful adding additional flags here, as not all geth flags are supported. If you have a static IP address you could also add: --nat extip:

Next we’re telling Supervisor to run it as the erigon user we created earlier, telling it to auto start and auto restart.

The stderr and stdout lines tell Supervisor where to log the console output to and sets up log rotation. Logs can get rather big if you don’t rotate them.

stopwaitsecs=300 tells Supervisor to wait at least 5 minutes after the kill signal before forcefully shutting it down. This is probably not required for Erigon, but I got into the habit of including it with my Ethereum node processes because nothing sucks more than pre-mature killing of the process resulting in a corrupt DB.

rpcdaemon service

Now, let’s create the service for the rpcdaemon

vi /etc/supervisor/conf.d/rpcdaemon.conf 

command=bash -c '/opt/erigon/bin/rpcdaemon --datadir="/data/erigon/datadir" --private.api.addr="localhost:9090" --http.addr="" --http.port=8545 --http.vhosts="*" --http.corsdomain="*" --http.api="eth,debug,net,trace,web3,erigon" --ws'

Here we have created our second service. The important thing here is that we’re pointing rpcdaemon at the private.api.addr that erigon is listening on. Additionally, rpcdaemon can operate in a “dual mode” where it shares memory from the erigon binary, so we set --datadir to point to the datadir folder. From there we’re exposing our RPC endpoint to “all IPs” by using --http.addr="" and we’re listening on port 8545. We’ve basically disabled any host or cors checking by using ="*", we’re exposing all available methods (currently: eth,debug,net,trace,web3,erigon) and we’re also enabling WebSocket support.

The rpcdaemon doesn’t have a database to get corrupted so no need to worry about killing the process.


I assume that most people reading this are just trying to run a node inside their own network, and that some sort of firewall should be protecting their node from external connections. Otherwise, you should setup ufw or similar on your node to protect your endpoints. Of course if you’re running Erigon on your workstation or you have no reason to access it remotely you can change to and then only local connections will be accepted.

If you are running this on a cloud server and you don’t really know what you’re doing here’s a quick firewall using ufw:

# Allow SSH form anywhere so we don't get locked out
ufw allow ssh
# Allow TPC/UDP 30303 from anywhere for peering
ufw allow 30303
# Turn on the firewall
ufw enable

# If you want to allow specific IPs (e.g. to hit your RPC endpoint:
ufw allow proto tcp from to any port 8545

Let the nodling commence

systemctl enable supervisor
systemctl start supervisor
supervisorctl update

This should enable supervisor, telling it to start at startup, and it should start supervisor which in turn should start your erigon and rpcdaemon services.

You can check on the status of stuff:

# Check on the erigon service:
supervisorctl status erigon
tail -f /var/log/supervisor/erigon.err.log

# Check on the rpcdaemon status:
supervisorctl status rpcdaemon

If for some reason the services don’t start it’s probably a typo in your supervisor config files /etc/supervisor/conf.d/erigon.conf or /etc/supervisor/conf.d/rpcdaemon.conf

Once you make whatever changes you need to make to the config you reload it with this:

supervisorctl update

Updating Your Node

Updating Erigon is fairly straight forward, we simply pull the latest changes from github, run make, and restart our services.

cd /opt/github/erigon/
git pull
supervisorctl stop rpcdaemon
supervisorctl stop erigon
cp -r ./build/bin /opt/erigon/
supervisorctl start erigon
supervisorctl start rpcdaemon

I would suggest excising some caution in updating, although the Erigon team does their best to ensure that the stable branch of Erigon is safe and stable, it’s always best to be safe. Also, some updates might not be reversible, as the database model can change, when that happens, the startup of your node after update will include a migration of data (no need to re-sync). However, if you want to downgrade, you would likely have to re-sync.

Published inTech


  1. Birdman Birdman

    After following the above instructions (thanks for this blog post), I got the following error (‘EROR’):
    [EROR] [12-07|12:02:36.479] Erigon startup err=”could not create listener: listen tcp bind: address already in use, addr=localhost:9090″

    It seemed it was conflicting with Prometheus, also on port 9091. I changed ‘–private.api.addr’ in both config files to port 9091 and that seems to enable creating the listener.

  2. Shatz Shatz

    Great tutorial… Although when you run “supervisorctl status erigon” you get
    “erigon FATAL Exited too quickly (process log may have details)” Log reports “bash: /opt/erigon/build/bin/erigon: No such file or directory” and it does exit.

    Can’t figure out the issue.

    • Error says: `/opt/erigon/build/bin/erigon` can’t be found, figure out why it can’t find the binary, you probably missed a step.

      • luominx luominx

        The problem seems to be in the line: cp -r ./build/bin /opt/erigon/

        It creates a copy of the binaries to /opt/erigon/bin and not /opt/erigon/build/bin as it is later required in the start configuration files for the supervisor.

        I changed the path in both configruation files to /opt/erigon/bin/erigon and /opt/erigon/bin/rpcdaemon.
        Now it works.

Leave a Reply

Your email address will not be published.