# lib/sahara

# Dependencies:
# ``functions`` file
# ``DEST``, ``DATA_DIR``, ``STACK_USER`` must be defined

# ``stack.sh`` calls the entry points in this order:
#
# install_sahara
# configure_sahara
# start_sahara
# stop_sahara
# cleanup_sahara

# Save trace setting
XTRACE=$(set +o | grep xtrace)
set +o xtrace


# Defaults
# --------

# Set up default repos
SAHARA_REPO=${SAHARA_REPO:-${GIT_BASE}/openstack/sahara.git}
SAHARA_BRANCH=${SAHARA_BRANCH:-master}

# Set up default directories
SAHARA_DIR=$DEST/sahara
SAHARA_CONF_DIR=${SAHARA_CONF_DIR:-/etc/sahara}
SAHARA_CONF_FILE=${SAHARA_CONF_DIR}/sahara.conf

SAHARA_SERVICE_HOST=${SAHARA_SERVICE_HOST:-$SERVICE_HOST}
SAHARA_SERVICE_PORT=${SAHARA_SERVICE_PORT:-8386}
SAHARA_SERVICE_PROTOCOL=${SAHARA_SERVICE_PROTOCOL:-$SERVICE_PROTOCOL}

SAHARA_AUTH_CACHE_DIR=${SAHARA_AUTH_CACHE_DIR:-/var/cache/sahara}

SAHARA_ENABLED_PLUGINS=${SAHARA_ENABLED_PLUGINS:-vanilla,hdp,fake}

# Support entry points installation of console scripts
if [[ -d $SAHARA_DIR/bin ]]; then
    SAHARA_BIN_DIR=$SAHARA_DIR/bin
else
    SAHARA_BIN_DIR=$(get_python_exec_prefix)
fi

# Tell Tempest this project is present
TEMPEST_SERVICES+=,sahara

# Functions
# ---------

# create_sahara_accounts() - Set up common required sahara accounts
#
# Tenant      User       Roles
# ------------------------------
# service     sahara    admin
function create_sahara_accounts {

    SERVICE_TENANT=$(openstack project list | awk "/ $SERVICE_TENANT_NAME / { print \$2 }")
    ADMIN_ROLE=$(openstack role list | awk "/ admin / { print \$2 }")

    SAHARA_USER=$(get_or_create_user "sahara" \
        "$SERVICE_PASSWORD" $SERVICE_TENANT)
    get_or_add_user_role $ADMIN_ROLE $SAHARA_USER $SERVICE_TENANT

    if [[ "$KEYSTONE_CATALOG_BACKEND" = 'sql' ]]; then

        SAHARA_SERVICE=$(get_or_create_service "sahara" \
            "data_processing" "Sahara Data Processing")
        get_or_create_endpoint $SAHARA_SERVICE \
            "$REGION_NAME" \
            "$SAHARA_SERVICE_PROTOCOL://$SAHARA_SERVICE_HOST:$SAHARA_SERVICE_PORT/v1.1/\$(tenant_id)s" \
            "$SAHARA_SERVICE_PROTOCOL://$SAHARA_SERVICE_HOST:$SAHARA_SERVICE_PORT/v1.1/\$(tenant_id)s" \
            "$SAHARA_SERVICE_PROTOCOL://$SAHARA_SERVICE_HOST:$SAHARA_SERVICE_PORT/v1.1/\$(tenant_id)s"
    fi
}

# cleanup_sahara() - Remove residual data files, anything left over from
# previous runs that would need to clean up.
function cleanup_sahara {

    # Cleanup auth cache dir
    sudo rm -rf $SAHARA_AUTH_CACHE_DIR
}

# configure_sahara() - Set config files, create data dirs, etc
function configure_sahara {

    if [[ ! -d $SAHARA_CONF_DIR ]]; then
        sudo mkdir -p $SAHARA_CONF_DIR
    fi
    sudo chown $STACK_USER $SAHARA_CONF_DIR

    # Copy over sahara configuration file and configure common parameters.
    cp $SAHARA_DIR/etc/sahara/sahara.conf.sample $SAHARA_CONF_FILE

    # Create auth cache dir
    sudo mkdir -p $SAHARA_AUTH_CACHE_DIR
    sudo chown $STACK_USER $SAHARA_AUTH_CACHE_DIR
    rm -rf $SAHARA_AUTH_CACHE_DIR/*

    # Set actual keystone auth configs
    iniset $SAHARA_CONF_FILE keystone_authtoken auth_uri $KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:$KEYSTONE_SERVICE_PORT/
    iniset $SAHARA_CONF_FILE keystone_authtoken auth_host $KEYSTONE_AUTH_HOST
    iniset $SAHARA_CONF_FILE keystone_authtoken auth_port $KEYSTONE_AUTH_PORT
    iniset $SAHARA_CONF_FILE keystone_authtoken auth_protocol $KEYSTONE_AUTH_PROTOCOL
    iniset $SAHARA_CONF_FILE keystone_authtoken admin_tenant_name $SERVICE_TENANT_NAME
    iniset $SAHARA_CONF_FILE keystone_authtoken admin_user sahara
    iniset $SAHARA_CONF_FILE keystone_authtoken admin_password $SERVICE_PASSWORD
    iniset $SAHARA_CONF_FILE keystone_authtoken signing_dir $SAHARA_AUTH_CACHE_DIR
    iniset $SAHARA_CONF_FILE keystone_authtoken cafile $KEYSTONE_SSL_CA

    iniset $SAHARA_CONF_FILE DEFAULT verbose True
    iniset $SAHARA_CONF_FILE DEFAULT debug $ENABLE_DEBUG_LOG_LEVEL

    iniset $SAHARA_CONF_FILE DEFAULT plugins $SAHARA_ENABLED_PLUGINS

    iniset $SAHARA_CONF_FILE database connection `database_connection_url sahara`

    if is_service_enabled neutron; then
        iniset $SAHARA_CONF_FILE DEFAULT use_neutron true
        iniset $SAHARA_CONF_FILE DEFAULT use_floating_ips true
    fi

    if is_service_enabled heat; then
        iniset $SAHARA_CONF_FILE DEFAULT infrastructure_engine heat
    else
        iniset $SAHARA_CONF_FILE DEFAULT infrastructure_engine direct
    fi

    iniset $SAHARA_CONF_FILE DEFAULT use_syslog $SYSLOG

    # Format logging
    if [ "$LOG_COLOR" == "True" ] && [ "$SYSLOG" == "False" ]; then
        setup_colorized_logging $SAHARA_CONF_FILE DEFAULT
    fi

    recreate_database sahara utf8
    $SAHARA_BIN_DIR/sahara-db-manage --config-file $SAHARA_CONF_FILE upgrade head
}

# install_sahara() - Collect source and prepare
function install_sahara {
    git_clone $SAHARA_REPO $SAHARA_DIR $SAHARA_BRANCH
    setup_develop $SAHARA_DIR
}

# start_sahara() - Start running processes, including screen
function start_sahara {
    screen_it sahara "cd $SAHARA_DIR && $SAHARA_BIN_DIR/sahara-all --config-file $SAHARA_CONF_FILE"
}

# stop_sahara() - Stop running processes
function stop_sahara {
    # Kill the Sahara screen windows
    screen -S $SCREEN_NAME -p sahara -X kill
}


# Restore xtrace
$XTRACE

# Local variables:
# mode: shell-script
# End:
