#!/usr/bin/env sh

usage()
{
    (
       echo "usage: $0: [-r root-directory] [-U] [-V TAG]\n"
       echo "    -U      - use existing EUPS product tree."
       echo "    -V TAG  - use specified git tag for our products."
       echo "    -r root - create and use this root directory."
       echo "    --with-python=PATH - use this python executable for our system."
       echo
       echo "    If no root directory is specified, use $ICS_ROOT\n" 
    ) >&2
    exit 1
}

ICS_ROOT=$HOME/mhs
EUPS_BOOTSTRAP_VERSION=2.1.4

PFS_REPO_ROOT="https://github.com/Subaru-PFS"

# New eups versions want to use /usr/bin/python, and insist that
# anything else is explicitly requested. Bypass that logic.
PYTHON_PATH=$(which python3)
EUPS_OPTIONS="--with-python=$PYTHON_PATH"

#  The ICS pieces we want to install, in order. 
#    These are the essential products to run tron and to build and run an actor.
#    Note that ics_mhs_config is handled independently, by this script.
# 
ICS_DEVEL_PRODUCTS="ics_config:1.4.5"

get_product()
{
    echo "${1%%:*}"
}

get_version()
{
    local v=${1##*:}
    echo "${v:-master}"
}

get_products()
{
    local plist=""
    for p in $ICS_DEVEL_PRODUCTS; do
        plist="$plist $(get_product $p)"
    done

    echo $plist
}

get_versions()
{
    local vlist=""
    for p in $ICS_DEVEL_PRODUCTS; do
        vlist="$vlist $(get_version $p)"
    done

    echo $vlist
}

while getopts :hUV-:r: arg; do
    case $arg in
       r) ICS_ROOT="$OPTARG"
           ;; 
       U) addToEups=1
           ;; 
       V) ICS_TAG="$OPTARG"
           ;; 
       -) if test "with-python" = ${OPTARG:0:11}; then
              EUPS_OPTIONS="--$OPTARG"
               echo "EUPS_OPTIONS: $EUPS_OPTIONS"
          else
               echo "unknown -arg: $OPTARG"
               exit 2
          fi
           ;;
       ?) echo "unknown argument: $OPTARG"
          usage
          ;;
       h) usage
          ;;
    esac
done

echo "Using python environment based on $PYTHON_PATH...."
sleep 3

# Some sanity tests.
#  . make is required by eups, but not always supplied.
requiredPrograms="make"
for p in $requiredPrograms; do
    if ! type $p >/dev/null 2>&1; then 
       echo "FATAL: we need some version of $p"
       exit 2
    fi
done

# Configuration variables.
# 1. The root directory for image/data files, logs, etc. 
#    In practice, I'd make this the home directory for an operations/development account.
#    This script will create several subdirectories, which could then be moved around/linked/etc.
#
if test -d $ICS_ROOT; then 
    echo "ICS_ROOT=$ICS_ROOT exists ... NOT overwriting it. It contains:" >&2
    ls -l $ICS_ROOT >&2 
    exit 1
else
    echo "####### Bootstrapping the ICS MHS and actors into $ICS_ROOT...." >&2
fi

# 2. The root directory for development. The git repos will be cloned into this
#    By default, uses $ICS_ROOT/devel
ICS_DEVEL_ROOT=$ICS_ROOT/devel

# 3. The root directory for eups products. 
#    By default, uses $EUPS_PATH if already set, otherwise $ICS_ROOT/products 
export EUPS_PATH_TMP=${EUPS_PATH:-${ICS_ROOT}/products}

# 4. The EUPS version to fetch and install.
#    If eups is already installed, do not install a new one, and
#    only add our products if we were explicitely told to with -U
if type eups >/dev/null 2>&1; then
    echo "eups is already installed -- NOT overwriting it."
    if test -n "$addToEups"; then
        echo "  Adding ICS products to the existing EUPS database in $EUPS_PATH_TMP ..." >&2
    else
        echo "  Pass in -U to add ICS products to the existing EUPS database in $EUPS_PATH_TMP." >&2
        exit 1
    fi
    unset EUPS_VERSION
else
    if test -n "$EUPS_DIR"; then
        echo
        echo "I cannot find eups, but an EUPS_DIR=$EUPS_DIR is defined."
        echo "Not sure what is safe to do, so am stopping now."
        exit 1 
   fi
    EUPS_VERSION=${EUPS_BOOTSTRAP_VERSION:-"master"}
    EUPS_INSTALL_DIR=$EUPS_PATH_TMP/eups/$EUPS_VERSION
    EUPS_DEFAULT_DIR=$EUPS_PATH_TMP/eups/default

    if test -e "$EUPS_INSTALL_DIR" || test -e "$EUPS_DEFAULT_DIR"; then
        echo
        echo "Either $EUPS_INSTALL_DIR or $EUPS_DEFAULT_DIR exists."
        echo "Not sure what is safe to do, so am stopping now."
        exit 1
    fi
fi

export EUPS_PATH=$EUPS_PATH_TMP


#################################

mkdir -p $ICS_ROOT || (echo "could not create $ICS_ROOT directory!"; exit 1)
mkdir -p $ICS_DEVEL_ROOT
cd $ICS_DEVEL_ROOT

# Do we need to bootstrap a eups version?
if test -n "$EUPS_VERSION"; then 
    echo 
    echo "######## installing eups (version=$EUPS_VERSION) to $EUPS_INSTALL_DIR ...."
    git clone -b $EUPS_VERSION https://github.com/RobertLuptonTheGood/eups.git eups 

    (cd eups 
        ./configure --with-eups=$EUPS_PATH --prefix=$EUPS_INSTALL_DIR --with-python=`which python3`
        make install
    )
    if test $? -ne 0; then 
        echo "Failed to install eups."
        exit 1
    fi

    # Make convenience link, for logins, etc.
    ln -s $EUPS_VERSION $EUPS_DEFAULT_DIR

    # Act as if we are logging in.
    . $EUPS_DEFAULT_DIR/bin/setups.sh
fi

# Clean out any possible crud in the environment
for p in ics_config $(get_products); do
    unsetup -f -q $p >/dev/null 2>/dev/null
done

. setups.sh

# Install the core products. We install a full, perhaps tagged, version in the eups
# product tree, plus we leave and declare a live master version here.
#
for p in $ICS_DEVEL_PRODUCTS; do
    prod=$(get_product $p)
    vers=$(get_version $p)
    echo
    echo "######## installing version $vers of $prod..."

    cd $ICS_DEVEL_ROOT
    git clone $PFS_REPO_ROOT/$prod
    ( cd $prod;
      git checkout $vers

      . setups.sh
      
      # Bootstrap: 
      if test "$prod" = "ics_config"; then
          sed "s;%(ICS_ROOT);$ICS_ROOT;g" < ups/ics_config.table-in > ups/ics_config.table
      fi
      setup -v -r .
      
      eupsinstall

      # Get rid of additional versions. Only need to do this until
      # we have access to more eups information.
      unsetup $prod 
      eups declare -v -c $prod $(eups list $prod)

      # Hackity-hack-hack, until we adjust the --install-lib logic in eupsinstall
      ( cd $(eups list -c -d $prod);
        ln -s lib/python python
      )

      # Declare the current live directory version.
      git checkout master
      eups declare -v -F -r . $prod git
    )
    setup -v $prod
done

# Create any necessary subdirectories to run under $ICS_ROOT
#
mkdir -p ${ICS_MHS_DATA_ROOT}
mkdir -p ${ICS_MHS_LOGS_ROOT}/tron

# Finish with a reminder
echo
echo "###### The bootstrap MHS parts are installed."
echo

if test -n "$EUPS_VERSION"; then
    echo "###### You _must_ now source $EUPS_DEFAULT_PATH/eups/bin/setups.sh before anything else will work. That's:"
    echo
    echo ". $EUPS_DEFAULT_DIR/bin/setups.sh"
    echo   or
    echo "source $EUPS_DEFAULT_DIR/bin/setups.csh"
    echo   or
    echo ". $EUPS_DEFAULT_DIR/bin/setups.zsh"
    echo
    echo "You probably also want to put that into your login script. Use setups.zsh if you use a strict POSIX shell. "
    echo 
    echo "After setting up eups, 'eups list' will show all available products and versions, and "
    echo "'setup -v xxxx' will setup the given product and all its dependencies."
fi

exit 0



