Merge pull request #371 from NebulousLabs/safe-restart-scripts

add safe stop and restart sia scripts
This commit is contained in:
Karol Wypchło 2020-09-18 17:08:19 +02:00 committed by GitHub
commit dc73367a66
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 73 additions and 77 deletions

View File

@ -18,11 +18,13 @@ List of available parameters:
## Contributing ## Contributing
### Testing you Code ### Testing you Code
Before pushing your code you should verify that it will pass our online test Before pushing your code you should verify that it will pass our online test
suite. suite.
**Cypress Tests** **Cypress Tests**
Verify the Cypress test suite by doing the following: Verify the Cypress test suite by doing the following:
1. In one terminal screen run `GATSBY_API_URL=https://siasky.net yarn workspace webapp start` 1. In one terminal screen run `GATSBY_API_URL=https://siasky.net yarn workspace webapp start`
1. In a second terminal screen run `yarn workspace webapp cypress run` 1. In a second terminal screen run `yarn workspace webapp cypress run`

18
scripts/portal-down.sh Executable file
View File

@ -0,0 +1,18 @@
#!/bin/bash
set -e # exit on first error
countdown() {
local secs=$1
while [ $secs -gt 0 ]; do
echo -ne "Waiting $secs\033[0K\r"
sleep 1
: $((secs--))
done
}
# stop healh-check so the server is taken our of load balancer
docker exec health-check cli/disable
# then wait 5 minutes for the load balancer to propagate the dns records
countdown 300

6
scripts/portal-up.sh Executable file
View File

@ -0,0 +1,6 @@
#!/bin/bash
set -e # exit on first error
# start the health-checks service
docker exec health-check cli/enable

17
scripts/portal-upgrade.sh Executable file
View File

@ -0,0 +1,17 @@
#!/bin/bash
set -e # exit on first error
# get current working directory (pwd doesn't cut it)
cwd=$(cd -P -- "$(dirname -- "$0")" && pwd -P)
# put the server down for maintenance
. ${cwd}/portal-down.sh
# rebuild and restart all docker containers
docker-compose build --no-cache
docker-compose down
docker-compose up -d
# enable the server again
. ${cwd}/portal-up.sh

View File

@ -15,21 +15,22 @@ You may want to fork this repository and replace ssh keys in
- [sia](https://sia.tech) ([docker hub](https://hub.docker.com/r/nebulouslabs/sia)): storage provider, heart of the portal setup - [sia](https://sia.tech) ([docker hub](https://hub.docker.com/r/nebulouslabs/sia)): storage provider, heart of the portal setup
- [caddy](https://caddyserver.com) ([docker hub](https://hub.docker.com/r/caddy/caddy)): reverse proxy (similar to nginx) that handles ssl out of a box and acts as a transparent entry point - [caddy](https://caddyserver.com) ([docker hub](https://hub.docker.com/r/caddy/caddy)): reverse proxy (similar to nginx) that handles ssl out of a box and acts as a transparent entry point
- [openresty](https://openresty.org) ([docker hub](https://hub.docker.com/r/openresty/openresty)): nginx custom build, acts as a cached proxy to siad and exposes all api endpoints - [openresty](https://openresty.org) ([docker hub](https://hub.docker.com/r/openresty/openresty)): nginx custom build, acts as a cached proxy to siad and exposes all api endpoints
- health-check: this is a simple service that runs periodically and collects health data about the server (status and response times) and exposes `/health-check` api endpoint that is deliberately delayed based on the response times of the server so potential load balancer could prioritize servers based on that (we use it with cloudflare) - [health-check](https://github.com/NebulousLabs/skynet-webportal/tree/master/packages/health-check): simple service that runs periodically and collects health data about the server (status and response times) - [read more](https://github.com/NebulousLabs/skynet-webportal/blob/master/packages/health-check/README.md)
- siad setup: we use "double siad" setup that has one node solely for download and one for upload to improve performance - [handshake](https://handshake.org) ([github](https://github.com/handshake-org/hsd)): full handshake node
- we use systemd to manage siad service - [handshake-api](https://github.com/NebulousLabs/skynet-webportal/tree/master/packages/handshake-api): simple API talking to the handshake node - [read more](https://github.com/NebulousLabs/skynet-webportal/blob/master/packages/handshake-api/README.md)
- siad is not installed as docker service for improved performance - [webapp](https://github.com/NebulousLabs/skynet-webportal/tree/master/packages/webapp): portal frontend application - [read more](https://github.com/NebulousLabs/skynet-webportal/blob/master/packages/webapp/README.md)
- discord integration - discord integration
- [funds-checker](funds-checker.py): script that checks wallet balance and sends status messages to discord periodically - [funds-checker](funds-checker.py): script that checks wallet balance and sends status messages to discord periodically
- [health-checker](health-checker.py): script that monitors health-check service for server health issues and reports them to discord periodically
- [log-checker](log-checker.py): script that scans siad logs for critical errors and reports them to discord periodically - [log-checker](log-checker.py): script that scans siad logs for critical errors and reports them to discord periodically
- [blacklist-skylink](blacklist-skylink.sh): script that can be run locally from a machine that has access to all your skynet portal servers that blacklists provided skylink and prunes nginx cache to ensure it's not available any more (that is a bit much but that's the best we can do right now without paid nginx version) - if you want to use it, make sure to adjust the server addresses - [blacklist-skylink](../scripts/blacklist-skylink.sh): script that can be run locally from a machine that has access to all your skynet portal servers that blacklists provided skylink and prunes nginx cache to ensure it's not available any more (that is a bit much but that's the best we can do right now without paid nginx version) - if you want to use it, make sure to adjust the server addresses
### Step 1: setting up server user ### Step 1: setting up server user
1. SSH in a freshly installed Debian machine on a user with sudo access (can be root) 1. SSH in a freshly installed Debian machine on a user with sudo access (can be root)
1. `apt-get update && apt-get install sudo` to make sure `sudo` is available 1. `apt-get update && apt-get install sudo -y` to make sure `sudo` is available
1. `adduser user` to create user called `user` (creates `/home/user` directory) 1. `adduser user` to create user called `user` (creates `/home/user` directory)
1. `usermod -a -G sudo user` to add this new user to sudo group 1. `usermod -aG sudo user` to add this new user to sudo group
1. Quit the ssh session with `exit` command 1. Quit the ssh session with `exit` command
You a can now ssh into your machine as the user `user`. You a can now ssh into your machine as the user `user`.
@ -42,7 +43,7 @@ You a can now ssh into your machine as the user `user`.
**Following step will be executed on remote host logged in as a `user`:** **Following step will be executed on remote host logged in as a `user`:**
1. `sudo apt-get install git` to install git 1. `sudo apt-get install git -y` to install git
1. `git clone https://github.com/NebulousLabs/skynet-webportal` 1. `git clone https://github.com/NebulousLabs/skynet-webportal`
1. run setup scripts in the exact order and provide sudo password when asked (if one of them fails, you can retry just this one before proceeding further) 1. run setup scripts in the exact order and provide sudo password when asked (if one of them fails, you can retry just this one before proceeding further)
1. `/home/user/skynet-webportal/setup-scripts/setup-server.sh` 1. `/home/user/skynet-webportal/setup-scripts/setup-server.sh`
@ -74,12 +75,11 @@ At this point we have almost everything running, we just need to set up your wal
### Step 4: configuring docker services ### Step 4: configuring docker services
1. generate and copy sia api token `printf ":$(cat /home/user/.sia/apipassword)" | base64`
1. edit `/home/user/skynet-webportal/.env` and configure following environment variables 1. edit `/home/user/skynet-webportal/.env` and configure following environment variables
- `DOMAIN_NAME` (optional) is your domain name if you have it - `DOMAIN_NAME` (optional) is your domain name if you have it
- `EMAIL_ADDRESS` (required) is your email address used for communication regarding SSL certification (required) - `EMAIL_ADDRESS` (required) is your email address used for communication regarding SSL certification (required)
- `SIA_WALLET_PASSWORD` (required) is your wallet password (or seed if you did not set a password) - `SIA_WALLET_PASSWORD` (required) is your wallet password (or seed if you did not set a password)
- `HSD_API_KEY` (optional) this is a random security key for an optional handshake integration that gets generated automatically - `HSD_API_KEY` (optional) this is a random security key for a handshake integration that gets generated automatically
- `CLOUDFLARE_AUTH_TOKEN` (optional) if using cloudflare as dns loadbalancer (need to change it in Caddyfile too) - `CLOUDFLARE_AUTH_TOKEN` (optional) if using cloudflare as dns loadbalancer (need to change it in Caddyfile too)
- `AWS_ACCESS_KEY_ID` (optional) if using route53 as a dns loadbalancer - `AWS_ACCESS_KEY_ID` (optional) if using route53 as a dns loadbalancer
- `AWS_SECRET_ACCESS_KEY` (optional) if using route53 as a dns loadbalancer - `AWS_SECRET_ACCESS_KEY` (optional) if using route53 as a dns loadbalancer
@ -90,21 +90,24 @@ At this point we have almost everything running, we just need to set up your wal
## Useful Commands ## Useful Commands
- Starting the whole stack
> `docker-compose up -d`
- Stopping the whole stack
> `docker-compose down`
- Accessing siac - Accessing siac
> `docker exec -it sia siac` > `docker exec -it sia siac`
- Checking status of siad service - Portal maintenance
> `systemctl --user status siad` - Pulling portal out for maintenance
- Stopping siad service > `scripts/portal-down.sh`
> `systemctl --user stop siad` - Putting portal back into place after maintenance
- Starting siad service > `scripts/portal-up.sh`
> `systemctl --user start siad` - Upgrading portal containers (takes care of pulling it and putting it back)
- Restarting siad service > `scripts/portal-upgrade.sh`
> `systemctl --user restart siad` - Restarting caddy gracefully after making changes to Caddyfile (no downtime)
- Restarting caddy gracefully after making changes to Caddyfile
> `docker exec caddy caddy reload --config /etc/caddy/Caddyfile` > `docker exec caddy caddy reload --config /etc/caddy/Caddyfile`
- Restarting nginx gracefully after making changes to nginx configs - Restarting nginx gracefully after making changes to nginx configs (no downtime)
> `docker exec nginx openresty -s reload` > `docker exec nginx openresty -s reload`
- Checking siad service logs (last hour) - Checking siad service logs (since last hour)
> `docker logs --since 1h $(docker ps -q --filter "name=^sia$")` > `docker logs --since 1h $(docker ps -q --filter "name=^sia$")`
- Checking caddy logs (for example in case ssl certificate fails) - Checking caddy logs (for example in case ssl certificate fails)
> `docker logs caddy -f` > `docker logs caddy -f`

View File

@ -12,6 +12,9 @@ sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io sudo apt-get install -y docker-ce docker-ce-cli containerd.io
docker --version # sanity check docker --version # sanity check
# add user to docker group to avoid having to use sudo for every docker command
sudo usermod -aG docker user
# Install docker-compose # Install docker-compose
sudo curl -L "https://github.com/docker/compose/releases/download/1.25.5/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose sudo curl -L "https://github.com/docker/compose/releases/download/1.25.5/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose sudo chmod +x /usr/local/bin/docker-compose

View File

@ -1,53 +0,0 @@
#!/usr/bin/env bash
LOGFILE=$1
SIA_PORT=${SIA_PORT:-9980}
# This is a logger service that pulls some current skynet stats and appends them to json log file.
# You should probably run it using crontab, most likely as a root due to access_log read restrictions.
#
# basic usage:
# /home/user/skynet-webportal/setup-scripts/stats-logger.sh public/logs.json
#
# usage with custom sia port:
# SIA_PORT=9970 /home/user/skynet-webportal/setup-scripts/stats-logger.sh public/logs.json
#
# configuring hourly logging with crontab (run crontab -e)
# 0 * * * * /home/user/skynet-webportal/setup-scripts/stats-logger.sh /home/user/skynet-webportal/public/stats.json >/dev/null 2>&1
if ! [ -x "$(command -v jq)" ]; then
echo 'Error: jq is not installed. Please install with `sudo apt-get install jq`.' >&2
exit 1
fi
if ! [ -x "$(command -v sponge)" ]; then
echo 'Error: sponge is not installed. Please install with `sudo apt-get install moreutils`.' >&2
exit 1
fi
if [ -z "$LOGFILE" ]; then
echo 'Error: You need to specify json log file name.' >&2
exit 1
fi
# create logfile if it doesn't exist and initialize it with empty array
if [ ! -f "$LOGFILE" ]; then
mkdir -p "`dirname \"$LOGFILE\"`" 2>/dev/null
echo [] > $LOGFILE
fi
# get downloads count from nginx logs
awk -vDate=`date -d'now-1 hours' +[%d/%b/%Y:%H:%M:%S` ' { if ($4 > Date) print $0}' /var/log/nginx/access.log > /var/log/nginx/access_last_hour.log
DOWNLOADS_COUNT_LAST_HOUR=$(awk '{print $7}' /var/log/nginx/access_last_hour.log | grep -E '/[a-zA-Z0-9_-]{46}(/.*)?' | wc -l)
# get siac output
SKYNET_LS=$(/home/user/go/bin/siac skynet ls --addr localhost:${SIA_PORT} | grep -i listing)
SKYNET_LS_REGEX="Listing (.*) files\/dirs:\s+(.*)"
if [[ "${SKYNET_LS}" =~ $SKYNET_LS_REGEX ]]; then
SKYFILES_COUNT="${BASH_REMATCH[1]}"
SKYFILES_SIZE_BYTES=$(echo ${BASH_REMATCH[2]} | sed -r 's/[ B]//g' | numfmt --from=iec)
fi
DATE=$(date -u +"%Y-%m-%d %H:%M:%S")
LOG_ENTRY=$(echo {\"date\":\"${DATE}\", \"skyfiles_count\":${SKYFILES_COUNT}, \"skyfiles_size_bytes\":${SKYFILES_SIZE_BYTES}, \"downloads_count_last_hour\":${DOWNLOADS_COUNT_LAST_HOUR}})
jq -c ". += [${LOG_ENTRY}]" $LOGFILE | sponge $LOGFILE