Ethereum Mainnet & Kovan Nodes on Same Machine
Tags: ethereum, kovan, parity, ubuntu
Published: 2017-12-31 13:32:56

---
title: Ethereum Mainnet & Kovan Nodes on Same Machine
published: true
description: I couldn't find a guide for a server setup with multiple ethereum instances (for different chains), so I wrote one.
tags: ethereum,kovan,parity,ubuntu
cover_image: https://thepracticaldev.s3.amazonaws.com/i/3oe1f0vdk5jz295u1n4j.png
---
# Introduction
Right after installing an Ethereum node on my developer machine, the initial sync caused it to run wild, pushing the fan to its limit, and in the end I had several gigabytes of blockchain data on my tiny SSD. Sounds familiar? Then this guide is for you.

You don't need to run the node on your development machine directly, any computer in your network can do the job. So I've chosen my NAS, which is running Ubuntu 17.10 and has enough space on its HDD.

And since we're developers, it is a good idea not only to have access to the mainnet, but also to one of the test nets. So I will setup an additional parity instance for the kovan chain. 
 
# Installation
Please tell me that I was too dumb to find a PPA repo for [parity](http://parity.io) yesterday. I cannot believe that it doesn't exist. Anyway, the parity installation instructions tell you to download a .deb file, so here we go with the beta release, which is 1.8.x at the time of writing:
```bash
wget "https://d1h4xl4cr1h0mo.cloudfront.net/beta-release/x86_64-unknown-linux-gnu/parity" -O parity.deb
sudo dpkg -i parity.deb
```
There's also a download option with curl/bash script, but since you never know what it does I prefer to download and install a .deb file.

# Ethereum Setup
We will need an Ethereum account in each instance for interacting with contracts and such. I don't want these accounts (and their keys) in a system directory, since they are probably coupled to my user (I will refer to him as *hans* in this article). I also want to keep open the option of adding more instances that might use accounts of other users. So let's create some directories in my user's home directory:
```bash
mkdir ~/ethereum
mkdir ~/ethereum/mainnet
mkdir ~/ethereum/kovan
```
And wow it's time to create an account in each chain:
```bash
parity account new -d ~/ethereum/mainnet
parity account new -d ~/ethereum/kovan
```
If you want to import existing accounts instead, you can follow the instruction in the official [wiki](https://github.com/ethereum/go-ethereum/wiki/Managing-your-accounts).

# System Setup
Let's start with the directory for our config files and our log files.
```bash
sudo mkdir /etc/ethereum
sudo touch /var/log/parity-mainnet.log
sudo touch /var/log/parity-kovan.log
sudo chown hans /var/log/parity-*.log
```
Now put the config files for our chains into /etc/systemd. You will need sudo permissions for this file and the 3 other files in this paragraph to come. Let's start with **/etc/ethereum/config-mainnet.toml**.
```
[parity]
chain = "mainnet"
base_path = "/home/hans/ethereum/mainnet"
identity = ""

[account]
unlock = ["0x6e6dbb24dd98dd37c41a9964a766e5eb64352d9c"]
password = ["/home/hans/ethereum/mainnet/password"]

[ui]
disable = false
port = 8180
interface = "all"

[network]
port = 30303
reserved_only = false
#reserved_peers = "/etc/parity/mainnetpeers.txt"

[rpc]
disable = false
port = 8545
interface = "all"
apis = ["web3", "eth", "net", "parity", "traces", "rpc", "secretstore"]

[websockets]
disable = false
port = 8546
interface = "all"
apis = ["web3", "eth", "net", "parity", "traces", "rpc", "secretstore"]

[ipc]
disable = false
apis = ["web3", "eth", "net", "parity", "parity_accounts", "personal", "traces", "rpc", "secretstore"]

[dapps]
disable = false

[secretstore]
http_interface = "local"
http_port = 8082
interface = "local"
port = 8083

[ipfs]
enable = false
port = 5001
interface = "all"

[misc]
log_file = "/var/log/parity-mainnet.log"
```
And here's **/etc/ethereum/config-kovan.toml**.
```
[parity]
chain = "kovan"
base_path = "/home/hans/ethereum/kovan"
identity = ""

[account]
unlock = ["0xaa125f607bb23f41c0c45c27eca820f2b133d1b6"]
password = ["/home/hans/ethereum/kovan/password"]

[ui]
disable = false
port = 18180
interface = "all"

[network]
port = 30304
reserved_only = false
#reserved_peers = "/etc/parity/kovanpeers.txt"

[rpc]
disable = false
port = 18545
interface = "all"
apis = ["web3", "eth", "net", "parity", "traces", "rpc", "secretstore"]

[websockets]
disable = false
port = 18546
interface = "all"
apis = ["web3", "eth", "net", "parity", "traces", "rpc", "secretstore"]

[ipc]
disable = false
apis = ["web3", "eth", "net", "parity", "parity_accounts", "personal", "traces", "rpc", "secretstore"]

[dapps]
disable = false

[secretstore]
http_interface = "local"
http_port = 18082
interface = "local"
port = 18083

[ipfs]
enable = false
port = 15001
interface = "all"

[misc]
log_file = "/var/log/parity-kovan.log"
```

Then we need a systemd config file for each instance, so that the system will start parity at boot time (but don't worry, the processes will run under your user account). Let's start with mainnet again, the file name is **/etc/systemd/system/parity-mainnet.service**.
```
[Unit]
Description=Parity Mainnet Daemon
After=network.target

[Service]
# run as root, set base_path in config.toml
ExecStart=/usr/bin/parity --config /etc/parity/config-mainnet.toml
# To run as user, comment out above and uncomment below, fill in user and group
# picks up users default config.toml in $HOME/.local/share/io.parity.ethereum/
User=hans
# Group=groupname
# ExecStart=/usr/bin/parity
Restart=on-failure
Nice=15

# Specifies which signal to use when killing a service. Defaults to SIGTERM.
# SIGHUP gives parity time to exit cleanly before SIGKILL (default 90s)
KillSignal=SIGHUP

[Install]
WantedBy=multi-user.target
```

And here comes **/etc/systemd/system/parity-kovan.service**.
```
[Unit]
Description=Parity Kovan Daemon
After=network.target

[Service]
# run as root, set base_path in config.toml
ExecStart=/usr/bin/parity --config /etc/parity/config-kovan.toml
# To run as user, comment out above and uncomment below, fill in user and group
# picks up users default config.toml in $HOME/.local/share/io.parity.ethereum/
User=hans
# Group=groupname
# ExecStart=/usr/bin/parity
Restart=on-failure
Nice=15

# Specifies which signal to use when killing a service. Defaults to SIGTERM.
# SIGHUP gives parity time to exit cleanly before SIGKILL (default 90s)
KillSignal=SIGHUP

[Install]
WantedBy=multi-user.target
```
You can check if systemd has found your new services with the following command:
```bash
systemctl list-units parity*
```

# Test Run
We're ready for a test ride. Just start an instance in your shell (as your user) with one of the config files we just created:
```bash
parity --config /etc/parity/config-mainnet.toml
```
You should see some information and after some seconds the sync process will begin, printing a new status line every few seconds. If everything's fine press Ctrl+c to stop the test run.

# Starting & Enabling the Service
First we start the services, then we enable autostart at boot time:
```bash
sudo systemctl start parity-mainnet
sudo systemctl start parity-kovan
sudo systemctl enable parity-mainnet
sudo systemctl enable parity-kovan
```
If everything went fine, you will probably see your shell becoming less responsive. I tried to minimise this effect by giving the parity processes a low priority by setting the nice level to 15. My suggestion for the nice level in general is: since you always want the system to be responsive, never give your user processes a higher priority (i.e. a negative number). A nice level of 15 is pretty low. It can go down as low as 20. However setting the nice level to 20 might not help much, because the load that is caused by the initial (warp) sync of the chains spawns quite a lot of threads. The load on my dual core machine goes up to 8 or 9 during this task. [Here](https://github.com/paritytech/parity/issues/4940) is a more detailed explanation of that problem, which is being worked on, but Parity 1.8.x still comes with RocksDB, so for now we have to live with this load and a decreased responsiveness of the shell. It will get better after the initial sync is over.

# Port Info
You might wonder about the ports I've chosen. Here's my reasoning:

- 30303 is the default ethereum port, so mainnet will use it
- 30304 is not used by any other module, so kovan will use it

The rpc and http ports (8xxx) can not follow the same logic, because some of the default values are consecutive. So here we will use...

- 8xxx for mainnet (8180 for ui, 8545 for rpc, 8546 for websockets, ...)
- 18xxx for kovan (18180 for ui, 18545 for rpc, 18546 for websockets, ...)


<br/>
**UPDATE 2018-01-20**
systemd: WantedBy=multi-user.target instead of default.target