# shellcheck shell=dash

xrc ui
xrc fsiter

___x_cmd log init eget

xrc:mod:lib     eget            \
    api         cache   detect  \
    extract     verify          \
    manifest    snap    which   \
    ls/_index   ls/ls_install   \
    resolve use upgrade download

___X_CMD_EGET_TMP="$___X_CMD_ROOT_TMP/eget"
___X_CMD_EGET_DATA="$___X_CMD_ROOT_DATA/eget"
___x_cmd mkdirp "${___X_CMD_EGET_DATA}" "${___X_CMD_EGET_TMP}"

___x_cmd_eget___main(){
    [ "$#" -gt 0 ] || set -- --help

    local op="$1"; shift
    case "$op" in
        -h|--help)          ___x_cmd help -m eget; return 0 ;;
        --version|-v)       ___x_cmd_eget___version; return 0 ;;
        snap)               ___x_cmd_eget_snap "$@"; return ;;
        ls|list)            ___x_cmd_eget_ls "$@"; return ;;
        resolve)            ___x_cmd_eget_resolve "$@"; return ;;
        detect-test)        ___x_cmd_eget_subcmd_detect_test "$@"; return ;;
        detect-orig)        ___x_cmd_eget_subcmd_detect_orig "$@"; return ;;
        which)              ___x_cmd_eget_which "$@"; return ;;
        use)                ___x_cmd_eget_use "$@"; return ;;
        unuse)              ___x_cmd_eget_unuse "$@"; return ;;
        usels)              ___x_cmd_eget_usels "$@"; return ;;
        upgrade)            ___x_cmd_eget_upgrade "$@"; return ;;
        cache)              ___x_cmd_eget_cache "$@"; return ;;
        extract)            ___x_cmd_eget_subcmd_extract "$@"; return ;;
        verify)             ___x_cmd_eget_subcmd_verify "$@"; return ;;
        rate)               ___x_cmd_eget_api_rate "$@"; return ;;
        remove)             ___x_cmd_eget___remove "$@"; return ;;
        download|run|get)   ___x_cmd_eget_download "$@"; return ;;
        *)                  ___x_cmd_eget_download "$op" "$@" ;;
    esac
}

___x_cmd_eget___version(){
    printf "x eget (x-cmd pure shell implementation)\nInspired by zyedidia/eget\n"
}

___x_cmd_eget_subcmd_detect_test(){
    # Run detect using scoring algorithm, print result
    local _target="" _system="" _tag=""
    while [ $# -gt 0 ]; do
        case "$1" in
            -s|--system) shift; _system="$1" ;;
            -t|--tag)    shift; _tag="$1" ;;
            *)           _target="$1" ;;
        esac
        shift
    done
    [ -z "$_target" ] && { N=eget M="Usage: x eget detect-test <owner/repo> [-s system] [-t tag]" log:ret:64; return; }

    [ -z "$_system" ] && {
        local x_=""
        ___x_cmd os name_;  local osname="$x_"
        ___x_cmd os arch_;  local osarch="$x_"
        _system="${osname}/${osarch}"
    }

    ___X_CMD_EGET_VERBOSE="1" ___X_CMD_EGET_DETECT_MODE="scoring"
    ___x_cmd_eget_resolve_ "$_target" "github" "$_tag" "$_system" "" "0" "0" || {
        N=eget M="No asset found" log:ret:1; return;
    }
    local _pick="$x_"
    local asset_name="${_pick%%
*}"
    printf "\n[scoring] Selected: %s\n" "$asset_name"
}

___x_cmd_eget_subcmd_detect_orig(){
    # Run detect using original tier algorithm, print result
    local _target="" _system="" _tag=""
    while [ $# -gt 0 ]; do
        case "$1" in
            -s|--system) shift; _system="$1" ;;
            -t|--tag)    shift; _tag="$1" ;;
            *)           _target="$1" ;;
        esac
        shift
    done
    [ -z "$_target" ] && { N=eget M="Usage: x eget detect-orig <owner/repo> [-s system] [-t tag]" log:ret:64; return; }

    [ -z "$_system" ] && {
        local x_=""
        ___x_cmd os name_;  local osname="$x_"
        ___x_cmd os arch_;  local osarch="$x_"
        _system="${osname}/${osarch}"
    }

    ___X_CMD_EGET_VERBOSE="1" ___X_CMD_EGET_DETECT_MODE="original"
    ___x_cmd_eget_resolve_ "$_target" "github" "$_tag" "$_system" "" "0" "0" || {
        N=eget M="No asset found" log:ret:1; return;
    }
    local _pick="$x_"
    local asset_name="${_pick%%
*}"
    printf "\n[original] Selected: %s\n" "$asset_name"
}

___x_cmd_eget___remove(){
    case "${1:-}" in -h|--help) ___x_cmd help -m eget remove; return 0 ;; esac
    local target_dir="${EGET_BIN:-.}"
    local file="$1"
    [ -n "$file" ] || { N=eget M="Missing file name for remove" log:ret:64; return; }
    local path="$target_dir/$file"
    [ -f "$path" ] || { N=eget M="File not found: $path" log:ret:1; return; }
    ___x_cmd rmrf "$path"
    eget:info "Removed $path"
}

# --- Subcommands ---

___x_cmd_eget_subcmd_extract(){
    case "${1:-}" in -h|--help) ___x_cmd help -m eget extract; return 0 ;; esac
    [ "$#" -gt 0 ] || { N=eget M="extract: missing archive file" log:ret:64; return; }
    local archive="$1"; shift
    local file_glob="" all="0" to="." name=""
    while [ $# -gt 0 ]; do
        case "$1" in
            -f|--file)  shift; file_glob="$1" ;;
            --all)      all="1" ;;
            --to)       shift; to="$1" ;;
            --name)     shift; name="$1" ;;
            *)          name="$1" ;;
        esac
        shift
    done
    : "${name:=$( basename "$archive" )}"
    name="${name%%.*}"
    ___x_cmd_eget_extract "$archive" "$file_glob" "$all" "$to" "$name"
}

___x_cmd_eget_subcmd_verify(){
    case "${1:-}" in -h|--help) ___x_cmd help -m eget verify; return 0 ;; esac
    [ "$#" -ge 2 ] || { N=eget M="verify: usage: x eget verify <file> <expected_hash>" log:ret:64; return; }
    local filepath="$1" expected="$2"
    ___x_cmd_eget_verify "$filepath" "$expected"
}
