#!/bin/bash

__vipnetclient()
{
    local cur prev opts
    COMPREPLY=()
    cmd="${COMP_WORDS[1]}"
    cur="${COMP_WORDS[COMP_CWORD]}"
    prev="${COMP_WORDS[COMP_CWORD - 1]}"
    cmds="\
start stop installkeys deletekeys reconfigure report \
info list debug iplirdiag dbviewer eventlog fw firewall"

    case "${cmd}" in
        start)
            pattern="--(psw|pin|token-select)"
            if [[ $prev =~ $pattern ]]; then
                COMPREPLY=()
            else
                opts="--no-failprotect --psw --pin --token-select"
                for opt in $(seq 3 $((COMP_CWORD - 1))); do
                    opts="${opts//${COMP_WORDS[$opt]}/}"
                done
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            fi
            return 0
            ;;
        stop | deletekeys | reconfigure)
            if [[ "${prev}" == "--skip-accept" ]]; then
                COMPREPLY=()
            else
                COMPREPLY=($(compgen -W "--skip-accept" -- "${cur}"))
            fi
            return 0
            ;;
        installkeys)
            if [[ $COMP_CWORD -eq 2 ]]; then
                _filedir '@(dst)'
                return 0
            fi

            pattern="--(psw|pin|token-select)"
            if [[ $prev =~ $pattern ]]; then
                COMPREPLY=()
            else
                opts="--no-autostart --no-failprotect --no-start --psw --pin --token-select"
                for opt in $(seq 3 $((COMP_CWORD - 1))); do
                    opts="${opts//${COMP_WORDS[$opt]}/}"
                done
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            fi
            return 0
            ;;
        report)
            if [[ "${prev}" == "--output" ]]; then
                _filedir
            else
                COMPREPLY=($(compgen -W "--output" -- "${cur}"))
            fi
            return 0
            ;;
        info)
            if [[ "${prev}" == "--regulations" ]]; then
                COMPREPLY=($(compgen -W "--psw" -- "${cur}"))
            elif [[ "${prev}" == "--psw" ]]; then
                COMPREPLY=()
            else
                COMPREPLY=($(compgen -W "--regulations" -- "${cur}"))
            fi
            return 0
            ;;
        list)
            pattern="--(nodes|users|tokens)"
            if [[ $prev =~ $pattern ]] || [[ $COMP_CWORD > 2 ]]; then
                COMPREPLY=()
            else
                opts="--nodes --users --tokens"
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            fi
            return 0
            ;;
        debug)
            if [[ "${prev}" == "--loglevel" || "$prev" == "--pin" || "$prev" == "--token-select" ]]; then
                COMPREPLY=()
            elif [[ "${prev}" == "--active-server" ]]; then
                COMPREPLY=($(vipnetclient ${cmd} ${prev} | grep -Po "^${cur}\\w+"))
            elif [[ "${prev}" == "--benchmark" ]]; then
                COMPREPLY=(1400)
            elif [[ "${prev}" == "--tcp-tunnel-mode" ]]; then
                COMPREPLY=($(compgen -W "on off auto" -- "${cur}"))
            elif [[ "${prev}" == "--ping" ]]; then
                COMPREPLY=($(vipnetclient list --nodes | tail +2 | cut -f 1 -d " " | grep -Po "^${cur}\\w+"))
            elif [[ "${COMP_WORDS[@]}" == *"--change-logon-type"* ]]; then
                opts="--pin --token-select"
                for opt in $(seq 2 $((COMP_CWORD - 1))); do
                    opts="${opts//${COMP_WORDS[$opt]}/}"
                done
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            elif [[ $COMP_CWORD == 2 ]]; then
                opts="--loglevel --mftp-reconnect --autostart --no-autostart --active-server --ping \
                --benchmark --tokens --change-logon-type --tcp-tunnel-mode --reload \
                --mdns --no-mdns --mdns-debug --no-mdns-debug --mdns-cache"
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            else
                opts="--loglevel --mftp-reconnect --autostart --no-autostart --active-server --ping \
                --benchmark --tokens --tcp-tunnel-mode --reload \
                --mdns --no-mdns --mdns-debug --no-mdns-debug --mdns-cache"
                for opt in $(seq 2 $((COMP_CWORD - 1))); do
                    opti="${COMP_WORDS[$opt]//--?(no-)/--?(no-)}"
                    opts="${opts//$opti/}"
                done
                COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
            fi
            return 0
            ;;
        iplirdiag)
            if [[ $COMP_CWORD -eq 2 ]]; then
                COMPREPLY=($(compgen -W "-s" -- "${cur}"))
            elif [[ "${prev}" == "-s" ]]; then
                COMPREPLY=($(compgen -W "adapters cipher dnsproxy firewall ipsettings" -- "${cur}"))
            elif [[ "${prev}" == "adapters" ]]; then
                COMPREPLY=($(compgen -W "--stats --info --dumper" -- "${cur}"))
            elif [[ "${prev}" == "cipher" ]]; then
                COMPREPLY=($(compgen -W "--info" -- "${cur}"))
            elif [[ "${prev}" == "dnsproxy" ]]; then
                COMPREPLY=($(compgen -W "--info --query-logging" -- "${cur}"))
            elif [[ "${prev}" == "firewall" ]]; then
                COMPREPLY=($(compgen -W "--stats --static --ip --tcp --udp --udp-bcast --icmp --icmp-bcast --icmp-tcp --icmp-udp --icmp-icmp --wait-rule --natal-bindings --bcast-id --params --counters --used-ports --store --dnsnamedump --unknownips --drv-alg-trace" -- "${cur}"))
            elif [[ "${prev}" == "ipsettings" ]]; then
                COMPREPLY=($(compgen -W "--stats --v-table --v-tun-table --node-info" -- "${cur}"))
            elif [[ "${prev}" == "--node-info" ]]; then
                COMPREPLY=($(vipnetclient list --nodes | tail -n +2 | cut -f 1 -d " " | grep -Po "^${cur}\\w+"))
            else
                COMPREPLY=()
            fi
            return 0
            ;;
        dbviewer)
            COMPREPLY=()
            return 0
            ;;
        eventlog)
            pattern="(--(psw|output|delete)|-o)"
            if [[ $prev =~ $pattern ]]; then
                COMPREPLY=()
            else
                opts=(--output -o --delete --psw)
                for id in $(seq 2 2 $((COMP_CWORD - 1))); do
                    word="${COMP_WORDS[$id]}"
                    pattern="(--option|-o|--delete)"
                    if [[ $word =~ $pattern ]]; then
                        unset opts[0]
                        unset opts[1]
                        unset opts[2]
                    elif [[ $word == "--psw" ]]; then
                        unset opts[3]
                    fi
                done
                COMPREPLY=($(compgen -W "$(echo ${opts[@]})" -- "${cur}"))
            fi
            return 0
            ;;
        fw | firewall)
            if [[ $COMP_CWORD -eq 2 ]]; then
                COMPREPLY=($(compgen -W "--help info public protected" -- "${cur}"))
            elif [[ ${prev} == "--psw" ]]; then
                COMPREPLY=()
            elif [[ ${prev} == "--user-xml" || ${prev} == "--save-user-xml" ]]; then
                _filedir '@(xml)'
            elif [[ "${COMP_WORDS[2]}" == "public" ]]; then
                opts="--block --no-block --psw"
                for opt in $(seq 3 $((COMP_CWORD - 1))); do
                    opti="${COMP_WORDS[$opt]//--?(no-)/--?(no-)}"
                    opts="${opts//$opti/}"
                done
                COMPREPLY=($(compgen -W "$opts" -- "${cur}"))
            elif [[ "${COMP_WORDS[2]}" == "protected" ]]; then
                id=3
                opts=(--policy --no-policy --user-xml --save-user-xml --erase-user-xml --psw)
                while [ $id -lt $COMP_CWORD ]; do
                    case ${COMP_WORDS[$id]} in
                        --psw)
                            id=$((id + 2))
                            unset opts[5]
                            ;;
                        --policy | --no-policy | --erase-user-xml)
                            id=$((id + 1))
                            unset opts[0]
                            unset opts[1]
                            unset opts[2]
                            unset opts[3]
                            unset opts[4]
                            ;;
                        --user-xml | --save-user-xml)
                            id=$((id + 2))
                            unset opts[0]
                            unset opts[1]
                            unset opts[2]
                            unset opts[3]
                            unset opts[4]
                            ;;
                        *) break ;;
                    esac
                done
                COMPREPLY=($(compgen -W "$(echo ${opts[@]})" -- "${cur}"))
            else
                COMPREPLY=()
            fi
            return 0
            ;;
        *) ;;

    esac

    opts="--help --version --no-background"

    if [[ ${cur} == -* ]]; then
        COMPREPLY=($(compgen -W "${opts}" -- "${cur}"))
        return 0
    fi

    COMPREPLY=($(compgen -W "${cmds}" -- "${cur}"))
    return 0
}

complete -F __vipnetclient vipnetclient
