403 lines
11 KiB
Bash
Executable File
403 lines
11 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
set -exo pipefail
|
|
|
|
BLUE_BOLD=$'\e[1;34m'
|
|
RESET=$'\e[0m'
|
|
|
|
checkpoint=$(cat ./hmn_setup_checkpoint || echo 0)
|
|
|
|
savecheckpoint() {
|
|
echo $1 > ./hmn_setup_checkpoint
|
|
}
|
|
|
|
do_as() {
|
|
sudo -u $1 --preserve-env=PATH bash -s
|
|
}
|
|
|
|
# Add swap space
|
|
# https://www.digitalocean.com/community/tutorials/how-to-add-swap-space-on-ubuntu-20-04
|
|
if [ $checkpoint -lt 10 ]; then
|
|
fallocate -l 1G /swapfile
|
|
chmod 600 /swapfile
|
|
mkswap /swapfile
|
|
swapon /swapfile
|
|
swapon --show
|
|
echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab
|
|
sysctl vm.swappiness=10
|
|
sysctl vm.vfs_cache_pressure=50
|
|
echo 'vm.swappiness=10' >> /etc/sysctl.conf
|
|
echo 'vm.vfs_cache_pressure=50' >> /etc/sysctl.conf
|
|
|
|
savecheckpoint 10
|
|
fi
|
|
|
|
# Configure Linux users
|
|
if [ $checkpoint -lt 20 ]; then
|
|
groupadd --system caddy
|
|
useradd --system \
|
|
--gid caddy \
|
|
--shell /bin/bash \
|
|
--create-home --home-dir /home/caddy \
|
|
caddy
|
|
groupadd --system hmn
|
|
useradd --system \
|
|
--gid hmn \
|
|
--shell /bin/bash \
|
|
--create-home --home-dir /home/hmn \
|
|
hmn
|
|
groupadd --system annotations
|
|
useradd --system \
|
|
--gid annotations \
|
|
--shell /bin/bash \
|
|
--create-home --home-dir /home/annotations \
|
|
annotations
|
|
usermod -a -G annotations hmn
|
|
|
|
savecheckpoint 20
|
|
fi
|
|
|
|
# Install important stuff
|
|
if [ $checkpoint -lt 30 ]; then
|
|
apt update
|
|
apt install -y \
|
|
build-essential \
|
|
libcurl4-openssl-dev byacc flex \
|
|
s3cmd
|
|
|
|
savecheckpoint 30
|
|
fi
|
|
|
|
# Install Go
|
|
if [ $checkpoint -lt 40 ]; then
|
|
wget https://golang.org/dl/go1.17.linux-amd64.tar.gz
|
|
tar -C /usr/local -xzf go1.17.linux-amd64.tar.gz
|
|
|
|
export PATH=$PATH:/usr/local/go/bin:/root/go/bin
|
|
echo 'export PATH=$PATH:/usr/local/go/bin:/root/go/bin' >> ~/.bashrc
|
|
go version
|
|
|
|
do_as hmn <<'SCRIPT'
|
|
set -euxo pipefail
|
|
echo 'export PATH=$PATH:/usr/local/go/bin:/home/hmn/go/bin' >> ~/.bashrc
|
|
go version
|
|
SCRIPT
|
|
|
|
savecheckpoint 40
|
|
fi
|
|
|
|
export PATH=$PATH:/usr/local/go/bin:/root/go/bin
|
|
|
|
# Install Caddy
|
|
# https://www.digitalocean.com/community/tutorials/how-to-host-a-website-with-caddy-on-ubuntu-18-04
|
|
if [ $checkpoint -lt 50 ]; then
|
|
go install github.com/caddyserver/xcaddy/cmd/xcaddy@v0.1.9
|
|
xcaddy build \
|
|
--with github.com/caddy-dns/cloudflare \
|
|
--with github.com/aksdb/caddy-cgi/v2
|
|
mv caddy /usr/bin
|
|
chown root:root /usr/bin/caddy
|
|
chmod 755 /usr/bin/caddy
|
|
|
|
savecheckpoint 50
|
|
fi
|
|
|
|
# Install Postgres
|
|
# (instructions at https://www.postgresql.org/download/linux/ubuntu/)
|
|
if [ $checkpoint -lt 60 ]; then
|
|
sudo sh -c 'echo "deb http://apt.postgresql.org/pub/repos/apt $(lsb_release -cs)-pgdg main" > /etc/apt/sources.list.d/pgdg.list'
|
|
wget --quiet -O - https://www.postgresql.org/media/keys/ACCC4CF8.asc | sudo apt-key add -
|
|
sudo apt-get update
|
|
sudo apt-get -y install postgresql
|
|
|
|
savecheckpoint 60
|
|
fi
|
|
|
|
# Configure Postgres
|
|
if [ $checkpoint -lt 70 ]; then
|
|
echo "Enter the password for the HMN postgres user:"
|
|
sudo -u postgres createuser --createdb --login --pwprompt hmn
|
|
|
|
savecheckpoint 70
|
|
fi
|
|
|
|
# Set up the folder structure
|
|
if [ $checkpoint -lt 80 ]; then
|
|
set +x
|
|
|
|
do_as hmn <<'SCRIPT'
|
|
cd ~
|
|
mkdir log
|
|
mkdir bin
|
|
|
|
echo 'export PATH=$PATH:/home/hmn/bin' >> ~/.bashrc
|
|
SCRIPT
|
|
|
|
savecheckpoint 80
|
|
fi
|
|
|
|
# Set up SSH for hmn
|
|
if [ $checkpoint -lt 81 ]; then
|
|
set +x
|
|
|
|
do_as hmn <<'SCRIPT'
|
|
ssh-keygen -t ed25519 -C "beta-server" -N "" -f ~/.ssh/gitlab-hmn
|
|
git config --global core.sshCommand "ssh -i ~/.ssh/gitlab-hmn"
|
|
SCRIPT
|
|
|
|
do_as annotations <<'SCRIPT'
|
|
ssh-keygen -t ed25519 -C "beta-server" -N "" -f ~/.ssh/gitlab-annotation-system
|
|
ssh-keygen -t ed25519 -C "beta-server" -N "" -f ~/.ssh/gitlab-hmml
|
|
SCRIPT
|
|
|
|
echo ""
|
|
echo "Add the following keys as Deploy Keys to the following projects:"
|
|
echo ""
|
|
cat /home/hmn/.ssh/gitlab-hmn.pub
|
|
echo "https://git.handmade.network/hmn/hmn/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
cat /home/annotations/.ssh/gitlab-annotation-system.pub
|
|
echo "https://git.handmade.network/Annotation-Pushers/Annotation-System/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
cat /home/annotations/.ssh/gitlab-hmml.pub
|
|
echo "https://git.handmade.network/Annotation-Pushers/cinera_handmade.network/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
echo "Run this script again when you're done - it will continue where it left off."
|
|
|
|
savecheckpoint 81
|
|
|
|
# This is a special case, where we want to halt the script and allow the
|
|
# user to perform an action before moving on.
|
|
exit 0
|
|
fi
|
|
|
|
# Test SSH for hmn
|
|
if [ $checkpoint -lt 82 ]; then
|
|
do_as hmn <<'SCRIPT'
|
|
set -euxo pipefail
|
|
|
|
if ! ssh -T -i ~/.ssh/gitlab-hmn git@git.handmade.network; then
|
|
set +x
|
|
|
|
echo "Copy the following key:"
|
|
echo ""
|
|
cat ~/.ssh/gitlab-hmn
|
|
echo ""
|
|
echo "Add it as a Deploy Key to the HMN project in GitLab:"
|
|
echo ""
|
|
echo " https://git.handmade.network/hmn/hmn/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
exit 1
|
|
fi
|
|
SCRIPT
|
|
|
|
do_as annotations <<'SCRIPT'
|
|
if ! ssh -T -i ~/.ssh/gitlab-annotation-system git@git.handmade.network; then
|
|
set +x
|
|
|
|
echo "Copy the following key:"
|
|
echo ""
|
|
cat ~/.ssh/gitlab-annotation-system
|
|
echo ""
|
|
echo "Add it as a Deploy Key to this project in GitLab:"
|
|
echo ""
|
|
echo " https://git.handmade.network/Annotation-Pushers/Annotation-System/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
exit 1
|
|
fi
|
|
|
|
if ! ssh -T -i ~/.ssh/gitlab-hmml git@git.handmade.network; then
|
|
set +x
|
|
|
|
echo "Copy the following key:"
|
|
echo ""
|
|
cat ~/.ssh/gitlab-hmml
|
|
echo ""
|
|
echo "Add it as a Deploy Key to this project in GitLab:"
|
|
echo ""
|
|
echo " https://git.handmade.network/Annotation-Pushers/cinera_handmade.network/-/settings/ci_cd#js-deploy-keys-settings"
|
|
echo ""
|
|
exit 1
|
|
fi
|
|
SCRIPT
|
|
|
|
savecheckpoint 82
|
|
fi
|
|
|
|
# Clone the repo
|
|
if [ $checkpoint -lt 90 ]; then
|
|
do_as hmn <<'SCRIPT'
|
|
set -euxo pipefail
|
|
|
|
cd ~
|
|
git clone git@git.handmade.network:hmn/hmn.git
|
|
SCRIPT
|
|
|
|
savecheckpoint 90
|
|
fi
|
|
|
|
# Copy config files to the right places
|
|
if [ $checkpoint -lt 100 ]; then
|
|
cp /home/hmn/hmn/server/Caddyfile /home/caddy/Caddyfile
|
|
|
|
cp /home/hmn/hmn/server/caddy.service /etc/systemd/system/caddy.service
|
|
cp /home/hmn/hmn/server/hmn.service /etc/systemd/system/hmn.service
|
|
cp /home/hmn/hmn/server/cinera.service /etc/systemd/system/cinera.service
|
|
chmod 644 /etc/systemd/system/caddy.service
|
|
chmod 644 /etc/systemd/system/hmn.service
|
|
chmod 644 /etc/systemd/system/cinera.service
|
|
|
|
cp /home/hmn/hmn/server/logrotate /etc/logrotate.d/hmn
|
|
|
|
cp /home/hmn/hmn/src/config/config.go.example /home/hmn/hmn/src/config/config.go
|
|
cp /home/hmn/hmn/server/hmn.conf.example /home/hmn/hmn/server/hmn.conf
|
|
cp /home/hmn/hmn/adminmailer/config.go.example /home/hmn/hmn/adminmailer/config.go
|
|
cp /home/hmn/hmn/cinera/cinera.conf.sample /home/hmn/hmn/cinera/cinera.conf
|
|
chown hmn:hmn /home/hmn/hmn/src/config/config.go
|
|
chown hmn:hmn /home/hmn/hmn/server/hmn.conf
|
|
chown hmn:hmn /home/hmn/hmn/cinera/cinera.conf
|
|
|
|
cp /home/hmn/hmn/server/.s3cfg /home/hmn/.s3cfg
|
|
chown hmn:hmn /home/hmn/.s3cfg
|
|
chmod 600 /home/hmn/.s3cfg
|
|
|
|
cp /home/hmn/hmn/server/root.Makefile /root/Makefile
|
|
|
|
systemctl daemon-reload
|
|
|
|
savecheckpoint 100
|
|
fi
|
|
|
|
# Set up crons
|
|
if [ $checkpoint -lt 105 ]; then
|
|
# See https://stackoverflow.com/a/9625233/1177139
|
|
(crontab -l 2>/dev/null; echo "50 4 * * * /home/hmn/hmn/server/backup.sh") | crontab -
|
|
|
|
# TODO: This seems to fail the first time you run it? But then works fine afterward, thanks
|
|
# to checkpoints. Probably should fix this someday.
|
|
|
|
savecheckpoint 105
|
|
fi
|
|
|
|
# Build the site for the first time (despite bad config)
|
|
if [ $checkpoint -lt 110 ]; then
|
|
do_as hmn <<'SCRIPT'
|
|
set -euxo pipefail
|
|
|
|
cd /home/hmn/hmn
|
|
echo "Building the site for the first time. This may take a while..."
|
|
go build -v -o /home/hmn/bin/hmn src/main.go
|
|
SCRIPT
|
|
|
|
echo 'PATH=$PATH:/home/hmn/bin' >> ~/.bashrc
|
|
source ~/.bashrc
|
|
|
|
savecheckpoint 110
|
|
fi
|
|
|
|
cat <<HELP
|
|
Everything has been successfully installed!
|
|
|
|
${BLUE_BOLD}===== Next steps =====${RESET}
|
|
|
|
First, make sure you have everything on your path:
|
|
|
|
source ~/.bashrc
|
|
|
|
${BLUE_BOLD}Edit the Caddy config${RESET}
|
|
|
|
Get an API token from Cloudflare. The token must have the Zone / Zone / Read and
|
|
Zone / DNS / Edit permissions (as laid out in the following links).
|
|
|
|
https://github.com/caddy-dns/cloudflare
|
|
https://github.com/libdns/cloudflare
|
|
|
|
Then edit the Caddyfile:
|
|
|
|
vim /home/caddy/Caddyfile
|
|
|
|
Add the Cloudflare token to allow the ACME challenge to succeed, and add
|
|
the correct domains. (Don't forget to include both the normal and wildcard
|
|
domains.)
|
|
|
|
Also, in the CGI config, add the name of the Git branch you would like to
|
|
use when deploying. For example, a deployment of the beta site should use
|
|
the 'beta' branch.
|
|
|
|
${BLUE_BOLD}Edit the website config${RESET}
|
|
|
|
Edit the config file using a special make task:
|
|
|
|
make edit-config
|
|
|
|
Fill out everything, then rebuild the site:
|
|
|
|
make build
|
|
|
|
You don't need to deploy the site yet; wait until you've
|
|
configured everything.
|
|
|
|
${BLUE_BOLD}Edit HMN environment vars${RESET}
|
|
|
|
First, go to GitLab and add a webhook with a secret. Set it to trigger on
|
|
push events for the branch you are using for deploys.
|
|
|
|
https://git.handmade.network/hmn/hmn/hooks
|
|
|
|
Then, edit the following file and fill in all the environment vars, including
|
|
the secret value from the GitLab webhook:
|
|
|
|
/home/hmn/hmn/server/hmn.conf
|
|
|
|
${BLUE_BOLD}Configure s3cmd${RESET}
|
|
|
|
Edit the following file:
|
|
|
|
/home/hmn/.s3cfg
|
|
|
|
Add the DigitalOcean Spaces credentials, and ensure that the bucket info is correct.
|
|
|
|
${BLUE_BOLD}Configure Cinera${RESET}
|
|
|
|
Edit the following file, adding the correct domain:
|
|
|
|
/home/hmn/hmn/cinera/cinera.conf
|
|
|
|
${BLUE_BOLD}Configure the admin mailer${RESET}
|
|
|
|
Fill in the config file and build the mailer:
|
|
|
|
cd /home/hmn/hmn/adminmailer
|
|
vim config.go
|
|
go build -o /usr/bin/adminmailer .
|
|
|
|
${BLUE_BOLD}Download and restore a database backup${RESET}
|
|
|
|
make download-database
|
|
|
|
su hmn
|
|
cd ~
|
|
hmn seedfile <your backup file>
|
|
hmn migrate
|
|
|
|
${BLUE_BOLD}Restore static files${RESET}
|
|
|
|
make restore-static-files
|
|
|
|
${BLUE_BOLD}Set up Cinera${RESET}
|
|
|
|
cd /home/hmn/hmn/cinera
|
|
./setup.sh
|
|
|
|
${BLUE_BOLD}Start up Caddy${RESET}
|
|
|
|
systemctl start caddy
|
|
|
|
${BLUE_BOLD}Deploy the site!${RESET}
|
|
|
|
make deploy
|
|
|
|
Run 'make' on its own to see all the other tasks available to you!
|
|
|
|
HELP
|