
if [[ -z "${OIDC_CONFIG_DIR}" ]]; then
  if [ -d ~/.config ];then
    agentdir="$HOME/.config/oidc-agent"
  else
    agentdir="$HOME/.oidc-agent"
  fi
else
  agentdir="$OIDC_CONFIG_DIR"
fi

_elementIn () {
  local e match="$1"
  shift
  for e; do [[ "$e" == "$match" ]] && return 0; done
  return 1
}

_getOptions() {
  IFS=$'\r\n' GLOBIGNORE='*' command eval 'optLines=($($1 -h | grep "^[[:space:]]*-"))'
  usage="$($1 -h | grep Usage:)"
  usage=${usage#*\[OPTION...\]}
  #might add something for ACCOUNT_SHORTNAME here
  usage=$(echo $usage | sed -r -e 's/^.*\[?ACCOUNT_SHORTNAME\]?[[:space:]]*//')
  IFS=$'\r\n' GLOBIGNORE='*' command eval 'singleOpts=($(echo "${usage}"  | sed "s/|/\n/g"| sed -e "s/^[[:space:]]*//" -e "s/[[:space:]]*$//"))'
  opts=""
  singleOptsLong="--help#--usage#--version"
  for var in "${optLines[@]}"
  do
    IFS=$'\r\n' GLOBIGNORE='*' command eval 'elements=($(echo "${var}"  | sed -e "s/^[[:space:]]*//" -e "s/,//g" -e "s/[[:space:]]*$//"| sed "s/[[:space:]]/\n/g"))'
    shortname=""
    longnames=()
    for el in "${elements[@]}"
    do
      if [[ $el == --* ]] ; then
        longname=$el
        longnames+=($longname)
        if [[ $longname == *=* ]]; then
          if [[ $longname == *\[=*\] ]]; then
            longparam="${longname%\[=*}="
            opts+="${longname%\[=*} #"
            argument=${longname#*\[=}
            argument=${argument:0:-1}
          else
            longparam="${longname%=*}="
            argument=${longname#*=}
          fi
          argument=$(echo $argument | sed 's/|/ &/g')
          suboptions[$longparam]="$argument "
        else
          longparam="$longname "
        fi
        opts+="$longparam#"
      fi
      if [[ $el == -[a-zA-Z], ]]; then
        shortname="${el:0:-1}"
      fi
    done
    if  _elementIn $shortname "${singleOpts[@]}"; then
      for longname in "${longnames[@]}"; do
        singleOptsLong+="#${longname}"
      done
    fi
  done
}

_matchFiles() {
  local IFS=$'\n'
  local LASTCHAR=' '

  COMPREPLY=($(compgen -o plusdirs -f  -- "$1"))

  if [ ${#COMPREPLY[@]} = 1 ]; then
    [ -d "$COMPREPLY" ] && LASTCHAR=/
    COMPREPLY=$(printf %q%s "$COMPREPLY" "$LASTCHAR")
  else
    for ((i=0; i < ${#COMPREPLY[@]}; i++)); do
      [ -d "${COMPREPLY[$i]}" ] && COMPREPLY[$i]=${COMPREPLY[$i]}/
    done
  fi

  return 0
}

_suboption() {
  ret=0
  for key in "${!suboptions[@]}";
  do
    if [[ "$key" == "$1" ]]; then
      option="${suboptions[$key]}"
      case $option in
        TIME[[:space:]] )
          local value=999999999999
          COMPREPLY=( $( compgen -W "{${value:1:((${#value}-2))}}" \
            -- "$cur" ) )
          ;;
        FILE[[:space:]] )
          _matchFiles ${cur}
          ;;
        ISSUER[[:space:]] | ISSUER_URL[[:space:]] )
            if [ -f "$agentdir/issuer.config" ]; then
              issuers=`cat $agentdir/issuer.config | awk '{print $1}' | sed -e 's/$/& /g'`
            else
              issuers=""
            fi
            compreply=( $(compgen -W "${issuers[*]}" -- "$cur") )
            COMPREPLY=( "${compreply[@]}" )
            __ltrim_colon_completions "$cur"
            if [[ ${#COMPREPLY[@]} -gt 1 ]]; then
              local common_prefix
              _common_prefix common_prefix "${COMPREPLY[@]}"
              if [[ $common_prefix == "$CUR" ]]; then
                COMPREPLY=( "${compreply[@]}" " " )
              fi
            fi
          ;;
        [[:upper:]_]* )
          ;;
        [[:lower:]]* )
          local IFS=$'|\n'
          COMPREPLY=( $(compgen -W "${option}" -- ${cur}) )
          ;;
      esac
      ret=1
      break
    fi
  done
}


_isSingleOpt() {
  for word in $singleOptsLong; do
    if [[ "$word" = "$1" ]]; then
      return 0
    fi
  done
  return 1
}

_needArgument() {
  local IFS=$'#'
  for ((i=1; i<$COMP_CWORD; i++)); do
    local word="${COMP_WORDS[i]}"
    local pre="${COMP_WORDS[i-1]}"
    if [[ $word != -* ]] && [[ "$word" != "=" ]] && [[ "$pre" != "=" ]]; then
      return 1
    fi
    if _isSingleOpt $word ; then
      return 1
    fi
  done
  return 0
}

_oidc-gen() {
local cur prev prevprev word cword opts
local CUR=$2
COMPREPLY=()
_get_comp_words_by_ref -n : cur prev words cword
prevprev="${words[cword-2]}"
local IFS=$'\t\n'
shortnames=`ls $agentdir 2>/dev/null | grep -v "config" | sed -e 's/$/& /g'`

declare -A suboptions
_getOptions "oidc-gen"
local IFS=$'#\n'
if [[ "$cur" == "=" ]]; then
  prev+="="
  cur=""
fi
if [[ "$prev" == "=" ]]; then
  prev="$prevprev$prev"
fi

_suboption $prev
if [[ "$prev" == "--print=" || "$prev" == "-p" ]]; then
  _matchFiles ${cur}
  local oidcDirFiles=`ls $agentdir 2>/dev/null | sed -e 's/$/& /g'`
  COMPREPLY+=( $(compgen -W "${oidcDirFiles}" -- ${cur}) )
fi
if [[ "$prev" == "--update=" || "$prev" == "-u" ]]; then
  _matchFiles ${cur}
  local oidcDirFiles=`ls $agentdir 2>/dev/null | sed -e 's/$/& /g'`
  COMPREPLY+=( $(compgen -W "${oidcDirFiles}" -- ${cur}) )
fi
if [[ "$prev" == "--manual" || "$prev" == "-m" ]]; then
  COMPREPLY=( $(compgen -W "${shortnames}" -- ${cur}) )
fi
if [[ "x$ret" == "x1" ]]; then
  return 0
fi

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

_common_prefix() {
  local vname=$1
  local first prefix v

  shift
  if [[ $# -eq 0 ]]; then
    local "$vname" && _upvars -v "$vname" ""
    return 0
  fi

  first=$1
  shift
  for ((i = 0; i < ${#first}; ++i)); do
    prefix=${first:0:i+1}
    for v; do
      if [[ ${v:0:i+1} != "$prefix" ]]; then
        local "$vname" && _upvars -v "$vname" "${first:0:i}"
        return 0
      fi
    done
  done

  local "$vname" && _upvars -v "$vname" "$first"
  return 0
}

_oidc-token() {
local cur prev prevprev word cword opts
local CUR=$2
COMPREPLY=()
_get_comp_words_by_ref -n : cur prev words cword
prevprev="${words[cword-2]}"
local IFS=$'\t\n'
declare -A suboptions
_getOptions "oidc-token"
# shortnames=`ls $agentdir 2>/dev/null | grep -v "config" | sed -e 's/$/& /g'`
# issuers=`cat $agentdir/issuer.config | awk '{print $1}' | sed -e 's/$/& /g'`
if [ -f "$agentdir/issuer.config" ]; then
  shortnamesAndIssuers=`{ ls $agentdir 2>/dev/null | grep -v "config" & cat $agentdir/issuer.config | awk '{print $1}'; } | sed -e 's/$/& /g'`
else
  shortnamesAndIssuers=""
fi

if [[ ${cur} == -* ]] ; then
  local IFS=$'#\n'
  COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
  return 0
fi

if [[ "$cur" == "=" ]]; then
  prev+="="
  cur=""
fi
if [[ "$prev" == "=" ]]; then
  prev="$prevprev$prev"
fi
# _suboption $prev
# if [[ "x$ret" == "x1" ]]; then
#   return 0
# fi
if [[ ${cur} == * ]]  ; then
  compreply=( $(compgen -W "${shortnamesAndIssuers[*]}" -- "$cur") )
  COMPREPLY=( "${compreply[@]}" )
  __ltrim_colon_completions "$cur"

  if [[ ${#COMPREPLY[@]} -gt 1 ]]; then
    local common_prefix
    _common_prefix common_prefix "${COMPREPLY[@]}"
    if [[ $common_prefix == "$CUR" ]]; then
      COMPREPLY=( "${compreply[@]}" " " )
    fi
  fi
  return 0
fi
return 0
}

_oidc-add() {
local cur prev opts
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
prev="${COMP_WORDS[COMP_CWORD-1]}"
prevprev="${COMP_WORDS[COMP_CWORD-2]}"
local IFS=$'\t\n'
declare -A suboptions
_getOptions "oidc-add"
shortnames=`ls $agentdir 2>/dev/null | grep -v "config" | sed -e 's/$/& /g'`
if [[ "$cur" == "=" ]]; then
  prev+="="
  cur=""
fi
if [[ "$prev" == "=" ]]; then
  prev="$prevprev$prev"
fi

_suboption $prev
if [[ "x$ret" == "x1" ]]; then
  return 0
fi
if [[ ${cur} == -* ]] ; then
  local IFS=$'#\n'
  COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
  return 0
fi
if [[ ${cur} == * ]] &&  _needArgument ; then
  COMPREPLY=( $(compgen -W "${shortnames}" -- ${cur}) )
  return 0
fi
return 0
}

_oidc-agent() {
local cur prev opts
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
prev="${COMP_WORDS[COMP_CWORD-1]}"
local IFS=$'\t\n'
declare -A suboptions
_getOptions "oidc-agent"

if [[ ${cur} == * ]] ; then
  local IFS=$'#\n'
  COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
  return 0
fi
return 0
}

_oidc-keychain() {
local cur prev opts
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
prev="${COMP_WORDS[COMP_CWORD-1]}"
local IFS=$'\t\n'
declare -A suboptions
_getOptions "oidc-agent"
opts+="--accounts #"

if _elementIn "--accounts" "${COMP_WORDS[@]}"; then
  shortnames=`ls $agentdir 2>/dev/null | grep -v "config" | sed -e 's/$/& /g'`
  COMPREPLY=( $(compgen -W "${shortnames}" -- ${cur}) )
  return 0
fi
if [[ ${cur} == * ]] ; then
  local IFS=$'#\n'
  COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
  return 0
fi
return 0
}

complete -o nospace -F _oidc-gen oidc-gen
complete -o nospace -F _oidc-token oidc-token
complete -o nospace -F _oidc-add oidc-add
complete -o nospace -F _oidc-agent oidc-agent
complete -o nospace -F _oidc-keychain oidc-keychain
