#!/bin/bash
#
# SCC Hyperscale Bootstrapper
#
# This script bootstraps and configure Hyperscale prerequisites
# so full deployment can be triggered from SCC HyperScale NOC:
# - installation of SCC RPM packages repositories
# - installation & configuration of SCC's BED-ping daemon
# - installation & configuration of Teleport with trusted cluster
#   association on Hyperscale NOC
#
# It requires the following inputs:
# - the Hyperscale "Common Name" (CN) subject's X.509 certificate
# - the "airgap" flag mode
#
# The provisionning of the Hyperscale product itself is triggered from
# NOC Ansible controller through teleport
#
# Usage example:
#   curl -s https://installer.noc.scc-hyperscale.net/hyperscale-bootstrap.sh | bash -s -- -c CU0001-12345.CT1234-5678
#
# initial write: Eric Belhomme <ebelhomme@fr.scc.com>
# Copyright by SCC France SA (2023 & onwards)

PATH=/usr/sbin:/usr/bin:/sbin:/bin:/usr/local/sbin:/usr/local/bin
HEAVENDOOR='heavendoor.scc-services.fr'
ELRELEASE="$(sed -E 's/^.* ([0-9]+)\.[0-9\.]+ .*/\1/' /etc/redhat-release)"
CN=
AIRGAP=
PKI=

die() {
    echo -e "$1"
    test -n "$2" && exit "$2" || exit 1
}

if [ $UID -ne 0 ]; then
    die "\e[1;31mError :\e[22m the Hyperscale bootstrapper requires root privileges to execute\e[0m"
fi

if [ "$ELRELEASE" -lt "8" ]; then
    die "\e[1;31mError :\e[22m Unsupported Linux distribution. Please reinstall to EL8 or EL9\e[0m"
fi

print_help() {
cat <<EOF

                      ---<  SCC - Hyperscale - Online bootstrapper  >---
                    ---        Run as root user with argument:         ---
                      --------------------------------------------------

bash <(curl -s https://installer.noc.scc-hyperscale.net/hyperscale-bootstrap.sh [ -c CN ]  [ -a ]

  -c <Common Name> : Hyperscale certificate's CN
  -a               : airgap installation mode (d/l all resources from SCC's NOC artifacts servers)

EOF
    exit 1
}

while getopts ahc: arg; do
    case "$arg" in
        h) print_help;;
        c) CN=$OPTARG;;
        a) AIRGAP='yes';;
        *) print_help;;
    esac
done

# retrieve Hyperscale X.509 certificate from published PKIs (production/staging)
test -z "$CN" && print_help
for item in 'hyperscale-consumers' 'hyperscale-consumers-staging'; do
    RC="$(curl -so "/etc/pki/tls/certs/${CN}.crt" -w "%{http_code}" "https://pki.scc-hyperscale.net/${item}/issued/${CN}.crt")"
    if [ "$RC" == '200' ]; then
        PKI="$item"
        break
    fi
done
if [ -z "$PKI" ]; then
    die "Fatal: unable to get certificate CN $CN"
fi
chmod 0644 "/etc/pki/tls/certs/${CN}.crt"
chown root.root "/etc/pki/tls/certs/${CN}.crt"

# First ping SecurBridge to allow access to SCC packages mirror
test -f /usr/bin/openssl || dnf install -y openssl
TOKEN="$(openssl x509 -noout -in "/etc/pki/tls/certs/${CN}.crt" -fingerprint -sha512 | cut -d'=' -f2)"
curl -s "https://${HEAVENDOOR}/api/v1/ping/${TOKEN}" || die "\e[1;31mError :\e[22m Failed to ping SecurBridge at ${HEAVENDOOR}\e[0m"
SECURBRIDGE_OK=0
# shellcheck disable=SC2034
for i in $(seq 1 12); do
    curl https://packages.scc-services.fr &> /dev/null && SECURBRIDGE_OK=1 && break
    sleep 5
done
if [ "$SECURBRIDGE_OK" -ne 1 ]; then
    echo die "\e[1;31mError :\e[22m Failed to ping SecurBridge at ${HEAVENDOOR}\e[0m"
fi

# install SCC release packages at very first
rpm -q scc-release &>/dev/null || \
    dnf install -y "https://rpms.scc-services.fr/stable/el${ELRELEASE}/x86_64/Packages/scc-release-${ELRELEASE}-0.el${ELRELEASE}.noarch.rpm"
dnf update -y scc-release || die "Unable to update package scc-release"
dnf install -y scc-artifacts-release || die "Unable to install package scc-artifacts-release"
dnf config-manager --set-enabled scc-teleport || die "Unable to enable Teleport packages repo from scc-artifacts-release"

# pseudo airgap mode uses SCC RPM proxy
if [ -n "$AIRGAP" ]; then
    dnf erase -y epel-release
    dnf config-manager --set-enabled scc-epel
else
    dnf config-manager --set-disabled scc-epel
    dnf install -y epel-release
fi
dnf clean all &> /dev/null

# install packages
dnf install -y python3-dnf-plugin-versionlock || die "Unable to install package python3-dnf-plugin-versionlock"
dnf install -y chrony jq openssl ca-certificates tar unzip bed-client

# configure bed-client
ln -s "/etc/pki/tls/certs/${CN}.crt" /var/lib/bed/certs/bed.pem
systemctl enable bed-ping.service
systemctl start bed-ping.service

# force dnf cache update
dnf clean all
dnf makecache

# enable & start chronyd
systemctl enable chronyd
systemctl restart chronyd
# force chrony time synchronization
chronyc makestep

# configure & start Teleport
dnf install -y hyperscale-teleport
/usr/libexec/teleport-setup.sh "$CN"
exit $?
