#
#
###############################################################
################   Delete a Function   ####################
###############################################################
#
#
#
#  
# STEPS
# 1. Call this file
#    
#     npm run Delete_Function.sh
#       
#
. ./@Core/Scripts/templates.sh
. ./@Core/Scripts/createMenu.sh

function delete_function {
    local NAMESPACE=$1
    local FUNCTION_NAME=$2
    local VERSION_NUMBER=$3
    local ACTUAL_FUNCTION_NAME="$NAMESPACE""_""$FUNCTION_NAME""_""$VERSION_NUMBER"

    # Validate existing function
    if [ -d "./API/$NAMESPACE/$FUNCTION_NAME/$VERSION_NUMBER" ]
    then
        echo "\n\n${BLACK_TEXT_ON_GREEN_BACKGROUND} ${TICK_EMOJI}  DONE... ${NAMESPACE}/${FUNCTION_NAME}/${VERSION_NUMBER} is DELETED  ${NC}"
    else
        echo "\n${RED}No such function${NC}\n"
        echo "${ABORT_TEXT}"
        exit
    fi

    # Remove the reference in the API index file
    sed -i '' "/$ACTUAL_FUNCTION_NAME/d" ./API/index.ts

    # Remove the files of the version.
    rm -rf ./API/$NAMESPACE/$FUNCTION_NAME/$VERSION_NUMBER

    # Cleanup remaining folders and files
    if [ -z "$(ls -A ./API/$NAMESPACE/$FUNCTION_NAME/)" ]
    then
        rm -rf ./API/$NAMESPACE/$FUNCTION_NAME
        if [ -z "$(ls -A ./API/$NAMESPACE/)" ]
        then
            printf "${DARK_GRAY}Clearing the ${NAMESPACE} namespace..."
            rm -rf ./API/$NAMESPACE/
        fi
    else
        echo "\n${NC}Other versions exist"
        exit
    fi
}

###############################################################
#####################   CONSTANTS   ###########################
###############################################################

# Folders to be ignored in namespace directory
IGNORE_API_FOLDERS=("./API/CoreHelpers/" "./API/Core/")
# The default name for deleting a function
DELETE_FUNCTION="Delete a hidden function"
# PASCAL CASE REGEX
PASCAL_REGEX='^[A-Z][a-z]+([A-Z][a-z]+)*$'

###############################################################
################   INTERNAL STATE MUTATIONS  ##################
###############################################################

# The currently selected namespace (string)
NAMESPACE=""
# The currently selected function name (string)
FUNCTION_NAME=""
# The lines to remove from the terminal (int)
LINES_TO_REMOVE=0
# The currently selected version
VERSION_NUMBER=""
# The boolean to determine to move forward (yes | no)
CONTINUE=""

###############################################################
####################   MENU HELPERS   #########################
###############################################################

# Erase lines and set lines to remove to 0
function clear_lines {
    erase_lines $LINES_TO_REMOVE
    LINES_TO_REMOVE=0
}

# Initiate flow for selecting a namespace
function select_namespace {
    local NAMESPACES=()
    for name in ./API/*/
    do
        if ! [[ ${IGNORE_API_FOLDERS[*]} =~ "$name" ]]; then
            NAMESPACES+=(`basename ${name}`)
        fi
    done

    NAMESPACES+=("$DELETE_FUNCTION")

    printf "${RED}Select one of the following namespaces${NC}\n"
    printf "${DARK_GRAY}   Use the arrow keys to move around... ${NC}\n"

    select_option "${NAMESPACES[@]}"
    local CHOICE=$?
    NAMESPACE="${NAMESPACES[$CHOICE]}"

    # Clearing lines
    local BUFFER=3
    LINES_TO_REMOVE=$((${#NAMESPACES[@]}+$BUFFER))
    clear_lines
}

# Initiate flow for selecting an existing function
function select_function_name {
    # Selecting function
    printf "Namespace:${GREEN} $NAMESPACE ${NC}\n"

    local FUNCTION_NAMES=()
    for name in ./API/$NAMESPACE/*/
    do
        FUNCTION_NAMES+=(`basename ${name}`)
    done

    printf "${NC}Select one of the following functions: \n"

    # Function Menu
    select_option "${FUNCTION_NAMES[@]}"
    local CHOICE=$?
    FUNCTION_NAME=${FUNCTION_NAMES[$CHOICE]}

    # Clearing lines
    local BUFFER=3
    LINES_TO_REMOVE=$((${#FUNCTION_NAMES[@]}+$BUFFER))
    clear_lines

    printf "${NC}Function name:${GREEN} $FUNCTION_NAME\n"
}

# Delete version
function select_version {
    echo "${NC}Select a version to be deleted "
    DIRECTORY="./API/${NAMESPACE}/${FUNCTION_NAME}"
    VERSION_NUMBERS=()
    for version in ./API/$NAMESPACE/$FUNCTION_NAME/*/; do 
        LATEST_VERSION=$version
        VERSION_NUMBERS+=(`basename $version`)
    done;

    # Version Menu
    select_option "${VERSION_NUMBERS[@]}"
    local CHOICE=$?
    VERSION_NUMBER=${VERSION_NUMBERS[$CHOICE]}

    # Clear lines
    local BUFFER=3
    LINES_TO_REMOVE=$((${#VERSION_NUMBERS[@]}+$BUFFER))
    clear_lines

    printf "${NC}Version number:${GREEN} $VERSION_NUMBER\n\n"
}

function confirm_decision_menu {
    echo "${WHITE}Would you like to continue? ${NC}"
    BOOLEAN_OPTIONS=("yes" "no")
    select_option "${BOOLEAN_OPTIONS[@]}"
    CHOICE=$?
    CONTINUE="${BOOLEAN_OPTIONS[$CHOICE]}"

     # Clear lines
    local BUFFER=4
    LINES_TO_REMOVE=$((${#BOOLEAN_OPTIONS[@]}+$BUFFER))
    clear_lines
}

function delete_hidden_function {
    # Namespace menu
    printf "Namespace:${GREEN} "
    
    while [ true ]
    do
        LINES_TO_REMOVE=$(($LINES_TO_REMOVE+2))
        read NAMESPACE
        if [[ ! $NAMESPACE  =~ $PASCAL_REGEX ]]
            then
                echo "${RED} ! $NAMESPACE is not a PascalCase ${NC}"
                printf "Namespace:${GREEN} "
            else
                clear_lines
                printf "${NC}Namespace:${GREEN} $NAMESPACE\n"
                break
        fi
    done
    
    # Function name menu
    printf "\r${NC}Function name:${GREEN} "
    while [ true ]
    do
        LINES_TO_REMOVE=$(($LINES_TO_REMOVE+2))
        read FUNCTION_NAME
        if [[ ! $FUNCTION_NAME  =~ $PASCAL_REGEX ]]
            then
                echo "${RED} ! $FUNCTION_NAME is not a PascalCase ${NC}"
                printf "Function name:${GREEN} "
            else
                clear_lines
                printf "${NC}Function name:${GREEN} $FUNCTION_NAME\n"
                break      
        fi
    done

    # Version menu
    printf "\r${NC}Version name:${GREEN} "
    read VERSION_NUMBER
}

###############################################################
################   Main Program flow here   ###################
###############################################################

function main {
    echo "${RED}You are about to delete a function::"

    confirm_decision_menu

    if [ $CONTINUE = "yes" ]
    then
        select_namespace
        if [ "$NAMESPACE" = "$DELETE_FUNCTION" ]
        then
            delete_hidden_function
            delete_function $NAMESPACE $FUNCTION_NAME $VERSION_NUMBER
        else
            select_function_name
            select_version
            confirm_decision_menu

            if [ $CONTINUE = "yes" ]
            then
                delete_function $NAMESPACE $FUNCTION_NAME $VERSION_NUMBER
            else
                echo "${ABORT_TEXT}"
            fi
        fi
    else
        echo "${ABORT_TEXT}"
    fi
}

main
