#!/bin/bash

source /etc/sysconfig/jsonar

DEFAULT=${JSONAR_LOCALDIR}/sonarsql/default

usage() {
    echo "Error: $1"
    echo "Usage: $0 [--sonarw-uri SONARW_URI] [--root-password ROOT_PW] [--quiet]"
    exit -1
}

service-do() {
    # usage: service-do <action> <service>...
    action=$1
    shift
    echo "${action} $* ..."
    systemctl ${action} $*
}

start() {
    service-do start $*
}

stop() {
    service-do stop $*
}

restart() {
    stop $*
    start $*
}

service-help() {
    # usage service-help <action> <service>...
    action=$1
    shift
    echo "Please run the following to ${action} the required services:"
    echo
    echo "  sudo systemctl ${action} $*"
}

migrate-old-service() {
    local service=$1
    local service_file=${JSONAR_BASEDIR}/lib/systemd/system/${service}.service
    if [[ $(systemctl is-enabled "${service_file}" 2>/dev/null) == enabled ]]; then
        echo "Migrating service ${service} to new location ..."
        systemctl stop "${service_file}"
        systemctl disable "${service_file}"
        enable-service ${service}
    fi
}

enable-service() {
    local service=$1
    echo "Enabling service ${service} to start at boot ..."
    cp ${JSONAR_BASEDIR}/lib/systemd/system/${service}.service /etc/systemd/system/${service}.service
    systemctl enable ${service}
}

sed-escape-pattern() {
    # escape the pattern part in a sed expression
    echo "$@" | sed -e 's/[]\/$*.^[]/\\&/g'
}

sed-escape-replace() {
    # escape the replace part in a sed expression
    echo "$@" | sed -e 's/[\/&]/\\&/g'
}

modify-key() {
    local file=$1
    local key=$2
    local value=$3

    sed -i "s,^\(${key} *=\).*$,\1 $(sed-escape-replace ${value})," ${file}
}

mark-setup-done() {
    mkdir -p $(dirname ${DEFAULT})
    if grep -s ^SETUP_DONE= ${DEFAULT} > /dev/null; then
        sed -i 's/^\(SETUP_DONE=\).*/\11/' ${DEFAULT}
    else
        echo SETUP_DONE=1 >> ${DEFAULT}
    fi
}

#
# repeatedly ask for password until it is strong
#
get-password() {
    # get-password prompt var
    local prompt=$1
    local var=$2
    local pass2

    while true; do
        read -s -p "Password for $prompt (will not be shown): " ${var}
        echo
        result=$(echo "${!var}" | cracklib-check | sed "s/^$(sed-escape-pattern "${!var}"): //")
        if [[ ${result} == "OK" ]]; then
            read -s -p "Retype password for $prompt: " pass2
            echo
            if [[ "${!var}" = "${pass2}" ]]; then
                break
            else
                echo "Sorry, passwords do not match."
            fi
        else
            echo ${result}
        fi
    done
}

setup() {
    DEFAULT_CONFIG=${JSONAR_BASEDIR}/etc/sonar/sonarsql.conf
    CONFIG_FILE=${JSONAR_LOCALDIR}/sonarsql/sonarsql.conf

    if [[ ${QUIET} != "YES" ]]; then
        echo "SonarSQL Initial Setup"
        echo "======================"
        echo
    fi

    if [[ -z ${SONARW_URI+x} ]]; then
        SONARW_URI="mongodb://CN%3Dadmin@localhost:27117/admin?authSource=%24external&authMechanism=PLAIN&certfile=%24%7BJSONAR_LOCALDIR%7D%2Fssl%2Fclient%2Fadmin%2Fcert.pem"
    fi

    if [[ -z ${SONARSQL_ROOTPW+x} ]]; then
        cat <<EOF
Enter the root password to be used by SQL clients.

The root password is used to authenticate the root SonarSQL user. You can only
create new users if you authenticate with SonarSQL as root.

You can leave this field empty, in which case root login will be impossible.

EOF
        get-password "SonarSQL root" SONARSQL_ROOTPW
        echo
    fi

    mark-setup-done

    mkdir -p $(dirname ${CONFIG_FILE})
    cp ${DEFAULT_CONFIG} ${CONFIG_FILE}

    modify-key ${CONFIG_FILE} uri ${SONARW_URI}
    if [ ! -z "$SONARSQL_ROOTPW" ]; then
        modify-key ${CONFIG_FILE} root-pwhash $(${JSONAR_BASEDIR}/bin/sonarsql --generate-password-hash $SONARSQL_ROOTPW | cut -s -d= -f 2)
    fi

    chmod 0660 ${CONFIG_FILE}
    chown sonarw:sonar ${CONFIG_FILE}

    enable-service sonarsql
    start sonarsql
    if [[ ${QUIET} != "YES" ]]; then
        cat <<EOF

Initial configuration completed.

EOF
    fi
}

upgrade() {
    migrate-old-service sonarsql
    restart sonarsql
    if [[ ${QUIET} != "YES" ]]; then
        cat <<EOF

Upgrade completed.

EOF
    fi
}

SETUP_DONE=0
if [ -f ${DEFAULT} ]; then
   . ${DEFAULT}
fi


while [[ $# -gt 0 ]]; do
    key="$1"
    case $key in
        --sonarw-uri)
            SONARW_URI="$2"
            shift
            ;;
        --quiet)
            QUIET=YES
            ;;
        --root-password)
            SONARSQL_ROOTPW="$2"
            shift
            ;;
        *)
            usage "Unknown option $1"
            ;;
    esac
    shift
done

case ${SETUP_DONE} in
    # must be specifically to run setup
    0|NO|no|FALSE|false)
        setup
        ;;
    *)
        upgrade
        ;;
esac

exit 0
