#!/bin/bash

# This shell script was written in order to help you to create and maintain your
# local mirrors of MOS and/or Ubuntu. You could use this script as a cron job.
# Dependencies: rsync, gpg, docker + dpkg-dev (only for partial Ubuntu mirror)

usage() {
cat <<EOF
Usage: `basename $0` [options]

Create and update local mirrors of MOS and/or Ubuntu.

IMPORTANT!
If NO parameters specified, this script will:
- Create/Update both MOS and Ubuntu local mirrors
- Set them as repositories for existing NEW environments in Fuel UI
- Set them as DEFAULT repositories for new environments

Options:

  -h| --help          This help screen.
  -d| --no-default    Don't change default repositories for new environments
  -a| --no-apply      Don't apply changes to Fuel environments
  -M| --mos           Create/Update MOS local mirror only
  -U| --ubuntu        Create/Update Ubuntu local mirror only
  -N| --dry-run       Show commands to execute instead of running them
  -p| --password      Fuel Master admin password (defaults to admin)

CUSTOMIZATION
-------------
The following configuration file could be used to modify the
script behavior:

/etc/fuel-createmirror/common.cfg

If you are behind a proxy, you should set both http_proxy and RSYNC_PROXY env vars.

Please refer to the description of parameters in that configuration file.

See more detailed description in the Fuel Operations Guide:
https://docs.mirantis.com/openstack/fuel/fuel-6.1/operations.html#external-ubuntu-ops

EOF
}

usage_short() {
    echo Usage: `basename $0` [options]
    echo
    echo -e Try \``basename $0` --help\' for more options.
}

die() { echo "$@" 1>&2 ; exit 1; }

print_repositories_ubuntu() {
# $1 - directory name of local repository
    echo -e " * INFO: In order to setup these repositories MANUALLY, you should"
    echo -e "         go to Fuel UI, choose your cluster and go to the 'Settings' tab"
    if [ "$PARTIAL_UPSTREAM" == "0" ]; then
	echo -e "         Replace the URI value for the following repositories:"
	for dist in "${DISTs[@]}"; do
	    distlabel=`echo "$dist" | sed "s/$FUEL_VERSION//"`
	    echo -e "         Repository \"$distlabel\" URI=\"deb http://$FUEL_SERVER:8080/$1 $dist ${DIST_COMPONENTs[$dist]}\""
	done
    else
	echo -e "         Replace the URI value for the following repositories:"
	echo
	echo -e "         Repository \"ubuntu\" new URI=\"deb http://$FUEL_SERVER:8080/$1 ${DISTs[0]} main\""
	echo -e "         Repository \"ubuntu-security\" new URI=\"deb http://$FUEL_SERVER:8080/$1 ${DISTs[0]} main\""
	echo -e "         Repository \"ubuntu-updates\" new URI=\"deb http://$FUEL_SERVER:8080/$1 ${DISTs[0]} main\""
    fi
    echo
}

add_repositories_to_nailgun() {
# parameters:
# $1 - operating_system from fuel env
# $2 - distro name in fuel-package-updates format
# $3 - directory name of local repository
    echo " * INFO: Attempting to add created repositories to Nailgun..."
    local release_id=`env http_proxy="" fuel --user=admin --password="$FUEL_ADMIN_PASS" release 2>/dev/null| awk -F"|" '{print $1" "$4" "$5}' | grep "$1" | grep "$FULL_RELEASE" | awk '{print $1}'`
    local clearupstream=" --clear-upstream-repos "
    local makedefault=" --make-default "
    local apply=" --apply "
    [ "$PARTIAL_UPSTREAM" == "0" ] && clearupstream=""
    [ "$OPT_NO_APPLY" == "1" ] && apply=""
    # find envs with status "new" and with given release_id
    envs=`env http_proxy="" fuel --user=admin --password="$FUEL_ADMIN_PASS" env 2>&1 | grep -w new | awk -v release_id=$release_id -F'|' '$5 == release_id {print $1}'`
    for env in ${envs}; do
        $EXEC_PREFIX env http_proxy="" fuel-package-updates -d $2 -r $FULL_RELEASE --no-download $apply \
        -s $FUEL_SERVER -p "$FUEL_ADMIN_PASS" -b http://$FUEL_SERVER:8080/$3 -e $env $clearupstream 2>/dev/null
	EC_FPU=$?
	if [[ "$EC_FPU" == "0" ]]; then
	    [ "$OPT_NO_APPLY" ] || echo " * INFO: environment id=$env updated successfully, no manual actions is required"
	else
	    echo " * INFO: Failed to add repositories for environment id=$env to Nailgun, please add them MANUALLY"
	    EC_ADD=1
	fi
    done
    if [ "$OPT_NO_DEFAULT" ]; then
	echo " * INFO: Default repositories for new environments were not modified"
    else
	$EXEC_PREFIX env http_proxy="" fuel-package-updates -d $2 -r $FULL_RELEASE --no-download --make-default \
	-s $FUEL_SERVER -p "$FUEL_ADMIN_PASS" -b http://$FUEL_SERVER:8080/$3 $apply $clearupstream 2>/dev/null
	EC_FPU=$?
	if [[ "$EC_FPU" == "0" ]]; then
	    echo " * INFO: Created repositories were set as defaults for new environments"
	else
	    echo " * WARN: Failed to set repositories as defaults for new environments"
	fi
    fi
    [ "$EC_ADD" == "1" ] && print_repositories_ubuntu $3
}

### BEGIN

# Set defaults
OPT_MOS=1
OPT_UBUNTU=1
EXEC_PREFIX=""

# Parse options
OPTS=`getopt -o hdaMUNp: -l help,no-default,no-apply,mos,ubuntu,password:,dry-run -- "$@"`
if [ $? != 0 ]; then
    usage_short
    exit 1
fi

eval set -- "$OPTS"

while true ; do
    case "$1" in
        -h| --help        ) usage ; exit 0;;
        -d | --no-default ) OPT_NO_DEFAULT=1; shift;;
        -a | --no-apply   ) OPT_NO_APPLY=1; shift;;
        -N | --dry-run    ) EXEC_PREFIX="echo  EXEC  "; shift;;
        -M | --mos        ) unset OPT_UBUNTU; shift;;
        -U | --ubuntu     ) unset OPT_MOS; shift;;
        -p | --password   ) FUEL_MASTER_PASS="$2"; shift; shift;;
        --                ) shift; break;;
        *                 ) break;;
    esac
done

if [[ "$@" != "" ]]; then
    echo "Invalid option -- $@"
    usage_short
    exit 1
fi

if [ -z $OPT_MOS ] && [ -z $OPT_UBUNTU ]; then
    echo "The --mos and --ubuntu options are mutually exclusive, aborting..."
    usage_short
    exit 1
fi

export BINROOT=$(dirname `readlink -f "$0"`)

. $BINROOT/config/common.cfg
. $BINROOT/config/fuel.cfg

# If running on Fuel node - check if we can connect to backend
if hash fuel2 2>/dev/null; then
    echo " * INFO: Verifying connection to the Fuel backend"
    if env http_proxy="" fuel --user=admin --password=$FUEL_ADMIN_PASS release &>/dev/null; then
           echo " * INFO: Fuel backend connection OK"
    else
           echo " * FATAL: Connect to Fuel backend failed. Please verify that Fuel services are up&running."
           echo "   If services are OK, please make sure you have specified the correct Fuel Master admin password"
           usage_short
           exit 1
    fi
fi

if [ -z "${RSYNC_PROXY+x}" ] && [ $http_proxy ]; then
    export http_proxy
    export RSYNC_PROXY=$http_proxy
fi

$EXEC_PREFIX mkdir -p ${MIRROR_ROOT} || die "Cannot create ${MIRROR_ROOT}, exiting."
$EXEC_PREFIX mkdir -p ${LOG_ROOT} || die "Cannot create ${LOG_ROOT}, exiting."

EC=0

if [[ $OPT_MOS ]]; then
    $EXEC_PREFIX $BINROOT/deb-mirror $BINROOT/config/mos-ubuntu-updatesonly.cfg
    EC_MOS=$?
fi

if [[ $OPT_UBUNTU ]]; then
    $EXEC_PREFIX $BINROOT/deb-mirror $BINROOT/config/ubuntu.cfg
    EC_UBUNTU=$?
fi

if [[ $OPT_MOS ]]; then
    if [[ "$EC_MOS" == "0" ]]; then
	. $BINROOT/config/mos-ubuntu-updatesonly.cfg
	echo " * INFO: MOS mirror was created at: $LOCAL_DIR"
	if [[ "$DOCKER_MODE" == "true" ]]; then
	    add_repositories_to_nailgun Ubuntu ubuntu ${LOCAL_DIR##*/}
	else
	    print_repositories_ubuntu ${LOCAL_DIR##*/}
	fi
    else
	echo " * FATAL: Creation of MOS mirror FAILED, check logs at $LOG_ROOT"
	EC=1
    fi
fi
if [[ $OPT_UBUNTU ]]; then
    if [[ "$EC_UBUNTU" == "0" ]]; then
	. $BINROOT/config/ubuntu.cfg
	if [[ $PARTIAL_UPSTREAM = "1" ]]; then
	    echo " * INFO: Ubuntu partial mirror was created at: $PARTIAL_UPSTREAM_PATH"
	    if [[ "$DOCKER_MODE" == "true" ]]; then
		add_repositories_to_nailgun Ubuntu ubuntu-baseos ${PARTIAL_UPSTREAM_PATH##*/}
	    else
		print_repositories_ubuntu ${PARTIAL_UPSTREAM_PATH##*/}
	    fi
	else
	    echo " * INFO: Ubuntu mirror was created at: $LOCAL_DIR"
	    if [[ "$DOCKER_MODE" == "true" ]]; then
		add_repositories_to_nailgun Ubuntu ubuntu-baseos ${LOCAL_DIR##*/}
	    else
		print_repositories_ubuntu ${LOCAL_DIR##*/}
	    fi
	fi
    else
	echo " * FATAL: Creation of Ubuntu mirror FAILED, check logs at $LOG_ROOT"
	EC=1
    fi
fi

exit $EC
