This seems something like an XY problem; what exactly motivates this changing of the completion via a provided option? Like could the change instead be done via an environment variable, or why does the completion need to vary?
Anyways, a file at some point during the option processing may cause problems depending on where
-f ... appears relative to other things on the command line. Also the completion code will be repeatedly invoked so maintaining state across different calls to the same and new instances of a command may be tricky. And also
$(cat /tmp/file_with_opts) is bad as it needlessly forks out to
cat and then splits the contents on...well, who knows.
With these problems in mind, one way to figure out what options are available is to add something like
set > ~/tmp/what-is-set to an appropriate part of the completion code, then hit tab with the cursor at various places with and without the
-f ... option and then check the output file to see what things are available to a completion script:
% 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 )
In that case I was tab completing just after
foo and before
-f ..., so to vary the completion behavior one could check
BUFFER or better yet the
words array as
BUFFER might have
-f ... from other commands unrelated to your program that could confuse your completion script.
So if we loop over
words, we can vary what file is read depending on whether (without much error checking) the
-f ... option is present with something like:
local curcontext="$curcontext" state line ret=1
_arguments -C -S \
'-f[input file]:filename:_files' \
case "$state" in
#set > ~/tmp/what-is-set
# default filename
for (( i = 1; i <= $#words - 1; i++ )); do
if [[ $words[$i] == -f ]]; then
# cat-free read of file with split on newlines
_wanted t expl "available options" compadd -a t
It may be helpful to study the existing completions under the