Subject: Re: file completion(?) erases word typed
From: Bart Schaefer <[email-masked]>
To: [email-masked]
Date: Tue, 23 Aug 2016 22:52:04 -0700
List-Id: Zsh Workers List <zsh-workers.zsh.org>

On Aug 23, 10:48pm, Daniel Shahaf wrote:
}
} I noticed something odd in a completion function that (eventually) calls
} _path_files:
} 
} % git config sendemail.smtpserver <TAB><^C> # autoload
} % compdef __git_sendmail_smtpserver_values f 
} % f /usr/bin/gtk-update-icon-cache-3.<TAB>
} % f <CURSOR>
} 
} It erased the word I'd typed.

I'm not certain what's going on here either, but loading up a few more
zstyles and using a completion that's not unique might have provided a 
hint:

torch% f zsh-<TAB>
torch% f /usr/local/bin/zsh-5<TAB>
Completing hashed command by absolute path
/usr/local/bin/zsh-5.0.2-dev-0      /usr/local/bin/zsh-5.0.8          
/usr/local/bin/zsh-5.0.3            /usr/local/bin/zsh-5.1            
/usr/local/bin/zsh-5.0.4            /usr/local/bin/zsh-5.1.1          
/usr/local/bin/zsh-5.0.5            /usr/local/bin/zsh-5.2            
/usr/local/bin/zsh-5.0.7                                              
Completing file
zsh-5.0.2-dev-0*  zsh-5.0.5*        zsh-5.1*                          
zsh-5.0.3*        zsh-5.0.7*        zsh-5.1.1*                        
zsh-5.0.4*        zsh-5.0.8*        zsh-5.2*

Note that it lists the individual files as possible completions.  For
one of those to match the command line, the /usr/local/bin/ prefix
would have to be erased.

Repeated whacking of TAB at this point menu-cycles through only the
"hashed command by absolute path" selections, the base file names are
never offered.

If I append the "." and use list-choices (^D) I get the same listing
as above, but as soon as I hit TAB instead, the whole word is erased
like your example.

There are a couple of curious tidbits in the _complete_debug traces.

Here we add the command path but tell completion that the path prefix
should be removed from the resulting command line when completing:

         +_hashed_absolute_command_paths:6> compadd -M 'l:|=/usr/local/bin/' -J -default- -a 'commands[(R)${~i}[^/]#]'

Here we add all the base names but say the path prefix should be pasted
back on -- but (weirdly) that the path without its leading slash should
be an ignored prefix:

          +_path_files:713> compadd -Qf -J -default- -p usr/local/bin/ -s '' -W /usr/local/bin/ -M 'r:|/=* r:|=*' -a tmp1

I have no idea why ignoring the path minus its leading slash would ever
be correct, but in any case this appears to be adding the full path by
two different and contradictory approaches.