Skip to content

Instantly share code, notes, and snippets.

@austinjp
Last active July 4, 2025 10:02
Show Gist options
  • Save austinjp/6aa676cc8ef194b444160262a323dc70 to your computer and use it in GitHub Desktop.
Save austinjp/6aa676cc8ef194b444160262a323dc70 to your computer and use it in GitHub Desktop.
Automatic aliases in bash

I use direnv to automatically set environment variables per directory. It's great, but there's no elegant solution for aliases with direnv. So I rolled my own, inspired by this answer on Ask Ubuntu.

Add a few lines to your .bashrc and place custom aliases into a .aliases file in any directory. Those aliases will be set when you enter that dir, and unset when you leave.

It's certainly not perfect and there are doubtless some gotchas, but it's pretty handy.

Add the following to your .bashrc so whenever you start a shell, it will load the .aliases file in whichever dir your shell has started. You should add it somewhere after your other aliases are defined/loaded.

function _aliases_add() {
    source ./.aliases 2>/dev/null || :
}

function cd() {
    # Before leaving dir, unset aliases.
    if [[ -f ./.aliases ]]; then
        # Remove custom aliases
        kill_list=$(sed -re 's/^alias ([^=]+).+/\1/g' ./.aliases | tr $'\n' ' ')
        echo "Reverting aliases: ${kill_list}"
        unalias $kill_list || :

        # Then restore all previous aliases:
        source ~/.bash_aliases 2>/dev/null || :
    fi

    # Do the actual "cd".
    [[ -z "$*" ]] && builtin cd $HOME >/dev/null || :
    [[ -n "$*" ]] && builtin cd "$*"  >/dev/null || :

    # Add local aliases.
    if [[ -f ./.aliases ]]; then
        add_list=$(sed -re 's/^alias ([^=]+).+/\1/g' ./.aliases | tr $'\n' ' ')
        echo "Aliasing: ${add_list}"
        _aliases_add
    fi
}

# Hook to ensure aliases are added whenever prompt is displayed.
_aliases_hook() {
    # This inspired by (lovingly copied off from) direnv.
    local previous_exit_status=$?;
    trap -- '' SIGINT;

    _aliases_add

    trap - SIGINT;
    return $previous_exit_status;
};

if ! [[ "${PROMPT_COMMAND:-}" =~ _aliases_hook ]]; then
    PROMPT_COMMAND="_aliases_hook${PROMPT_COMMAND:+;$PROMPT_COMMAND}"
fi

The .aliases file should contain standard bash aliases, so for example something like this:

alias go=go1.24.4
alias ag="ag --python"
alias tree="tree --gitignore --ignore-case -I venv -I 'venv*'"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment