Donate VRC/VRM for the Wiki to VBzaNDExHyFpnNvYc5QH5e4ipBZqxxPnKJ . Thank you, Joe.

Setting up a Verium Mining Pool

From VeriCoin & Verium Wiki
Jump to: navigation, search

Overview

THIS GUIDE IS STILL BEING CREATED. FEEL FREE TO CONTRIBUTE TO HELP MAKE THIS THE BEST RESOURCE AVAILABLE!!!

This guide will help you get started with setting up your first mining pool. Consider this guide more of a "How to setup a Proof of Concept (PoC) mining pool" rather than a pool ready for public use. While this is a PoC, some effort has been made to illustrate good, basic security and operational best practices.

If you are thinking about setting up a public VRM mining pool for fun and profit, make sure you understand that pool operation is a commitment not to be taken lightly and will probably require a considerable investment of time and money on your part. Also, do not do a disservice to your loyal miners by deploying a soup sandwich mining pool. We are all learning and nobody is perfect but do your best to make sure your miners and their hard earned VRM coins are safe and secure.

Assumptions

In order to complete this guide, you will need the following:

  • Registered domain name
  • Ability to update DNS records for your registered domain name
  • Public, static IP address for your server
  • Email mailing service (e.g. Mailgun)
  • Ability to receive email (i.e. MPOS contact form)

Contraints

Since this guide is a POC, the following topics are not covered. If you think you might want to deploy a public mining pool for others to use, make sure that you understand and can reasonably do the following:

  • Web server load balancing
  • Database load balancing and redundance
  • Centralized monitoring, logging, and alerting
  • Backup and restoration
  • Security

Ubuntu Mining Pool POC

The commands in this guide were run on an updated Ubuntu 16.04 LTS server on AWS.

Update & Upgrade

With the root account or sudo, run these commands:

apt-get update
DEBIAN_FRONTEND=noninteractive apt-get upgrade -yq
apt-get dist-upgrade -f -y

Install VRM Wallet Dependencies

You will need the following packages installed in order to install the VRM wallet software on Ubuntu. Install using the root account or sudo:

apt install libminizip-dev libcurl4-openssl-dev unzip libboost-dev libboost-system-dev libboost-filesystem-dev libboost-program-options-dev libboost-thread-dev libssl-dev libdb++-dev libminiupnpc-dev libboost-all-dev libqrencode-dev freeglut3-dev git build-essential automake autoconf pkg-config libcurl4-openssl-dev libjansson-dev libssl-dev libgmp-dev -y

There is an error thrown when you update libssl-dev and when you do make -f you get bignum errors as the latest libssl-dev doesnt work ..there is a work around i have found

 sudo apt-get install libssl-dev=1.0.2g-1ubuntu4.10 

this will let the install continue and will need pinning as will be lost at next update. To prevent that use

 echo "libssl-dev hold" | sudo dpkg --set-selections

Use libssl-dev install" | sudo dpkg --set-selections to undo the hodling.

Install NOMP Dependencies

You will need the following packages to run NOMP stratum software [1]. Install using the root account or sudo:

apt install git build-essential libssl-dev npm nodejs nodejs-legacy -y

Install MPOS Dependencies

The following packages are required for the frontend software called MPOS and is explained here [2]. Note however that the commands below use more recent packages. If you have been following along, all of these packages will already be installed but if not, install using the root account or sudo:

apt install build-essential autoconf libtool libboost-all-dev libcurl4-openssl-dev libdb5.3-dev libdb5.3++-dev -y

Install MySQL & Setup a DB User

The frontend MPOS software uses MySQL as the database engine. However, MPOS is not 100% compatible with MySQL 5.7 per the project's FAQ [3]. Also, the example below as well as others use the export command. Do know that this will expose the variable contents in the command history so take steps to mitigate if this is a concern. For now, use the Linux root account or sudo to setup a MySQL database server and MySQL root account:

export DB_ROOT_PASS=<strong password>

export DEBIAN_FRONTEND="noninteractive"
sudo debconf-set-selections <<< "mysql-server mysql-server/root_password password $DB_ROOT_PASS"
sudo debconf-set-selections <<< "mysql-server mysql-server/root_password_again password $DB_ROOT_PASS"
apt install mysql-server -y 

Per the above linked FAQ, edit the 'my.cnf' file to make the recommended workaround persistent. If you know what you are doing you can do something similar to the script below. Otherwise, follow the manual steps that come after. Either way, DO NOT SKIP this configuration because it is a critical change:

cp /etc/mysql/my.cnf /etc/mysql/my.cnf.BAK
echo " " >> /etc/mysql/my.cnf
echo "[mysqld]" >> /etc/mysql/my.cnf
echo 'sql_mode=STRICT_TRANS_TABLES\,NO_ZERO_IN_DATE\,NO_ZERO_DATE\,ERROR_FOR_DIVISION_BY_ZERO\,NO_AUTO_CREATE_USER\,NO_ENGINE_SUBSTITUTION' >> /etc/mysql/my.cnf

/etc/init.d/mysql restart

If you've opted for the manual route, first edit the file. The example below assumes vi as the editor:

vi /etc/mysql/my.cnf

Then add the following line. DO NOT SKIP this step because MySQL 5.7 does not work and will cause problems with shares being credited. See here for background [4].

[mysqld]
sql_mode=STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION

The my.cnf file should look like this when you are done:

#
# The MySQL database server configuration file.
#
# You can copy this to one of:
# - "/etc/mysql/my.cnf" to set global options,
# - "~/.my.cnf" to set user-specific options.
# 
# One can use all long options that the program supports.
# Run program with --help to get a list of available options and with
# --print-defaults to see which it would actually understand and use.
#
# For explanations see
# http://dev.mysql.com/doc/mysql/en/server-system-variables.html

#
# * IMPORTANT: Additional settings that can override those from this file!
#   The files must end with '.cnf', otherwise they'll be ignored.
#

!includedir /etc/mysql/conf.d/
!includedir /etc/mysql/mysql.conf.d/

[mysqld]
sql_mode=STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION

Next restart the MySQL server:

/etc/init.d/mysql restart

Now apply some basic security to your new MySQL server:

mysql_secure_installation

Here is an example output of running the above command:

[email protected]:/home/ubuntu# mysql_secure_installation

Securing the MySQL server deployment.

Enter password for user root: 

VALIDATE PASSWORD PLUGIN can be used to test passwords
and improve security. It checks the strength of password
and allows the users to set only those passwords which are
secure enough. Would you like to setup VALIDATE PASSWORD plugin?

Press y|Y for Yes, any other key for No: Y

There are three levels of password validation policy:

LOW    Length >= 8
MEDIUM Length >= 8, numeric, mixed case, and special characters
STRONG Length >= 8, numeric, mixed case, special characters and dictionary file

Please enter 0 = LOW, 1 = MEDIUM and 2 = STRONG: 2
Using existing password for root.

Estimated strength of the password: 50 
Change the password for root ? ((Press y|Y for Yes, any other key for No) : Y

New password: 

Re-enter new password: 

Estimated strength of the password: 100 
Do you wish to continue with the password provided?(Press y|Y for Yes, any other key for No) : Y
By default, a MySQL installation has an anonymous user,
allowing anyone to log into MySQL without having to have
a user account created for them. This is intended only for
testing, and to make the installation go a bit smoother.
You should remove them before moving into a production
environment.

Remove anonymous users? (Press y|Y for Yes, any other key for No) : Y
Success.


Normally, root should only be allowed to connect from
'localhost'. This ensures that someone cannot guess at
the root password from the network.

Disallow root login remotely? (Press y|Y for Yes, any other key for No) : Y
Success.

By default, MySQL comes with a database named 'test' that
anyone can access. This is also intended only for testing,
and should be removed before moving into a production
environment.

Remove test database and access to it? (Press y|Y for Yes, any other key for No) : Y
 - Dropping test database...
Success.

 - Removing privileges on test database...
Success.

Reloading the privilege tables will ensure that all changes
made so far will take effect immediately.

Reload privilege tables now? (Press y|Y for Yes, any other key for No) : Y
Success.

All done! 

Finally, add a user for the MPOS frontend software. Do not run MPOS using the root MySQL DB account.

Connect to your MySQL server:

mysql -u root -p

Create a database and a database user. The default database name that NOMP and MPOS use is mpos. Try to avoid the defaults and use unique names. The snippet below illustrates how to create a database. After the database is created, a new MySQL DB user and password is created and assigned to the new database that will be used for MPOS and NOMP:

create database <YourUniqueDBName>;
GRANT ALL PRIVILEGES ON <YourUniqueDBName>.* To '<YourUniqueDBUser>'@'localhost' IDENTIFIED BY '<YourUniqueDBUserPassword>';
FLUSH PRIVILEGES;

After you've executed the above commands as the root MySQL user, confirm the permissions (i.e. grants) applied to the new DB user:

mysql> SHOW GRANTS for '<YourUniqueDBUser>'@'localhost';
+----------------------------------------------------------------+
| Grants for <YourUniqueDBUser>@localhost                                  |
+----------------------------------------------------------------+
| GRANT USAGE ON *.* TO '<YourUniqueDBUser>'@'localhost'                   |
| GRANT ALL PRIVILEGES ON `<YourUniqueDBName>`.* TO '<YourUniqueDBUser>'@'localhost' |
+----------------------------------------------------------------+
2 rows in set (0.00 sec)

Confirm that you can login using the new account and list all databases. The new DB user should only have access to two databases; the one your created and the information_schema database:

[email protected]:/home/ubuntu# mysql -u <YourUniqueDBUser> -p
Enter password: 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 8
Server version: 5.7.20-0ubuntu0.16.04.1 (Ubuntu)

Copyright (c) 2000, 2017, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| <YourUniqueDBName> |
+--------------------+
2 rows in set (0.00 sec)

mysql> exit
Bye

MySQL DB Security Considerations

Database security can be a job in itself. There are many things to consider, here are a few...

  • Avoid running DB on the same server as the Webserver and Wallet software. Segmentation goes a long way.
  • Make sure to not only make back ups, but make sure to test said backups.
  • Monitor your DB regularly for anything whacky.

Wallet Install & RPC Setup

DJoeDt at Github has scripts available to quickly get started here: [5]

The following code snippet is an example using pieces of DJoeDt's install_Verium_Wallet.sh script. The biggest difference is running the wallet daemon as a limited Linux user instead of root. Make sure the above mentioned dependencies have been installed before running these commands.

As root or an account with sudo, create a user account that will run the veriumd daemon:

export LINUX_OS_WALLET_USER=<UniqueOSUserName>
useradd -m -r $LINUX_OS_WALLET_USER

Now, login to the account and change directory to the account's home folder:

su $LINUX_OS_WALLET_USER
cd ~

The following commands will setup your VRM wallet for the mining pool:

export WALLET_RPC_PORT=33987
export WALLET_RPC_USER=<WalletRPCUser>
export WALLET_RPC_PASS=<WalletRPCUserPassword>
# Only set this if you need an additional IP range besides localhost and 127.0.0.1
export WALLET_RPC_ALLOW_IP=

mkdir ~/verium
git clone https://github.com/VeriumReserve/verium ~/verium/wallet
cd ~/verium/wallet/src
make -f makefile.unix
wget https://www.vericoin.info/downloads/verium.conf
echo " " >> ~/verium/wallet/src/verium.conf
echo "server=1" >> ~/verium/wallet/src/verium.conf
echo "listen=1" >> ~/verium/wallet/src/verium.conf
echo "daemon=1" >> ~/verium/wallet/src/verium.conf
echo "gen=0" >> ~/verium/wallet/src/verium.conf
echo "rpcuser=$WALLET_RPC_USER" >> ~/verium/wallet/src/verium.conf
echo "rpcpassword=$WALLET_RPC_PASS" >> ~/verium/wallet/src/verium.conf
echo "rpcallowip=127.0.0.1" >> ~/verium/wallet/src/verium.conf
echo "rpcallowip=localhost" >> ~/verium/wallet/src/verium.conf
echo "rpcallowip=$WALLET_RPC_ALLOW_IP" >> ~/verium/wallet/src/verium.conf
echo "rpcport=$WALLET_RPC_PORT" >> ~/verium/wallet/src/verium.conf
~/verium/wallet/src/veriumd
sleep 60
~/verium/wallet/src/veriumd bootstrap false
~/verium/wallet/src/veriumd stop
~/verium/wallet/src/veriumd
sleep 120

Once the wallet is installed, bootstrapped, and running, you can run several commands to make sure things are in order:

The first thing you"ll want to know is the VRM address:

./veriumd getaddressesbyaccount ""

Get a list of RPC commands available:

./veriumd help

Linux OS command to verify that the veriumd daemon is running:

ps aux | grep veriumd

Ensure that the wallet is connected to the network and working correctly.

./veriumd getinfo

Get the wallet address.

./veriumd getaddressesbyaccount ""

If you wanted to use the wallet address in a script, you could store it in a variable:

export WALLETADDRESS=$(/home/$VRM_WALLET_OS_USER/verium/wallet/src/veriumd getaddressesbyaccount "" | awk '/"/ {print $1;}' | cut -d\" -f2)

Confirm that the wallet daemon is running as the new, limited Linux OS user and not root with command ps aux | grep veriumd. The output should be something similar to below:

<UniqueOSUserName>@ip-x-x-x-x:~/verium/wallet/src$ ps aux | grep veriumd
<UniqueOSUserName>  2959 40.2  5.7 2480144 221412 ?      SLsl 06:39   4:12 /home/<UniqueOSUserName>/verium/wallet/src/veriumd

Wallet Security Consideration

This is not an exclusive list of considerations...

  • According to this issue [6], it appears that MPOS does not work with encrypted wallets.
  • Avoid running the wallet daemon on the same server (i.e. web server) exposed to the public Internet.
  • Configuring rpcssl=1 as well as certificates could improve security for the wallet verium.conf file. Not much added security value if all run on the same server but if making connections from different servers, encrypts RPC communications and adds an extra layer of security.
  • Avoid running wallet software on same server running DB and Webserver; in other words, take measures to guard this like an actual bank vault.
  • Backup your wallet and test that you can restore the wallet!!!

Redis Install

This is probably the easiest part of this PoC setup.

Make sure you exit from the wallet user Linux OS account. Then using the root account or sudo, install Redis

exit
apt install redis-server -y

And make sure the Redis daemon is running:

ps aux | grep redis

NOMP Install & Configuration

Now is the part that can be a complete pain if you've never installed NOMP before. Actually, its uncertain if this is even the correct, much less the "best" way to install NOMP but it works.

Setup User & Install

First, setup another Linux OS user that will run the NOMP stratum daemon. Do not run the daemon as root.

export STRATUM_OS_USER=<yournompstratumusername>

## -m = create home folder -r = create system user
useradd -m -r $STRATUM_OS_USER

Next, login to the newly created account and change directory to the home folder:

su $STRATUM_OS_USER
cd ~

NOMP will ONLY work with node v0.10+ as mentioned here [7].

curl https://raw.githubusercontent.com/creationix/nvm/v0.16.1/install.sh | sh
source ~/.profile
nvm install 0.10.25
nvm use 0.10.25
nvm alias default 0.10.25

Now we can finally download NOMP:

git clone https://github.com/zone117x/node-open-mining-portal nomp
cd nomp

You will need to make yet another weird change. In line 46 of the file package.json, the entry "request": "*", needs to be changed to "request": "2.69.0", .

If you want to be fancy make the change in one sweep with:

sed -i 's/"request": "\*",/"request": "2.69.0",/g' package.json

Otherwise, do it in an editor:

vi package.json

The file should like like this:

{
    "name": "node-open-mining-portal",
    "version": "0.0.4",
    "description": "An extremely efficient, highly scalable, all-in-one, easy to setup cryptocurrency mining pool",
    "keywords": [
        "stratum",
        "mining",
        "pool",
        "server",
        "poolserver",
        "bitcoin",
        "litecoin",
        "scrypt"
    ],
    "homepage": "https://github.com/zone117x/node-open-mining-portal",
    "bugs": {
        "url": "https://github.com/zone117x/node-open-mining-portal/issues"
    },
    "license": "GPL-2.0",
    "author": "Matthew Little",
    "contributors": [
        "vekexasia",
        "TheSeven"
    ],
    "main": "init.js",
    "bin": {
        "block-notify": "./scripts/blockNotify.js"
    },
    "repository": {
        "type": "git",
        "url": "https://github.com/zone117x/node-open-mining-portal.git"
    },
    "dependencies": {
        "stratum-pool": "git://github.com/zone117x/node-stratum-pool.git",
        "dateformat": "1.0.12",
        "node-json-minify": "*",
        "redis": "0.12.1",
        "mysql": "*",
        "async": "1.5.2",
        "express": "*",
        "body-parser": "*",
        "compression": "*",
        "dot": "*",
        "colors": "*",
        "node-watch": "*",
        "request": "2.69.0",
        "nonce": "*",
        "bignum": "0.12.5",
        "extend": "*"
    },
    "engines": {
        "node": ">=0.10"
    }
}

After you have made the change and saved the file, take a deep breath and run the following command:

npm update

If everything went well, the last six lines of the output should look similar to this:

.
.
.
make: Leaving directory '/home/stratumuser/nomp/node_modules/stratum-pool/node_modules/multi-hashing/build'
[email protected] node_modules/stratum-pool
├── [email protected]
├── [email protected] ([email protected], [email protected])
├── [email protected] ([email protected])
└── [email protected] ([email protected])

Frontend & Coin Configuration

Make sure you are still logged with the Linux OS account that will run the NOMP stratum daemon and still in the NOMP folder:

[email protected]:~/nomp$ pwd
/home/yournompstratumusername/nomp

From here you need to copy the example JSON file to a file called config.json and then edit it:

cp config_example.json config.json
vi config.json

THIS NEEDS TO BE CONFIRMED!!!

Change the website entry line (Line 33) from "true" to "false". This tells NOMP to not use NOMP's frontend so that the MPOS frontend can be used.

config.json should like like this when you are done:

{
    "logLevel": "debug",
    "logColors": true,

    "cliPort": 17117,

    "clustering": {
        "enabled": true,
        "forks": "auto"
    },

    "defaultPoolConfigs": {
        "blockRefreshInterval": 1000,
        "jobRebroadcastTimeout": 55,
        "connectionTimeout": 600,
        "emitInvalidBlockHashes": false,
        "validateWorkerUsername": true,
        "tcpProxyProtocol": false,
        "banning": {
            "enabled": true,
            "time": 600,
            "invalidPercent": 50,
            "checkThreshold": 500,
            "purgeInterval": 300
        },
        "redis": {
            "host": "127.0.0.1",
            "port": 6379
        }
    },

    "website": {
        "enabled": false,
        "host": "0.0.0.0",
        "port": 80,
        "stratumHost": "cryppit.com",
        "stats": {
            "updateInterval": 60,
            "historicalRetention": 43200,
            "hashrateWindow": 300
        },
        "adminCenter": {
            "enabled": true,
            "password": "password"
        }
    },

    "redis": {
        "host": "127.0.0.1",
        "port": 6379
    },

    "switching": {
        "switch1": {
            "enabled": false,
            "algorithm": "sha256",
            "ports": {
                "3333": {
                    "diff": 10,
                    "varDiff": {
                        "minDiff": 16,
                        "maxDiff": 512,
                        "targetTime": 15,
                        "retargetTime": 90,
                        "variancePercent": 30
                    }
                }
            }
        },
        "switch2": {
            "enabled": false,
            "algorithm": "scrypt",
            "ports": {
                "4444": {
                    "diff": 10,
                    "varDiff": {
                        "minDiff": 16,
                        "maxDiff": 512,
                        "targetTime": 15,
                        "retargetTime": 90,
                        "variancePercent": 30
                    }
                }
            }
        },
        "switch3": {
            "enabled": false,
            "algorithm": "x11",
            "ports": {
                "5555": {
                    "diff": 0.001,
                    "varDiff": {
                        "minDiff": 0.001,
                        "maxDiff": 1, 
                        "targetTime": 15, 
                        "retargetTime": 60, 
                        "variancePercent": 30 
                    }
                }
            }
        }
    },

    "profitSwitch": {
        "enabled": false,
        "updateInterval": 600,
        "depth": 0.90,
        "usePoloniex": true,
        "useCryptsy": true,
        "useMintpal": true,
        "useBittrex": true
    }
}

Next, we need to make a coin configuration. Let's call the new coin file, verium.json:

cp coins/vertcoin.json coins/verium.json
vi coins/verium.json

THIS NEEDS TO BE CONFIRMED!!!

Your verium.json coin file should now look like this:

{
    "name": "Verium",
    "symbol": "VRM",
    "algorithm": "scrypt-n",
    "reward":"POS",
    "timeTable": {
      "1048576": 100
    }
}

Stratum Pool Configuration

THIS NEEDS TO BE CONFIRMED!!! ESPECIALLY BEST PORTS AND DIFFICULTY SETTINGS + RATIONALE!!!

Now it's time to setup the stratum pool.

cp pool_configs/litecoin_example.json pool_configs/verium.json
vi pool_configs/verium.json

There are various configurations in this file, namely the ports and difficulty settings. Note that in the last entry in the sample configuration below, "mposMode" is where we tell NOMP to use MPOS for the front end and store data in the MySQL database. Up to this point, we have configured the database server, but not an actual database for NOMP and MPOS to use. Consider using a different database name from the default.

Your final pool config verium.json should look similar to this:

{
    "enabled": true,
    "coin": "verium.json",

    "address": "YourPoolWalletVRMAddress",

    "paymentProcessing": {
        "enabled": false,
        "paymentInterval": 20,
        "minimumPayment": 70,
        "daemon": {
            "host": "127.0.0.1",
            "port": 19332,
            "user": "testuser",
            "password": "testpass"
        }
    },

    "ports": {
        "3332": {
            "diff": 0.001,
            "varDiff": {
              "minDiff": 0.001,
              "maxDiff": 0.03,
              "targetTime": 100,
              "retargetTime": 90,
              "variancePercent": 30
            
            }
        },
        "3333": {
            "diff": 0.03,
            "varDiff": {
                "minDiff": 0.03,
                "maxDiff": 0.2,
                "targetTime": 100,
                "retargetTime": 90,
                "variancePercent": 30
            }
        },
        "3334": {
            "diff": 0.2,
            "varDiff": {
                "minDiff": 0.02,
                "maxDiff": 0.06,
                "targetTime": 100,
                "retargetTime": 90,
                "variancePercent": 30
            }
        }
    },

    "daemons": [
        {
            "host": "127.0.0.1",
            "port": 33987,
            "user": "<wallet rpc user>",
            "password": "<wallet rpc user>"
        }
    ],

    "p2p": {
        "enabled": false,
        "host": "127.0.0.1",
        "port": 19333,
        "disableTransactions": true
    },

    "mposMode": {
        "enabled": true,
        "host": "127.0.0.1",
        "port": 3306,
        "user": "yourMPOSDBusername",
        "password": "yourMPOSDBusersecurepassword",
        "database": "mpos",
        "checkPassword": true,
        "autoCreateWorker": false
    }

}

At this point you can exit out of the Linux OS stratum user account.

MPOS Install & Configuration

Using root or sudo, install the following dependencies required for MPOS as outlined at [8]. Note however that the commands below are updated and different from what the MPOS wiki explains.

apt install memcached php-memcached php-mysqlnd php-curl php-json libapache2-mod-php -y

Next, use the following commands to download MPOS:

cd /var/www
sudo git clone git://github.com/MPOS/php-mpos.git MPOS
cd MPOS
git checkout master

Make sure you are in the MPOS folder. If you aren't sure, use the pwd command:

[email protected]:/var/www/MPOS# pwd
/var/www/MPOS

Change ownership of the folders templates/compile, templates/cache, and logs as explained at [9]:

chown -R www-data templates/compile templates/cache logs 

Hopefully you have already created a new database for MPOS and NOMP as well as a limited DB user in section: Install MySQL & Setup a DB User. In the snippet below, we will configure the MPOS data schema for the database:

mysql -u <YourUniqueDBUser> -p <YourUniqueDBName> < sql/000_base_structure.sql

The following commands will copy a template and edit it:

cp include/config/global.inc.dist.php include/config/global.inc.php
vi include/config/global.inc.php

Here is a sample global.inc.php configuration. More detailed settings, configurations, and explanations will be outlined in section Link title.

<?php
$defflip = (!cfip()) ? exit(header('HTTP/1.1 401 Unauthorized')) : 1;

/**
 * Do not edit this unless you have confirmed that your config has been updated!
 * Also the URL to check for the most recent upstream versions available
 *  https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-config-version
 **/
$config['version'] = '1.0.1';
$config['version_url'] = 'https://raw.githubusercontent.com/MPOS/php-mpos/master/include/version.inc.php';

/**
 * Unless you disable this, we'll do a quick check on your config first.
 *  https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-config-check
 */
$config['skip_config_tests'] = false;

/**
 * Unless you disable this, we'll do a check for a valid coin address on registration.
 *  https://github.com/MPOS/php-mpos/wiki/Config-Setup#check-for-valid-wallet-address
 */
$config['check_valid_coinaddress'] = true;

/**
 * Defines
 *  Debug setting and salts for hashing passwords
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-defines--salts
 */
$config['DEBUG'] = 0;
$config['SALT'] = 'SetAtLeast30RandomCharactersHere';
$config['SALTY'] = 'SetAtLeast30RandomCharactersHere';

/**
  * Coin Algorithm
  *  Algorithm used by this coin, sha256d or scrypt
  *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-algorithm
  **/
$config['algorithm'] = 'scryptn';

/**
  * Getbalance API Calls
  *  System used for getting actual Balance from Wallet
  *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#getbalance-api-calls
  **/
$config['getbalancewithunconfirmed'] = false;

/**
 * Database configuration
 *  MySQL database configuration
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-database-configuration
 **/
$config['db']['host'] = 'localhost';
$config['db']['user'] = 'nonrootDBuser';
$config['db']['pass'] = 'nonrootDBuserpassword';
$config['db']['port'] = 3306;
$config['db']['name'] = 'mpos';
// Disabled by default and set in bootstrap if unset, but left in here so
// people know it exists
// $config['db']['shared']['accounts'] = $config['db']['name'];
// $config['db']['shared']['workers'] = $config['db']['name'];
// $config['db']['shared']['news'] = $config['db']['name'];

/**
 * Local wallet RPC
 *  RPC configuration for your daemon/wallet
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-local-wallet-rpc
 **/
$config['wallet']['type'] = 'http';
$config['wallet']['host'] = 'localhost:33987';
$config['wallet']['username'] = 'WALLET_RPC_USER';
$config['wallet']['password'] = 'WALLET_RPC_PASS';

/**
 * Swiftmailer configuration
 *  Configure your way to send mails
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-swiftmailer
 **/
$config['swiftmailer']['type'] = 'sendmail';
$config['swiftmailer']['sendmail']['path'] = '/usr/sbin/sendmail';
$config['swiftmailer']['sendmail']['options'] = '-bs';
$config['swiftmailer']['smtp']['host'] = 'your.mail-relay.com';
$config['swiftmailer']['smtp']['port'] = '587';
$config['swiftmailer']['smtp']['encryption'] = 'tls';
$config['swiftmailer']['smtp']['username'] = '';
$config['swiftmailer']['smtp']['password'] = '';
$config['swiftmailer']['smtp']['throttle'] = 100;

/**
 * Getting Started Config
 *  Shown to users in the 'Getting Started' section
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-getting-started
 **/
$config['gettingstarted']['coinname'] = 'Verium';
$config['gettingstarted']['coinurl'] = 'https://portal.vericoin.info/';
$config['gettingstarted']['stratumurl'] = '<yourdomain.com>';
$config['gettingstarted']['stratumport'] = '3333';

/**
 * Ticker API
 *  Fetch exchange rates via an API
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-ticker-api
 **/
$config['price']['enabled'] = false;
$config['price']['url'] = 'https://btc-e.com';
$config['price']['target'] = '/api/2/ltc_usd/ticker';
$config['price']['currency'] = 'USD';

/**
 * Automatic Payout Thresholds
 *  Minimum and Maximum auto payout amount
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-automatic-payout-thresholds
 **/
$config['ap_threshold']['min'] = 2;
$config['ap_threshold']['max'] = 20;

/**
 * Minimum manual Payout Threshold
 *  Minimum manual payout amount
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-manual-payout-threshold
 **/
$config['mp_threshold'] = 1;

/**
 * Donation thresholds
 *  Minimum donation amount in percent
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-donation-thresholds
 **/
$config['donate_threshold']['min'] = 1;

/**
 * Account Specific Settings
 *  Settings for each user account
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-account-specific-settings
 **/
$config['accounts']['invitations']['count'] = 5;

/**
 * Currency
 *  Shorthand name for the currency
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-currency
 */
$config['currency'] = 'VRM';

/**
 * Coin Target
 *  Target time for coins to be generated
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-coin-target
 **/
$config['cointarget'] = '150';

/**
 * Coin Diff Change
 *  Amount of blocks between difficulty changes
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-coin-diff-change
 **/
$config['coindiffchangetarget'] = 2016;

/**
 * TX Fees
 *  Fees applied to transactions
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-tx-fees
 **/
$config['txfee_auto'] = 0.1;
$config['txfee_manual'] = 0.1;

/**
 * Block & Pool Bonus
 *  Bonus coins for blockfinder or a pool bonus for everyone
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-block-bonus
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-pool-bonus
 */
$config['block_bonus'] = 0;
$config['pool_bonus'] = 0;
$config['pool_bonus_type'] = 'payout';

/**
 * Payout System
 *  Payout system chosen
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-payout-system
 **/
$config['payout_system'] = 'prop';

/**
 * Sendmany Support
 *  Enable/Disable Sendmany RPC method
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-sendmany-support
 **/
$config['sendmany']['enabled'] = false;

/**
 * Transaction Limits
 *  Number of transactions per payout run
 **/
$config['payout']['txlimit_manual'] = 500;
$config['payout']['txlimit_auto'] = 500;

/**
 * Round Purging
 *  Round share purging configuration
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-round-purging
 **/
$config['purge']['sleep'] = 1;
$config['purge']['shares'] = 25000;

/**
 * Share Archiving
 *  Share archiving configuration details
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-archiving
 **/
$config['archive']['maxrounds'] = 10; 
$config['archive']['maxage'] = 60 * 24; 


/**
 * Pool Fees
 *  Fees applied to users
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-pool-fees
 */
$config['fees'] = 0;

/**
 * PPLNS
 *  Pay Per Last N Shares
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-pplns-settings
 */
$config['pplns']['shares']['default'] = 4000000;
$config['pplns']['shares']['type'] = 'blockavg';
$config['pplns']['blockavg']['blockcount'] = 10;
$config['pplns']['reverse_payout'] = true;
$config['pplns']['dynamic']['percent'] = 30;

/**
 * Difficulty
 *  Difficulty setting for stratum/pushpool
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-pool-target-difficulty
 */
$config['difficulty'] = 20;

/**
 * Block Reward
 *  Block reward configuration details
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-reward-settings
 **/
$config['reward_type'] = 'block';
$config['reward'] = 3.8;

/**
 * Confirmations
 *  Credit and Network confirmation settings
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-confirmations
 */
$config['confirmations'] = 120;
$config['network_confirmations'] = 120;

/**
 * PPS
 *  Pay Per Share configuration details
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-pps-settings
 **/
$config['pps']['reward']['default'] = 50;
$config['pps']['reward']['type'] = 'blockavg';
$config['pps']['blockavg']['blockcount'] = 10;

/**
 * Memcache
 *  Memcache configuration details
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-memcache
 **/
$config['memcache']['enabled'] = true;
$config['memcache']['host'] = 'localhost';
$config['memcache']['port'] = 11211;
$config['memcache']['keyprefix'] = 'mpos_';
$config['memcache']['expiration'] = 90;
$config['memcache']['splay'] = 15;
$config['memcache']['force']['contrib_shares'] = false;
$config['memcache']['sasl'] = false;
$config['memcache']['sasl']['username'] = '';
$config['memcache']['sasl']['password'] = '';

/**
 * Cookies
 *  Cookie configuration details
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-cookies
 **/
$config['cookie']['duration'] = '1440';
$config['cookie']['domain'] = '';
$config['cookie']['path'] = '/';
$config['cookie']['httponly'] = true;
$config['cookie']['secure'] = false;

/**
 * Smarty Cache
 *  Enable smarty cache and cache length
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-smarty-cache
 **/
$config['smarty']['cache'] = 0;
$config['smarty']['cache_lifetime'] = 30;

/**
 * System load
 *  Disable some calls when high system load
 *   https://github.com/MPOS/php-mpos/wiki/Config-Setup#wiki-system-load
 **/
$config['system']['load']['max'] = 10.0;

Now it's time to choose a webserver and configure it!

Web Server Configuration

You can use Apache or NGINX for your web server. This PoC will (eventually) explain both methods.


Apache

Everyone has their own preferred way to configure a web server; this is just one. If you don't like anything you see here, feel free to suggest better methods and why.

Basics

Make sure that you have configured DNS to point your domain name to your server's IP address. Please do that before continuing. You can use this site to confirm that your DNS is resolving correctly [10].

View the current DocumentRoot setting inside the file 000-default.conf with this command:

[email protected]:/var/www/MPOS# cat /etc/apache2/sites-enabled/000-default.conf | grep DocumentRoot
	DocumentRoot /var/www/html

Now change it manually or with the following command:

sed -i 's/DocumentRoot \/var\/www\/html/DocumentRoot \/var\/www\/MPOS\/public/g' /etc/apache2/sites-enabled/000-default.conf

Although we will be setting up our site to use TLS only, you need to make sure that ports 80 (i.e. HTTP) and 443 (i.e. TLS) are open. The reason for this is that Let's Encrypt will need to verify your domain resolution and published DocumentRoot.

This can be verified by reviewing entries in your access.log file (/var/log/apache2/access.log). When the validation takes place an entry similar to below can be found:

64.78.149.164 - - [14/Jan/2018:07:31:27 +0000] "GET /.well-known/acme-challenge/NITYxxxxxxxxxxxx-_ASMxxxxxxxxxxxxx HTTP/1.1" 200 310 "-" "Mozilla/5.0 (compatible; Let's Encrypt validation server; +https://www.letsencrypt.org)"


Let's Encrypt

Let's Encrypt is an easy way to set your site up for TLS (i.e. SSL). While there are security concerns about using Let's Encrypt, it's still better than not using TLS encryption at all. For this section, make sure you have an A record in your domain management console pointing at your server.

Next, install the SSL module:

a2enmod ssl

And then the Headers module:

 
a2enmod headers

Stop and start the Apache service:

apache2ctl -k stop; sleep 2; apache2ctl -k start

At this point, confirm that when you go to your domain, the MPOS portal opens up without issue. Make sure you don't have any plugin running that might block scripts. Also, use the developer tools to confirm headers and see any error messages that might pop up.

alt text

The following package is required but it will probably already be installed if you've been following along:

apt install software-properties-common -y

Next, run the following command:

add-apt-repository ppa:certbot/certbot

Here is the output for your reference:

[email protected]:/var/www/MPOS# add-apt-repository ppa:certbot/certbot

 This is the PPA for packages prepared by Debian Let's Encrypt Team and backported for Ubuntu(s).
 More info: https://launchpad.net/~certbot/+archive/ubuntu/certbot
Press [ENTER] to continue or ctrl-c to cancel adding it

gpg: keyring `/tmp/tmpeisg0c_2/secring.gpg' created
gpg: keyring `/tmp/tmpeisg0c_2/pubring.gpg' created
gpg: requesting key 75BCA694 from hkp server keyserver.ubuntu.com
gpg: /tmp/tmpeisg0c_2/trustdb.gpg: trustdb created
gpg: key 75XXXXXX: public key "Launchpad PPA for certbot" imported
gpg: Total number processed: 1
gpg:               imported: 1  (RSA: 1)
OK

Now just a few more commands:

apt update
apt install python-certbot-apache -y

And finally, request the certificate. This is the part where you must have ports 80 and 443 accessible to Let's Encrypt so that they can validate your domain and document root:

certbot --authenticator webroot --webroot-path /var/www/MPOS/public --installer apache -d <YourDomainName> --pre-hook "service apache2 stop" --post-hook "service apache2 stop"

Here is a sample output for your reference. Note that you should have a working email address for renewal notices. Also, the sample output below assumes that a redirect (i.e. 301 Moved Permanently) on the web server is desirable. If you plan on using a service like Cloudflare, you could do the redirect there instead instead of the web server:

[email protected]:/var/www/MPOS# certbot --authenticator webroot --webroot-path /var/www/MPOS/public --installer apache -d <YourDomainName> --pre-hook "service apache2 stop" --post-hook "service apache2 stop"
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Plugins selected: Authenticator webroot, Installer apache
Enter email address (used for urgent renewal and security notices) (Enter 'c' to
cancel): <YourEmailAddress>

-------------------------------------------------------------------------------
Please read the Terms of Service at
https://letsencrypt.org/documents/LE-SA-v1.2-November-15-2017.pdf. You must
agree in order to register with the ACME server at
https://acme-v01.api.letsencrypt.org/directory
-------------------------------------------------------------------------------
(A)gree/(C)ancel: A

-------------------------------------------------------------------------------
Would you be willing to share your email address with the Electronic Frontier
Foundation, a founding partner of the Let's Encrypt project and the non-profit
organization that develops Certbot? We'd like to send you email about EFF and
our work to encrypt the web, protect its users and defend digital rights.
-------------------------------------------------------------------------------
(Y)es/(N)o: Y
Running pre-hook command: service apache2 stop
Obtaining a new certificate
Performing the following challenges:
http-01 challenge for <YourDomainName>
Using the webroot path /var/www/MPOS/public for all unmatched domains.
Waiting for verification...
Cleaning up challenges
Running post-hook command: service apache2 stop
Created an SSL vhost at /etc/apache2/sites-enabled/000-default-le-ssl.conf
Deploying Certificate for <YourDomainName> to VirtualHost /etc/apache2/sites-enabled/000-default-le-ssl.conf

Please choose whether or not to redirect HTTP traffic to HTTPS, removing HTTP access.
-------------------------------------------------------------------------------
1: No redirect - Make no further changes to the webserver configuration.
2: Redirect - Make all requests redirect to secure HTTPS access. Choose this for
new sites, or if you're confident your site works on HTTPS. You can undo this
change by editing your web server's configuration.
-------------------------------------------------------------------------------
Select the appropriate number [1-2] then [enter] (press 'c' to cancel): 2
Enabled Apache rewrite module
Redirecting vhost in /etc/apache2/sites-enabled/000-default.conf to ssl vhost in /etc/apache2/sites-enabled/000-default-le-ssl.conf

-------------------------------------------------------------------------------
Congratulations! You have successfully enabled https://<YourDomainName>

You should test your configuration at:
https://www.ssllabs.com/ssltest/analyze.html?d=<YourDomainName>
-------------------------------------------------------------------------------

IMPORTANT NOTES:
 - Congratulations! Your certificate and chain have been saved at:
   /etc/letsencrypt/live/<YourDomainName>/fullchain.pem
   Your key file has been saved at:
   /etc/letsencrypt/live/<YourDomainName>/privkey.pem
   Your cert will expire on 2018-04-14. To obtain a new or tweaked
   version of this certificate in the future, simply run certbot again
   with the "certonly" option. To non-interactively renew *all* of
   your certificates, run "certbot renew"
 - Your account credentials have been saved in your Certbot
   configuration directory at /etc/letsencrypt. You should make a
   secure backup of this folder now. This configuration directory will
   also contain certificates and private keys obtained by Certbot so
   making regular backups of this folder is ideal.
 - If you like Certbot, please consider supporting our work by:

   Donating to ISRG / Let's Encrypt:   https://letsencrypt.org/donate
   Donating to EFF:                    https://eff.org/donate-le

Reload your website - it should now redirect to HTTPS. Use the following command to confirm the redirect as well as many other important details:

curl -vL <YourDomainName>

Hopefully you will have a stable server that keeps running. If so, you'll need to make sure your Let's Encrypt certificate renews as well since they are only good for 90 days. If you look in your cron.d directory you should see a cron job that will attempt to renew the certificate twice a day:

[email protected]:/var/www/MPOS# cat /etc/cron.d/certbot 
# /etc/cron.d/certbot: crontab entries for the certbot package
#
# Upstream recommends attempting renewal twice a day
#
# Eventually, this will be an opportunity to validate certificates
# haven't been revoked, etc.  Renewal will only occur if expiration
# is within 30 days.
SHELL=/bin/sh
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin

0 */12 * * * root test -x /usr/bin/certbot -a \! -d /run/systemd/system && perl -e 'sleep int(rand(3600))' && certbot -q renew

Try a test certificate update with the following command:

certbot renew --dry-run

Here is an example of the output:

[email protected]:/var/www/MPOS# certbot renew --dry-run
Saving debug log to /var/log/letsencrypt/letsencrypt.log

-------------------------------------------------------------------------------
Processing /etc/letsencrypt/renewal/<YourDomainName>.conf
-------------------------------------------------------------------------------
Cert not due for renewal, but simulating renewal for dry run
Plugins selected: Authenticator webroot, Installer apache
Running pre-hook command: service apache2 stop
Renewing an existing certificate
Performing the following challenges:
http-01 challenge for <YourDomainName>
Waiting for verification...
Cleaning up challenges

-------------------------------------------------------------------------------
new certificate deployed with reload of apache server; fullchain is
/etc/letsencrypt/live/<YourDomainName>/fullchain.pem
-------------------------------------------------------------------------------

-------------------------------------------------------------------------------
** DRY RUN: simulating 'certbot renew' close to cert expiry
**          (The test certificates below have not been saved.)

Congratulations, all renewals succeeded. The following certs have been renewed:
  /etc/letsencrypt/live/<YourDomainName>/fullchain.pem (success)
** DRY RUN: simulating 'certbot renew' close to cert expiry
**          (The test certificates above have not been saved.)
-------------------------------------------------------------------------------
Running post-hook command: service apache2 stop

IMPORTANT NOTES:
 - Your account credentials have been saved in your Certbot
   configuration directory at /etc/letsencrypt. You should make a
   secure backup of this folder now. This configuration directory will
   also contain certificates and private keys obtained by Certbot so
   making regular backups of this folder is ideal.

Finally, as you can see in the examples above, the root account is being used for Let's Encrypt's certbot. Read Does Certbot require root/administrator privileges? for more context and guidance on the best way to run in your environment.

TLS and Header Security

If you go to the Qualys SSL Server Test site, you can test how your Let's Encrypt certificate and MPOS site have TLS security configured. Out of the box, it will be better than some banks:

alt text

However, there are actually many other security settings that should be applied. Check out your score at securityheaders.io. Your initial score will paint a very different picture from Qualys:

alt text

Ouch. But no fear, let's fix these security issues.

If you've been following along, your /etc/apache2/sites-enabled/000-default.conf should look like this:

<VirtualHost *:80>
	# The ServerName directive sets the request scheme, hostname and port that
	# the server uses to identify itself. This is used when creating
	# redirection URLs. In the context of virtual hosts, the ServerName
	# specifies what hostname must appear in the request's Host: header to
	# match this virtual host. For the default virtual host (this file) this
	# value is not decisive as it is used as a last resort host regardless.
	# However, you must set it for any further virtual host explicitly.
	#ServerName www.example.com

	ServerAdmin [email protected]
	DocumentRoot /var/www/MPOS/public

	# Available loglevels: trace8, ..., trace1, debug, info, notice, warn,
	# error, crit, alert, emerg.
	# It is also possible to configure the loglevel for particular
	# modules, e.g.
	#LogLevel info ssl:warn

	ErrorLog ${APACHE_LOG_DIR}/error.log
	CustomLog ${APACHE_LOG_DIR}/access.log combined

	# For most configuration files from conf-available/, which are
	# enabled or disabled at a global level, it is possible to
	# include a line for only one particular virtual host. For example the
	# following line enables the CGI configuration for this host only
	# after it has been globally disabled with "a2disconf".
	#Include conf-available/serve-cgi-bin.conf
RewriteEngine on
RewriteCond %{SERVER_NAME} =<YourDomainName>
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

# vim: syntax=apache ts=4 sw=4 sts=4 sr noet

However, as pointed out in the messages when Let's Encrypt created our certificate, the SSL configurations are stored in /etc/apache2/sites-enabled/000-default-le-ssl.conf. The default configuration will look similar to this:

<IfModule mod_ssl.c>
<VirtualHost *:443>
	# The ServerName directive sets the request scheme, hostname and port that
	# the server uses to identify itself. This is used when creating
	# redirection URLs. In the context of virtual hosts, the ServerName
	# specifies what hostname must appear in the request's Host: header to
	# match this virtual host. For the default virtual host (this file) this
	# value is not decisive as it is used as a last resort host regardless.
	# However, you must set it for any further virtual host explicitly.
	#ServerName www.example.com

	ServerAdmin [email protected]
	DocumentRoot /var/www/MPOS/public

	# Available loglevels: trace8, ..., trace1, debug, info, notice, warn,
	# error, crit, alert, emerg.
	# It is also possible to configure the loglevel for particular
	# modules, e.g.
	#LogLevel info ssl:warn

	ErrorLog ${APACHE_LOG_DIR}/error.log
	CustomLog ${APACHE_LOG_DIR}/access.log combined

	# For most configuration files from conf-available/, which are
	# enabled or disabled at a global level, it is possible to
	# include a line for only one particular virtual host. For example the
	# following line enables the CGI configuration for this host only
	# after it has been globally disabled with "a2disconf".
	#Include conf-available/serve-cgi-bin.conf
ServerName <YourDomainName>
SSLCertificateFile /etc/letsencrypt/live/<YourDomainName>/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/<YourDomainName>/privkey.pem
Include /etc/letsencrypt/options-ssl-apache.conf
</VirtualHost>
</IfModule>

Getting into the details of web security is definitely out of scope for this guide however, you can try the following settings to get A+ from Qualys and securityheaders.io:

<IfModule mod_ssl.c>
<VirtualHost *:443>
	# The ServerName directive sets the request scheme, hostname and port that
	# the server uses to identify itself. This is used when creating
	# redirection URLs. In the context of virtual hosts, the ServerName
	# specifies what hostname must appear in the request's Host: header to
	# match this virtual host. For the default virtual host (this file) this
	# value is not decisive as it is used as a last resort host regardless.
	# However, you must set it for any further virtual host explicitly.
	#ServerName <YourDomainName>

	#ServerAdmin webmast[email protected]
	DocumentRoot /var/www/MPOS/public

	# Available loglevels: trace8, ..., trace1, debug, info, notice, warn,
	# error, crit, alert, emerg.
	# It is also possible to configure the loglevel for particular
	# modules, e.g.
	#LogLevel info ssl:warn

	ErrorLog ${APACHE_LOG_DIR}/error.log
	CustomLog ${APACHE_LOG_DIR}/access.log combined

	# For most configuration files from conf-available/, which are
	# enabled or disabled at a global level, it is possible to
	# include a line for only one particular virtual host. For example the
	# following line enables the CGI configuration for this host only
	# after it has been globally disabled with "a2disconf".
	#Include conf-available/serve-cgi-bin.conf
ServerName <YourDomainName>
SSLCertificateFile /etc/letsencrypt/live/<YourDomainName>/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/<YourDomainName>/privkey.pem
Include /etc/letsencrypt/options-ssl-apache.conf

SSLEngine On
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains"
Header always set X-Xss-Protection "1; mode=block"
Header always set X-Content-Type-Options "nosniff"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set Content-Security-Policy: "default-src 'none'; script-src 'self' 'unsafe-eval' 'unsafe-inline'; connect-src 'self'; img-src 'self'; style-src 'self' 'unsafe-inline'; font-src 'self';"
Header always set Referrer-Policy: no-referrer
Header edit Set-Cookie ^(.*)$ $1;HttpOnly;Secure
RequestHeader append "X-Forwarded-Proto" "https"
RequestHeader set "X-Forwarded-Ssl" "on"
</VirtualHost>

SSLProtocol -all +TLSv1.1 +TLSv1.2
SSLCipherSuite ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256
SSLHonorCipherOrder on
SSLCompression off
</IfModule>

After you make the change, be sure to stop and start the Apache server:

apache2ctl -k stop; sleep 2; apache2ctl -k start

Here are the results of the security changes:

Qualys

alt text

securityheaders.io

alt text

Like with anything related to security, the above changes will probably break something. Specifically, the CSP (Content Security Policy) so make sure to test well. In the above CSP, style-src 'self' 'unsafe-inline'; is used. Typically the 'unsafe-inline' keyword should be avoided but in the case of MPOS, not including it will prevent jQuery Sparklines from executing which will prevent some graphs from displaying. More work on MPOS would need to be done to setup a good CSP that is effective so keep that in mind.

NGINX

WIP

Stratum Testing

Make sure you start the stratum as the stratum user that you made previously. (i.e. non-root account) and run the following command to start it:

node init.js

Here is sample output as well as a live screenshot:

<YourOSLinuxUser>@ip-x-x-x-x:~/nomp$ node init.js 
2018-01-15 05:13:48 [POSIX]	[Connection Limit] (Safe to ignore) POSIX module not installed and resource (connection) limit was not raised
2018-01-15 05:13:48 [Master]	[CLI] CLI listening on 127.0.0.1:17117
2018-01-15 05:13:49 [Master]	[PoolSpawner] Spawned 1 pool(s) on 2 thread(s)
2018-01-15 05:13:49 [Switching]	[Setup] (Thread 1) Loading last proxy state from redis
2018-01-15 05:13:49 [Pool]	[verium] (Thread 1) No rewardRecipients have been setup which means no fees will be taken
2018-01-15 05:13:49 [Pool]	[verium] (Thread 1) Stratum Pool Server Started for verium [VRM] {scrypt-n}
						Network Connected:	Mainnet
						Detected Reward Type:	POS
						Current Block Height:	168976
						Current Connect Peers:	20
						Current Block Diff:	1221.774606336
						Network Difficulty:	1223.65280256
						Network Hash Rate:	NaN KH
						Stratum Port(s):	3332, 3333, 3334
						Pool Fee Percent:	0%
						Block polling every:	1000 ms
2018-01-15 05:13:49 [Switching]	[Setup] (scrypt-n) Setting proxy difficulties after pool start
alt text

The next thing you should do is in another terminal, confirm that the stratum ports configured are listening. Note in the output above, the line Stratum Port(s): 3332, 3333, 3334. These are the ports that should be listening.

At the command line, use the following command:

netstat -antup | grep LISTEN

Here is the sample output:

[email protected]:/# netstat -antup | grep LISTEN 
tcp        0      0 0.0.0.0:22              0.0.0.0:*               LISTEN      1300/sshd       
tcp        0      0 0.0.0.0:36988           0.0.0.0:*               LISTEN      755/veriumd     
tcp        0      0 127.0.0.1:17117         0.0.0.0:*               LISTEN      19975/node      
tcp        0      0 127.0.0.1:3306          0.0.0.0:*               LISTEN      32703/mysqld    
tcp        0      0 127.0.0.1:11211         0.0.0.0:*               LISTEN      11143/memcached 
tcp        0      0 127.0.0.1:6379          0.0.0.0:*               LISTEN      1208/redis-server 1
tcp6       0      0 :::80                   :::*                    LISTEN      17173/apache2   
tcp6       0      0 :::22                   :::*                    LISTEN      1300/sshd       
tcp6       0      0 :::443                  :::*                    LISTEN      17173/apache2   
tcp6       0      0 :::33987                :::*                    LISTEN      755/veriumd     
tcp6       0      0 :::3332                 :::*                    LISTEN      19975/node      
tcp6       0      0 :::3333                 :::*                    LISTEN      19975/node      
tcp6       0      0 :::3334                 :::*                    LISTEN      19975/node

Now we will setup a miner on a different machine. Make sure that the ports are accessible from your test client.

This example will assume an Ubuntu 16.04 server as the mining client. Use the following commands to setup effectsToCause/veriumMiner:

sudo apt update -y
sudo apt install -y git make automake autoconf pkg-config libcurl4-openssl-dev libjansson-dev libssl-dev libgmp-dev
git clone https://github.com/effectsToCause/veriumMiner
cd veriumMiner
sudo ./autogen.sh
sudo ./build.sh

Now it's time to run the miner. Note that it will fail because worker information has yet to be configured in MPOS. Below is a sample of what your output will look like on the client (i.e. miner) side:

[email protected]:~/veriumMiner$ ./cpuminer -o stratum+tcp://<YourDomainName>3333 -O this.will:fail -t x

 Verium Miner forked from cpuminer-multi 1.3-dev by [email protected] **

[2018-01-15 06:12:35] Starting Stratum on stratum+tcp://verium.win:3333
[2018-01-15 06:12:35] 4 miner threads started, using 'scrypt²' algorithm.
[2018-01-15 06:12:36] Stratum authentication failed
[2018-01-15 06:12:36] ...retry after 10 seconds
[2018-01-15 06:12:46] Stratum authentication failed

The stratum output (i.e. server) should generate the following error:

2018-01-15 06:12:07 [Pool]	[verium] (Thread 1) No new blocks for 55 seconds - updating transactions & rebroadcasting work
2018-01-15 06:12:35 [Pool]	[verium] (Thread 1) Unauthorized  this.will:fail [::ffff:x.x.x.x]
2018-01-15 06:12:46 [Pool]	[verium] (Thread 2) Unauthorized  this.will:fail [::ffff:x.x.x.x]
2018-01-15 06:12:56 [Pool]	[verium] (Thread 1) Unauthorized  this.will:fail [::ffff:x.x.x.x]

This example confirms that the client miner can access the server stratum on port 3333. Repeat the same steps for the other ports you have configured.

Stratum Worker Setup and Testing

Now that we know that the miner and stratum server can connect, login with the MPOS admin account and setup a worker. Don't forget to turn on monitoring.

alt text

When you run the test client miner, you should see the following output:

alt text

The stratum server should show a successful connection. Entries that show that the shares are being sent to the MySQL database should also display. Here is a screenshot of it in action:

alt text

And finally, the MPOS dashboard should show the miner activity. Note that the accuracy of the MPOS dashboard metrics still needs work <citation needed>.

alt text

Mailers and Email

You will want a reliable way to send emails to your pool's users. There are many services to do this, Mailgun is one. Follow this easy to understand guide, Configure Postfix to use Mailgun SMTP Relay on Ubuntu to setup Mailgun on Ubuntu.

Also, you'll need an email address to receive messages from the MPOS contact form. Try to separate this from your regular email account so you don't miss important inquiries. Since you'll be using your own domain, you'd get setup an email called <yourpoolname>[email protected]<yourdomain.com>

There is a lot to talk about on this topic but for now, the bare minimum has been mentioned for your reference and further exploration.