ZSH 완료 스크립트에서 제공된 매개변수에 변수로 액세스할 수 있는 방법이 있습니까?
예는 다음과 같습니다.
#compdef test
_test_comp(){
t=($(cat /tmp/file_with_opts))
_wanted t expl "availavle options" compadd -a t
}
_arguments -C -S \
'-f[input file]:filename:_files' \
'*:test_autocomplete:_test_comp'
스크립트 test
는 하드코딩된 파일에서 옵션을 선택 /tmp/file_with_opts
하고 를 통해 정의된 파일에서 자동 완성 옵션을 선택할 수 있기를 원합니다 -f
. 또는 -f <filename>
정의된 경우 기본 파일 대신 이 파일을 구문 분석하고 싶습니다. 이를 수행하는 방법에 대한 조언이 있습니까?
답변1
이것은 XY 문제와 약간 비슷해 보입니다. 제공된 옵션을 사용하여 수행되는 방식의 변경에 정확히 동기를 부여하는 것은 무엇입니까? 환경 변수를 통해 변경을 수행할 수 있거나 변경을 수행해야 하는 이유는 무엇입니까?
그럼에도 불구하고 옵션 처리 중 어느 시점에서 파일은 -f ...
명령줄의 다른 내용과 관련하여 나타나는 위치에 따라 문제를 일으킬 수 있습니다. 또한 완료 코드는 반복적으로 호출되므로 동일한 명령 인스턴스와 새 인스턴스에 대한 서로 다른 호출 간의 상태를 유지하는 것이 까다로울 수 있습니다. 그리고 콘텐츠를 $(cat /tmp/file_with_opts)
불필요하게 분기한 다음 분할하기 때문에 좋지 않습니다 . 글쎄요, 누가 알겠습니까?cat
이러한 문제를 염두에 두고 어떤 옵션을 사용할 수 있는지 알아내는 한 가지 방법은 set > ~/tmp/what-is-set
완성 코드의 적절한 부분에 이와 같은 내용을 추가한 다음 options 유무에 관계없이 여러 위치에 커서를 놓고 탭한 -f ...
다음 출력 파일을 검사하여 완료 스크립트에 사용할 수 있는 항목을 확인하세요.
% grep file_ what-is-set
BUFFER='foo -f file_with_opts '
RBUFFER=' -f file_with_opts '
opt_args=( [-f]=file_with_opts )
words=( foo '' -f file_with_opts )
이 경우에는 foo
이후 및 이전에 탭 완성을 수행하고 -f ...
있으므로 완료 동작을 변경하기 위해 프로그램 과 관련되지 않은 다른 명령이 완료 스크립트를 혼동할 수 있으므로 배열을 확인 BUFFER
하거나 더 잘 확인할 수 있습니다.words
BUFFER
-f ...
따라서 루프를 실행하면 다음과 같이 words
옵션이 있는지 여부에 따라(많은 오류 검사 없이) 읽은 파일을 변경할 수 있습니다 -f ...
.
#compdef foo
local curcontext="$curcontext" state line ret=1
_arguments -C -S \
'-f[input file]:filename:_files' \
'*:options:->vary' \
&& ret=0
case "$state" in
vary)
integer i
local optsfile
#set > ~/tmp/what-is-set
# default filename
optsfile=~/tmp/file_with_opts
for (( i = 1; i <= $#words - 1; i++ )); do
if [[ $words[$i] == -f ]]; then
optsfile=$words[$((i+1))]
break
fi
done
# cat-free read of file with split on newlines
t=(${(f)"$(<$optsfile)"})
_wanted t expl "available options" compadd -a t
;;
esac
return $ret
이 디렉토리 $fpath[-1]
의 기존 완료 항목을 조사하는 것이 도움이 될 수 있습니다 .