1

Например, у меня есть исполняемый файл тестового app

#!/bin/bash
case $1 in
  (foo)
    echo "selected foo"
    ;;
  (bar)
    echo "selected bar"
    ;;
esac

И простое завершение для него включено в fpath

#compdef app
local -a subcmds
subcmds=('foo:show foo' 'bar:show bar')
_describe 'app' subcmds

Работает нормально. Теперь я хочу сделать оболочку, которая добавляет подкоманду в приложение

__app_wrapper () {
    if [[ "$1" == baz ]]; then
        echo "selected baz"
    else
        command app "$@"
    fi
}

alias app=__app_wrapper

Как только я получаю source , подкоманда работает нормально, но автозаполнение переключается на завершение с файлами в текущем каталоге вместо того, что предоставляет мой скрипт завершения. Почему это и как это исправить? Это потому, что приложение теперь является функцией вместо исполняемого?

На самом деле я пытаюсь использовать более сложный скрипт завершения для docker-machine но мне удалось свести мою проблему к этому примеру.

1 ответ1

1

Решение состояло в том, чтобы использовать compdef , вот что я закончил (для моего реального случая):

#
# Function wrapper to docker-machine that adds a use subcommand.
#
# The use subcommand runs `eval "$(docker-machine env [args])"`, which is a lot
# less typing.
#
# To enable:
#  1a. Copy this file somewhere and source it in your .bashrc
#      source /some/where/docker-machine-wrapper.bash
#  1b. Alternatively, just copy this file into into /etc/bash_completion.d
#
# Configuration:
#
# DOCKER_MACHINE_WRAPPED
#   When set to a value other than true, this will disable the alias wrapper
#   alias for docker-machine. This is useful if you don't want the wrapper,
#   but it is installed by default by your installation.
#

: ${DOCKER_MACHINE_WRAPPED:=true}

__docker_machine_wrapper () {
    if [[ "$1" == use ]]; then
        # Special use wrapper
        shift 1
        case "$1" in
            -h|--help|"")
                cat <<EOF
Usage: docker-machine use [OPTIONS] [arg...]
Evaluate the commands to set up the environment for the Docker client
Description:
   Argument is a machine name.
Options:
   --swarm  Display the Swarm config instead of the Docker daemon
   --unset, -u  Unset variables instead of setting them
EOF
                ;;
            *)
                eval "$(docker-machine env "$@")"
                echo "Active machine: ${DOCKER_MACHINE_NAME}"
                ;;
        esac
    elif [[ "$1" == "--help" || "$1" == "-h" ]]; then
    command docker-machine "$@"
        echo "  use         Get the URL of a machine"
    else
        # Just call the actual docker-machine app
        command docker-machine "$@"
    fi
}

if [[ ${DOCKER_MACHINE_WRAPPED} = true ]]; then
    alias docker-machine=__docker_machine_wrapper
    compdef __docker_machine_wrapper=docker-machine
fi

Кроме того, я отредактировал фактический файл завершения, чтобы показать имена машин

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .