setopt localoptions extendedglob clobber

function __zconvey_usage_zc-take() {
    __zconvey_pinfo2 "Takes a name for current Zsh session, i.e. takes it away from any other session if needed"
    __zconvey_pinfo2 "You can take a name for other session (not the current one) if -i or -n is provided"
    __zconvey_pinfo "Usage: zc-take [-i ID|-n NAME] [-q|--quiet] [-h|--help] NEW_NAME"
    print -- "-h/--help                - this message"
    print -- "-i ID / --id ID          - ID (number) of Zsh session"
    print -- "-n NAME / --name NAME    - NAME of Zsh session"
    print -- "-q/--quiet               - don't output status messages"
}

local -A opthash
zparseopts -E -D -A opthash h -help q -quiet i: -id: n: -name: || { __zconvey_usage_zc-rename; return 1; }

integer have_id=0 have_name=0 quiet=0
local id name new_name="$1"

# Help
(( ${+opthash[-h]} + ${+opthash[--help]} )) && { __zconvey_usage_zc-take; return 0; }
[ -z "$new_name" ] && { echo "No new name given"; __zconvey_usage_zc-take; return 1; }

# ID
have_id=$(( ${+opthash[-i]} + ${+opthash[--id]} ))
(( ${+opthash[-i]} )) && id="${opthash[-i]}"
(( ${+opthash[--id]} )) && id="${opthash[--id]}"

# NAME
have_name=$(( ${+opthash[-n]} + ${+opthash[--name]} ))
(( ${+opthash[-n]} )) && name="${opthash[-n]}"
(( ${+opthash[--name]} )) && name="${opthash[--name]}"

# QUIET
(( quiet = ${+opthash[-q]} + ${+opthash[--quiet]} ))

if [[ "$have_id" != "0" && "$have_name" != "0" ]]; then
    __zconvey_pinfo "Please supply only one of ID (-i) and NAME (-n)"
    return 1
fi

if [[ "$have_id" != "0" && ( "$id" != <-> || "$id" = "0" ) ]]; then
    __zconvey_pinfo "ID must be numeric, 1..100"
    return 1
fi

# Rename via NAME?
if (( $have_name )); then
    __zconvey_resolve_name_to_id "$name"
    local resolved="$REPLY"
    if [ -z "$resolved" ]; then
        echo "Could not find session named: \`$name'"
        return 1
    fi

    # Store the resolved ID and continue normally,
    # with ID as the main specifier of session
    id="$resolved"
elif (( $have_id == 0 )); then
    id="$ZCONVEY_ID"
fi

if [[ "$id" != <-> || "$id" = "0" ]]; then
    __zconvey_pinfo "Bad ID ($id), aborting"
    return 1
fi

if [[ "$id" -gt "100" ]]; then
    __zconvey_pinfo "Maximum nr of sessions is 100, aborting"
    return 1
fi

__zconvey_resolve_name_to_id "$new_name"
local other_id="$REPLY"
if [ -n "$other_id" ]; then
    # The new name exist in system - find an
    # altered name that doesn't exist in system
    # and rename conflicting session, so that
    # $new_name is free
    integer counter=1
    local subst_name
    while (( 1 )); do
        counter+=1
        subst_name="${new_name%%_[[:digit:]]#}_${counter}"
        __zconvey_resolve_name_to_id "$subst_name"
        if [ -z "$REPLY" ]; then
            # Found a name that doesn't exist in system, assign
            # it to the initial conflicting session $new_name
            print ":$subst_name:" > "$ZCONVEY_NAMES_DIR"/"$other_id".name

            (( ${quiet} == 0 )) && __zconvey_pinfo "Pre-rename: $new_name -> $subst_name"

            break
        fi
    done
fi

print ":$new_name:" > "$ZCONVEY_NAMES_DIR"/"$id".name

if (( ${quiet} == 0 )); then
    __zconvey_pinfo2 "Renamed session $id to: $new_name"
fi

local ls_after_rename
zstyle -b ":plugin:zconvey" ls_after_rename ls_after_rename || ls_after_rename="no"
[ "$ls_after_rename" = "yes" ] && print && zc-ls

# vim:ft=zsh
