Настройка полной ноды на базе VPS с предустановленной ОС Ubuntu 16/18


  • Reward

    Всем привет.

    13 декабря призошло отличное событие для Vite комьюнити. Стартовала программа по стимулированию пользователей запускать Vite full nodes (полных нод) для роста экосистемы Vite. Кратко можно почитать о том, что это собой представляет можно здесь: https://medium.com/@Enthusiast1/программа-стимулирования-полных-нод-8647692f9ae7

    Официальная инструкция по установке с примерами для Ubuntu, Mac, Windows достаточно простая:
    https://vite.wiki/tutorial/node/install.html#full-node-reward
    Статья для Windows
    https://snapsecure.network/beginners-guide-to-installing-and-operating-a-vite-sbp

    Ресурсы, которые мы будем использовать:

    Качаем последнюю версию софта
    https://github.com/vitelabs/go-vite/releases

    Смотрим состояние вашей полной ноды
    https://explorer.vite.net/FullNode

    Добавляем свой адрес и смотрим профит
    https://reward.vite.net/?language=en#/node

    Сразу оговорюсь, что я не сисадмин. Если вам не нравится отсутсвие sudo практически в каждой команде, то можете смело пропускать статью. Все представленное ниже - результат личного опыта с применением на практике. Надеюсь статья поможем всем тем, кто хочет поучаствовать в данной программе, но не может ввиду отсутсвия опыта.

    Собственно остановимся на ubuntu версии. В ходе работы с полной нодой возникли следующие вопросы:

    1. Выбор конфигурации ПК
    2. Установка и настройка
    3. Обеспечение бесперебойной работы
    4. Обновление.

    1. Выбор конфигурации ПК
    Так как это тестовая сеть, то возможно требования к системе изменятся при запуске мейннета. На текущий момент мне было интересно найти наиболее дешевый, с точки зрения помесячной оплаты, и рабочий на 99% вариант. Я выбирал арендуемый VPS как самый просто вариант.

    Данные сети будут загружены на наш сервер в ходе синхронизации. По большому счету наибольшая нагрузка ложится во время этой самой синхронизации (будь-то первая настройка или восстановление работ после простоя). Хорошим вариантом будет выбор конфигурации от 3 Gb RAM + 1 CPU (~15$). Но мы не ищем легких путей. Самая слабая конфигурация, которую я смог выбрать, с 1 CPU (~2,2GHz) и RAM от 1Gb в такой обстановке себя чувствует на текущий момент достаточно хорошо и обошлась в 5$/месяц. Достаточно, чтобы потестировать. В ходе работы CPU используется не особо активно, но вот RAM может незаметно закончится и все несистемные процессы будут остановлены, в том числе и gvite. По этому больше RAM = нет подобных проблем.

    2. Предварительная настройка VPS
    На текущий момент большинство хостинг сервисов предлагают VPS с уже предустановленой системой. Конечному пользователю нужно только выбрать версию системы, несколько настроек и нажать кнопку покупки/создания. На выходе спустя пару минут мы получаем уже готовый VPS к эксплуатации.

    Добавление SSH ключей, настройку фаерволов на определенные порты я не буду рассматривать. Для нашей работы мы сделаем по простому - обезопасим наш SSH доступ на простом, но ефективном уровне.

    Первичная настройка VPS

    Мы выбрали простую конфигурацию, нажали кнопку создать VPS, на почту пришло письмо с деталями (IP, логин\пароль). Что дальше? Качаем putty клиент с https://www.putty.org
    По умолчанию у нас будет доступ только на root-юзера. Для безопасности создадим нового юзера, дадим ему sudo права, чтобы можно было выполнять программы от имени root. Можно поступить проще и использовать его только для входа с последующим переключением на root через команду su.
    Наши следующие действия:

    1. Создаем юзера, обновляем пакеты на вашем VPS
    2. Меняем порт по умолчанию для доступа по SSH
    3. Запрещаем возможность логиниться по SSH с помощью root-юзера
    4. Устанавливаем сервис, блокирующий IP-адреса, с которых пытаются делать подбор пароля к нашему VPS

    Подключаемся к нашему VPS

    ssh root@ip_addr_here
    

    Создадим юзера gvite007 (можно выбрать любое имя)

    adduser gvite007
    

    Вводим пароль, подтверждаем, данные по умолчанию подтверждаем нажатием ENTER

    Даем данному юзеру sudo права.

    usermod -a -G sudo gvite007
    

    Перезагружаем VPS.

    Для обновления пакетов необходимы права root. Если вы используете gvite007 юзера, то добавляйте в начале команду sudo. Можно переключиться на root-юзера через su.
    Из дополнительных утилит я предпочитаю дополнительно устанавливать mc (midnight commander), htop(аналог top), ntpdate(программа-демон для синхронизации времени), fail2ban (для блокировки IP)

    apt-get update
    apt-get install -y mc
    apt-get install htop
    apt-get install -y ntp
    apt-get install ntpdate
    service ntp stop
    ntpdate pool.ntp.org
    service ntp start
    

    Я предпочитаю встроенный в mc редактор файлов mcedit вместо nano (далее его буду указывать в тексте). Выбрать нужный редактор можно командой:

    update-alternatives --config editor
    

    Меняем порт по умолчанию для доступа по SSH. Для этого редактируем файл /etc/ssh/sshd_config

    mcedit /etc/ssh/sshd_config
    

    Ищем значение Port 22 и меняем его на любое из диапазона 49152 - 65535, например Port 60000
    Далее ищем строчку ‘PermitRootLogin yes’ и меняем на ‘PermitRootLogin no’.

    Теперь для подключения мы будем использовать 60000 порт, ssh подключение с помощью юзера root запрещено.

    Занести изменения в файл еще можно автоматически командами

    sed -i 's/Port\ 22/Port\ 60000/g' /etc/ssh/sshd_config
    sed -i 's/PermitRootLogin\ yes/PermitRootLogin\ no/g' /etc/ssh/sshd_config
    

    Перезагружаем сервис ssh

    service ssh restart
    

    После такой конфигурации чтобы залогиниться на сервер нужно будет выполнить команды:

    ssh gvite007@ip_addr -p 60000
    

    И далее уже, как писал ранее, использовать либо sudo, либо переключится на root пользователя через команду su

    Устанавливаем fail2ban

    apt-get install -y fail2ban
    
    cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.local
    
    mcedit /etc/fail2ban/jail.local
    

    Ищем строчки port = ssh и заменяем на port = 60000

    Перезапускаем сервис и проверяем, что он запустился нормально, посмотрев лог-файл

    service fail2ban restart
    tail /var/log/fail2ban.log
    

    Можно посмотреть активны ли безопасности политики на нашем фаерволе

    iptables -L
    

    Настройка Swap файла

    VPS, предоставляем сервисами практически всегда идут с отключенным Swap(файлом подкачки). Для слабой конфигурации его отсутствие будет довольно критичным из-за постоянной нехватки памяти. Swap не рекомендуют включать если у вас используется SSD-диск.
    О том, что такое Swap и детальном описании шагов можно почитать здесь:
    https://www.digitalocean.com/community/tutorials/how-to-add-swap-space-on-ubuntu-16-04

    Пример ниже применался для VPS с 1Gb RAM

    Проверяем включен ли Swap

    swapon --show
    free -h
    

    Проверяем свободное место

    df -h
    

    Создаем и делаем активным Swap файл набором команд

    fallocate -l 2G /swapfile
    ls -lh /swapfile
    chmod 600 /swapfile
    ls -lh /swapfile
    mkswap /swapfile
    swapon /swapfile
    swapon --show
    free -h
    

    Делаем наш Swap файл постоянным, добавив информацию о нем в файл /etc/fstab
    Для этого делаем бэкап вайла /etc/fstab и заносим необходимые данные в конец файла.

    cp /etc/fstab /etc/fstab.bak
    echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab
    

    Далее выполняем настройку параметров swappiness (как часто при нехватке памяти будет происходить обрацения к Swap файлу) и vfs_cache_pressure (настройка кеширования)

    cat /proc/sys/vm/swappiness
    

    По умолчанию это значение будет 60, это значит, что обращение к кэшу будет при загрузке памяти 100-60=40%. Желательно, чтобы это значение приближалось к нулю. Мы установим его на уровень 10, то есть при загрузке на 90% только будет обращение к Swap.

    cat /proc/sys/vm/vfs_cache_pressure
    

    По умолчанию это значение будет 100. При уменьшении этого параметра ядро, будет дольше держать страницы памяти в кеше, в том числе и в swap'е. Так как у нас всего 1Gb RAM, то мы можем оставить это значение по умолчанию. Ели бы было меньше, то можно было уменьшить до 50. Если же у нас 2Gb RAM и больше, то мы можем наоборот его увеличить, например до 1000

    В зависимости от ситуации выполняем команды

    mcedit /etc/sysctl.conf
    

    Добавляем в самом низу строчки
    vm.swappiness=10
    И если необходимо то и строчку с указанием нужного значения параметра.
    vm.vfs_cache_pressure=1000

    Сохраняем и выполняем ребут, чтобы изменения вступили в силу

    На этом предварительную настройку можно завершить.

    3. Установка и настройка сервиса полной ноды

    Установка достаточно проста. Загружаем архив с последней версией, распаковываем его, вносим изменения в файл конфигурации, копируем в директорию установки, делаем gvite сервисом. Конечная иерархия папок будет выглядеть так:
    /opt/Vite - здесь все наши версии gvite (сюда качаем, распаковываем)
    /opt/gvite - наша папка, с которой мы будем выполнять первую нашу установку и создание vite как запускаемого сервиса.
    /usr/local/vite/ - здесь будет лежать наш исполняемый файл сервиса
    /etc/vite/ - здесь будет лежать файл конфига

    Выполним скачивание и подготовку к установке.

    cd /opt
    mkdir Vite
    mkdir gvite
    cd ./Vite
    curl -L -O https://github.com/vitelabs/go-vite/releases/download/v1.2.3-alpha.4/gvite-v1.2.3-alpha.4-linux.tar.gz
    tar -xf gvite-v1.2.3-alpha.4-linux.tar.gz
    cd ./gvite-v1.2.3-alpha.4-linux
    sed -i 's/vite-full-node/vite-Придумываем_свое_название/g' node_config.json
    sed -i 's/getURL\": \"\"/getURL\" :\"wss:\/\/stats.vite.net\"/g' node_config.json
    sed -i 's/vite_xxxxxxxxxxxxxxxxxx/vite_указываем_наш_кошелек /g' node_config.json
    cp /opt/Vite/gvite-v1.2.3-alpha.4-linux/*  /opt/gvite/
    

    Командой sed -i автоматически вносим изменения в файл конфигурации вместо ручного редактирования.

    Создаем файл (юнит) vite.service

    touch /etc/systemd/system/vite.service
    chmod 664 /etc/systemd/system/vite.service
    mcedit /etc/systemd/system/vite.service
    

    Сохраняем туда текст следующего формата

    [Unit]
    Description=GVite node service
    After=network.target
    
    [Service]
    ExecStart=/opt/gvite/bootstrap/gvite
    Restart=on-failure
    User=vite
    Group=vite
    
    [Install]
    WantedBy=multi-user.target
    

    Стоит помнить, что в данной строчке ExecStart=/path_to_gvite/gvite должен быть правильно указан параметр path_to_gvite
    Для нашего примера ниже наши файлы все находятся в /opt/gvite и path_to_gvite должен выглядеть /opt/gvite/bootstrap

    Далее создаем установочный скриптов

    cd /opt/gvite
    mcedit install.sh
    

    Сохраняем текст следующего содержания:

    #!/bin/bash
    
    set -e
    
    CUR_DIR=`pwd`
    CONF_DIR="/etc/vite"
    BIN_DIR="/usr/local/vite"
    LOG_DIR=$HOME/.gvite
    
    echo "install config to "$CONF_DIR
    
    
    mkdir -p $CONF_DIR
    cp $CUR_DIR/node_config.json $CONF_DIR
    ls  $CONF_DIR/node_config.json
    
    echo "install executable file to "$BIN_DIR
    mkdir -p $BIN_DIR
    mkdir -p $LOG_DIR
    cp $CUR_DIR/gvite $BIN_DIR
    
    echo '#!/bin/bash
    exec '$BIN_DIR/gvite' -pprof -config '$CONF_DIR/node_config.json' >> '$LOG_DIR/std.log' 2>&1' | sudo tee $BIN_DIR/gvited > /dev/null
    
    chmod +x $BIN_DIR/gvited
    
    ls  $BIN_DIR/gvite
    ls  $BIN_DIR/gvited
    
    echo "config vite service boot."
    
    echo '[Unit]
    Description=GVite node service
    After=network.target
    
    [Service]
    ExecStart='$BIN_DIR/gvited'
    Restart=on-failure
    User='`whoami`'
    
    [Install]
    WantedBy=multi-user.target' | tee /etc/systemd/system/vite.service>/dev/null
    
    systemctl daemon-reload
    

    Даем права на запуск, выполняем его

    chmod +x install.sh
    ./install.sh
    systemctl enable vite
    

    Управление сервисом теперь можно выполнять командами

    service vite start
    service vite stop
    service vite restart
    

    4. Обеспечение бесперебойной работы
    Нам необходимо, чтобы наш сервис gvite постоянно работал.
    На предыдущем этапе мы сделали vite сервис как загружаемый. Но он будет автоподгружаться если был запущен через команду service vite start или после перезагрузки. Дополнительно добавим еще одну проверку.
    Для этого мы можем настроить планировщик задач cron
    Для этого отредактируем файл crontab

    crontab -e
    

    Добавляем в самом конце строчку и нажимаем Enter (делая ниже пустую строку)

    */5 * * * * pidof gvite > /dev/null|| /usr/sbin/service vite start
    
    

    "pidof gvite > /dev/null|| /usr/sbin/service vite start" данной командой мы проверяем запущена ли команда, если нет то запускаем наш сервис. /usr/sbin/service для крона нужно указывать точный путь для команды service. Проверка выполняется раз в пять минут. Можно настроить расписание по желанию.

    Сохраняем изменения.

    5. Обновление полной ноды.

    Здесь все просто, наши шаги следующие:

    1. Временно останавливаем cron-проверку запущенного процеса gvite
    2. Останавливаем процес gvite
    3. Загружаем архив с последней версией и распаковывает его
    4. Заменяем нужные файлы.
    5. Запускаем cron-проверку запущенного процеса gvite

    На практике это выглядит так:

    Запускаем редактирование файла crontab

    crontab -e
    

    Добавляем # символ перед командой (закоментируем ее) и сохраняем изменения

    #*/5 * * * * pidof gvite > /dev/null|| /usr/sbin/service vite start
    

    Далее пункты 2, 3, 4. Ниже пример для gvite-v1.2.3-alpha.4 версии

    service vite stop или же чтобы 100% kill -9 $(pidof gvite)
    sleep 10
    cd /opt/Vite
    curl -O -L https://github.com/vitelabs/go-vite/releases/download/v1.2.3-alpha.4/gvite-v1.2.3-alpha.4-linux.tar.gz
    tar -xf gvite-v1.2.3-alpha.4-linux.tar.gz
    cp /opt/Vite/gvite-v1.2.3-alpha.4-linux/gvite  /usr/local/vite
    

    Раскоментируем проверку в crontab

    Касательно вопроса мониторинга мне нравится вариант вот такого мониторинга, как на скриншоте
    Console with filtered nodes for monitoring
    Кто-то предпочтет использовать системы на подобии Zabbix, Nagios, Prometheus. Для нескольких ПК можно вообще использовать https://explorer.vite.net/FullNode

    Послесловие
    На выходе мы получим достаточно автономную единицу с неплохой защитой. Наша задача будет только обновлять софт. Можно скомпоновать все в несколько bash-скриптов, можно просто команды копировать блоками в консоль - все это упростит и ускорит намного выполнение рутинных задач. Возможна доработка статьи. Критика, пожелания, вопросы - все принимается.
    ЗЫ Нашел пару интересных моментов, гайд отправляется на доработку.
    Но это уже совсем другая история

    Некоторые дополнительные использованные ресурсы:
    https://vite.wiki/tutorial/node/example.html#start-gvite-as-service
    https://www.digitalocean.com/community/tutorials/how-to-add-swap-space-on-ubuntu-16-04


  • Reward

    Несколько небольших заметок

    • вы можете назначать один и тот же кошелек для нескольких полных нод, не нужно создавать кучу адресов;
    • если у вас несколько VPS, то у них должны быть разные IP-адреса, иначе награда удет на ту, у которой больше всего аптайм;
    • аптайм должен быть 90% и более в сутки. Если вдруг нода упала и не смогла восстановить работу - а такое бывает даже с планировщиками, то впринципе есть окно для восстановления работы. Аналогично и для апдейта. Иногда апдейт может затянуться и закончиться откатом к предыдущй версии а это все время;
    • если есть вопросы к разработчикам, не стесняемся, присоединяемся к discord-каналу https://discordapp.com/invite/CsVY76q и задаем их там напрямую.

  • Reward

    Отличная работа 👏


  • Reward

    Добавил описание настройки запуска gvite как сервиса по шагам из официального гайда
    https://vite.wiki/tutorial/node/example.html#start-gvite-as-service

    На заметку полный список параметров для сервиса gvite можно посмотреть с помощью параметра --help
    Для текущей версии он выглядит следующим образом:

    /usr/local/vite/gvite --help
    gvite [global options] command [command options] [arguments...]
    
    VERSION:
       v1.2.3-alpha.4
    
    COMMANDS:
       attach   Start an interactive JavaScript environment (connect to node)
       console  Start an interactive JavaScript environment
       license  Display license information
       version  Print version numbers
       help     Shows a list of commands or help for one command
    GLOBAL OPTIONS:
       --config value                     Json configuration file
       --datadir                          use for store all files
       --keystore                         Directory for the keystore (default = inside the datadir)
       --devnet                           Rinkeby network: pre-configured proof-of-authority dev network
       --testnet                          Ropsten network: pre-configured proof-of-work test network
       --mainnet                          Rinkeby network: pre-configured proof-of-authority prod network
       --identity value                   Custom node name
       --networkid value                  Network identifier (integer, 1=MainNet, 2=TestNet, 3~12=DevNet,) (default: 0)
       --maxpeers value                   Maximum number of network peers (network disabled if set to 0) (default: 0)
       --maxpendpeers value               Maximum number of pending connection attempts (defaults used if set to 0) (default: 0)
       --port value                       Network listening port (default: 0)
       --nodekeyhex value                 P2P node key as hex
       --discovery value                  enable p2p discovery or not
       --ipc                              Enable the IPC-RPC server
       --ipcpath                          Filename for IPC socket/pipe within the datadir (explicit paths escape it)
       --rpc                              Enable the HTTP-RPC server
       --rpcaddr value                    HTTP-RPC server listening interface
       --rpcport value                    HTTP-RPC server listening port (default: 0)
       --ws                               Enable the WS-RPC server
       --wsaddr value                     WS-RPC server listening interface
       --wsport value                     WS-RPC server listening port (default: 0)
       --jspath loadScript                JavaScript root path for loadScript (default: ".")
       --exec value                       Execute JavaScript statement
       --preload value                    Comma separated list of JavaScript files to preload into the console
       --miner                            Enable the Miner
       --coinbase value                   Coinbase is an address into which the rewards for the SuperNode produce snapshot-block
       --minerinterval value              Miner Interval(unit: second) (default: 0)
       --loglevel value                   log level (info,eror,warn,dbug)
       --vmtest                           Enable the VM Test
       --vmtestparam                      Enable the VM Test params
       --single                           Enable the NodeServer single
       --fileport value                   File transfer listening port (default: 0)
       --pprof                            Enable a performance analysis tool, you can visit the address[http://localhost:8080/debug/pprof]
       --pprofport port                   pporof visit port, you can visit the address[http://localhost:`port`/debug/pprof] (default: 0)
       --metrics                          Enable metrics collection and reporting
       --metrics.influxdb                 Enable metrics export/push to an external InfluxDB database
       --metrics.influxdb.endpoint value  InfluxDB API endpoint to report metrics to
       --metrics.influxdb.database value  InfluxDB database name to push reported metrics to (default: "metrics")
       --metrics.influxdb.username value  Username to authorize access to the database (default: "test")
       --metrics.influxdb.password value  Password to authorize access to the database (default: "test")
       --metrics.influxdb.host.tag host   InfluxDB host tag attached to all measurements (default: "localhost")
       --help, -h                         show help
       --version, -v                      print the version
    

    Согласно официальному гайду статус синхронизации можно проверить прямо с консоли вашей полной ноды

    Enter gvite command line using script
    Отредактируем файл ~/.bashrc

    mcedit ~/.bashrc
    

    Добавляем строчку и сохраняем изменения:

    alias vite="/opt/gvite/gvite attach ~/.gvite/testdata/gvite.ipc"
    

    Не забываем, что для данного примера я использую путь /opt/gvite/gvite (поменять на свой вариант).
    Запускаем команду, чтобы применились внесенные нами изменения

    source ~/.bashrc
    

    Далее запускаем командную строку gvite

    vite
    

    Теперь в консоли мы можем проверять, к примеру раз в 10 секунд текущую длинну блоков

    Welcome to the Gvite JavaScript console!
    -> 
    # Periodically output current block height
    Execute below command in gvite command line:
    
    setInterval(function(){vite.ledger_getSnapshotChainHeight();}, 10000)
    

    Выход из консоли выполняется командой exit.


  • Reward

    Отличная работа 👍


  • Reward

    Собираем gvite из основной ветки на github

    Предварительно устанавливаем make, make-guile и gcc

    apt-get nstall make
    apt-get install make-guile
    apt-get install gcc
    
    curl -O -L https://dl.google.com/go/go1.11.5.linux-amd64.tar.gz
    sha256sum go1.11.5.linux-amd64.tar.gz
    

    Проверяем хеш, совпадает ли с тем, что на сайте (битый архив)

    tar -xf go1.11.5.linux-amd64.tar.gz
    mv go /usr/local
    

    Добавляем параметры для go

    mcedit ~/.profile
    

    Добавляем строчки в конец файла.

    export GOPATH=$HOME/go
    export PATH=$PATH:/usr/local/go/bin:$GOPATH/bin
    

    Применяем изменения

    source ~/.profile
    

    Качаем код

    mkdir $HOME/go
    go get github.com/vitelabs/go-vite
    cd $HOME/go/src/github.com/vitelabs/go-vite/
    

    Компилируем файл.

    make gvite
    

    Наш готовый файл находится по адресу:

    cd ~/go/src/github.com/vitelabs/go-vite/build/cmd/gvite/
    

    Фикс бага со стаком на 7436*** блоке
    Останавливаем сервис и выполняем команду из папки с ранее приготовленным файлом

    ./gvite -config /source_to_config/node_config.json recover -del=7436000
    

  • Reward

    Заметил, что с новой версией может немного меняться конфигурационный файл. Например, добавляются в лишние пробелы, параметры и т.д.

    К примеру было:
    getURL":"" с заменой на getURL":"wss://stats.vite.net"
    И соответствующая команда
    sed -i 's/getURL": ""/getURL":"wss://stats.vite.net"/g' node_config.json

    Стало:
    getURL": "" с заменой на getURL": "wss://stats.vite.net",
    И соответствующая команда
    sed -i 's/getURL": ""/getURL" :"wss://stats.vite.net"/g' node_config.json


  • Reward

    Нужно помнить, что место не резиновое. Например если вы используете ноду с 25Gb жестким диском.
    В помощь пару команд, чтобы почистить наши логи. Иногда они полностью забивают все дисковое пространство из-за частых ошибок - например нода перестала нормально синхронизироваться и вы за ней не уследили.
    Первых две команды вычищают все их из двух папок с логами. Третья команда покажет информацию об использованом дисковом пространстве.

    rm -rfv ~/.gvite/testdata/rpclog/*
    rm -rfv ~/.gvite/testdata/runlog/*
    df -h
    


  • Добрый день.
    Подскажите где можно почитать как настроить полную ноду на Windows 10.
    Так же возможно ли настроить несколько нод на 1 компьютере с Windows 10.
    Для каждой ноды у меня есть отдельный выделенный IP адрес.


  • Reward


Log in to reply
 

Suggested Topics