First, let's assume that I have:

alias foo='path/to/my/program'

in my .zshrc, then I created a completion script ~/.oh-my-zsh/completions/_foo for it, where inside the file I have:

#compdef foo

_foo() {
    echo "hello"


So, I expected that when I type foo [tab] from shell I will see

$foo [tab]

but instead I got

$ foo [tab]_foo

The text _foo was just printed out after I pressed tab.

Do you have any idea for solving this problem?


This is an answer about zsh in general. I don't know oh-my-zsh.

By default, zsh expands aliases before attempting completion. This is usually the right thing. As a consequence, associating a completion function to the name of an alias only has an effect when you bypass the alias, for example after \foo Tab.

You can turn off this behavior with setopt complete_aliases. But you'll lose completion for all aliases for which you don't set up completion explicitly.

If you want to have a special case for foo, the best way is to make it a function instead.

function foo {
  path/to/my/program "$@"

This doesn't explain why _foo is printed. Maybe some oh-my-zsh weirdness.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.