v3.0 Upgrade Guide - BareMetal / VM

ARK v3.0 is a major update not backward compatible with v2.7.

Concern Difficulty Description
Time HIGH upgrading to v3.0 requires new configuration files and database migrations.
Complexity HIGH a full overhaul of the internals and plugin system, which makes previous modifications incompatible.
Risk HIGH v3.0 is not backward compatible with v2.x releases as it includes a full overhaul of the internals and a new P2P server.

Upgrade Steps

Upgrading from v2.7 to v3.0 is relatively straightforward if you follow the instructions. Even though we try to ensure backward compatibility (BC) as much as possible, sometimes it is not possible or very complicated to avoid it and still create an excellent solution to a problem.


DANGER: Upgrading a complex software project always comes at the risk of breaking something, so make sure you have a backup.


After upgrading, check that your application still works as expected and that no plugins are broken. See the following notes on which changes to consider when upgrading from one version to another.


DANGER: Do NOT run any of the mentioned commands with sudo unless explicitly stated.


Check what node version you have currently installed by running node -v. If this shows a version below 14, you will have to update this before proceeding with the installation.

To do this, run the following commands:

1sudo sed -i s/node_11/node_14/ /etc/apt/sources.list.d/nodesource.list
2sudo sed -i s/node_12/node_14/ /etc/apt/sources.list.d/nodesource.list
3sudo apt-get update && sudo apt-get upgrade

When finished, you should see version 14 installed when you run node -v again!

Step 1: Database Migration Script

Use wget to fetch the v3-migrations.sql script.

1wget -N https://snapshots.ark.io/v3-migrations.sql

Step 2: Apply the iptables script


WARNING: Using the iptables script is highly recommended. Don’t skip this unless required by your system’s architecture and/or you’re aware of the security implications.

The iptables script uses standard firewall tools to rate-limit certain connections.


  • Parallel/simultaneous P2P connections are restricted to a total of 10 per IP address; this number can be adjusted using the P2P_GLOBAL_CONN script variable.
  • Global connections are limited to 4 NEW connections per 30-second interval.

Running the Script:

Download and execute the iptables script using the following commands:

1wget -N https://raw.githubusercontent.com/ArkEcosystem/core/master/scripts/v3-iptables.sh
2bash ./v3-iptables.sh start

Creating a cron job:

Because the filtering initiated by the iptables script does not persist after a system reboot, you should also consider adding the script to a cron job.

  1. edit the crontab file:

    1crontab -e
  2. add the following line to the end of the crontab file:

    1@reboot bash ~/v3-iptables.sh start
  3. save the changes and exit (e.g. ctrl + x).

  4. apply the permissions:

    1sudo bash -c "echo \"$USER ALL=(ALL) NOPASSWD:/sbin/iptables\" >> /etc/sudoers"


Failing to apply permissions will prevent the iptables script from executing after a system reboot.

Step 3: Update & Start Core


DANGER: The commands below will remove and reset your configuration files in ~/.config/ark-core/mainnet.


Please backup any configuration files you may need later, such as your delegate.json, plugin.js & .env files.

  1. Ensure that the database migration script is in your current directory–where you created the v3-migrations.sql file.

  2. Adapt the psql command with your user and database using the following commands:

    (the default DB password is password)

    1pm2 stop all
    1psql -U ark -h -d ark_mainnet -f v3-migrations.sql
    1ark update
  3. If applicable*, backup the delegate.json file:

    1cp ~/.config/ark-core/mainnet/delegates.json ~/delegate.json.backup
  4. Publish the updated configuration:

    1rm -rf ~/.config/ark-core/ && ark config:publish --token=ark --network=mainnet --reset
  5. If applicable*, restore the backed-up delegate.json file:

    1cp ~/delegate.json.backup ~/.config/ark-core/mainnet/delegates.json
  6. If applicable*, re-apply any changes made to your plugins.js or .env files.

  7. Upgrade yarn’s global packages:

    1yarn global upgrade
  8. Start Core using pm2:

    1pm2 start all


In your logs, you may see repeat messages about connecting to your database, such as Connecting to database: ark_mainnet. This is due to the database migration and can take up to 1 hour to complete depending on your server hardware.


Each run-mode (core, relay, and forger) now contains its own configuration for plugins. This configuration file can be located here: ~/.config/ark-core/mainnet/app.json.

Reporting Problems

If you happen to experience any issues, please open an issue with a detailed description of the problem, steps to reproduce it, and info about your environment.

API Changes

‘POST /search’ Endpoints Removed

All POST /search endpoints have been removed in favor of using the main index endpoint with URL parameters (e.g. GET /transactions). All main index endpoints have been improved to allow searching (see the API improvements below).

Standardized Wallet Response Format

Wallet endpoints now return a wallet object following this format:

2 "address",
3 "publicKey",
4 "balance",
5 "nonce",
6 "attributes": {
7 "delegate": {
8 "username",
9 "resigned", // this attribute will only be set if the delegate has resigned
10 // other delegate attributes
11 },
12 "vote",
13 "secondPublicKey",
14 "multiSignature",
15 }

As a result, getting wallets based on a specific attribute requires using the full attribute path.

GET /wallets?attributes.delegate.username=mydelegate


Note: isDelegate no longer exists in the wallet response**. To determine if the wallet is a delegate, check for the existence of attributes.delegate and that attributes.delegate.resigned is either non-existent or false.

‘addresses’ Parameter Removed

The addresses parameter was previously used to search for multiple addresses at the same time. This parameter is now deprecated in favor of using the address parameter.

GET /transactions?address=AXGc1bvU3g3rHmx9WVkUUHLA6gbzh8La7V,AVLPrtx669XgvervE6A594poB613HG3mSM

API improvements

Filter by Any Field

You can now filter by any field returned in the API response.

For example, GET /delegates now returns:

2 "username": "protokol1",
3 "address": "ATKegnoyu9Fkej5FxiJ3biup8xv8zM34M3",
4 "publicKey": "033f6d89ad9f3e6dfb8cfb4f2d7fca7adeb6db15c282c113d0452238293bb50046",
5 "votes": "302776200010000",
6 "rank": 1,
7 "isResigned": false,
8 "blocks": {
9 "produced": 13886,
10 "last": {
11 "id": "9630922981846498992",
12 "height": 1150380,
13 "timestamp": {
14 "epoch": 112045656,
15 "unix": 1602146856,
16 "human": "2020-10-08T08:47:36.000Z"
17 }
18 }
19 },
20 "production": {
21 "approval": 2.42
22 },
23 "forged": {
24 "fees": "10000000",
25 "rewards": "2777200000000",
26 "total": "2777210000000"
27 }

By examining the above response, we find that API queries allow filtering by any field.

For example:

  • GET /delegates?isResigned=true
  • GET /delegates?blocks.produced=13886

Combining Different Fields

We also see that combining different fields (AND) is permitted.

GET /delegates?isResigned=true&blocks.produced=0

Filtering By a Set of Values

Filtering by a set of comma-separated values for one field (OR) is also permitted.

GET /delegates?username=protokol1,protokol2

Chaining Multiple Fields

We can also chain multiple fields.

GET /delegates?username=protokol1,protokol2&isResigned=false

‘orderBy’ Any Field

Additionally, we can order any field using the orderBy parameter.

GET /delegates?orderBy=rank:desc


The format is field:asc|desc depending on whether you want to order by ascending or descending.

Combining Filters

Finally, we can combine all of the previously discussed filters in one call.

GET /delegates?isResigned=false&orderBy=rank:asc

Last updated 2 years ago
Edit Page