fix(virtualenvwrapper): several changes for checking git directory, including fixes (#5663)
* Test only for the presence of a .git directory in virtualenvwrapper
Instead of using both $(git rev-parse --show-toplevel) and a check for
a .git directory, use just the latter. As well as being redundant
the former does not work quite so well when using multiple worktrees;
each worktree will be treated as a separate project.
* Unset ENV_NAME & deactivate if no virtualenv found
This addresses #4603 without breaking current behaviour (where current
behaviour is correct).
When changing directories, if there is no environment matching
ENV_NAME, ENV_NAME is emptied and deactivate called if there is a
current environment active (based on CD_VIRTUAL_ENV).
* Use path comparison not string comparison for paths
This will solve part of issue #4255 where WORKON_HOME is defined with a
trailing slash or not normalised in some way, as well as instances
where symlinks are used, and any other instances where constructed
paths don't exactly match even though they go to the same file.
Co-authored-by: Robby Russell <robby@planetargon.com>
Diff
1diff --git a/plugins/virtualenvwrapper/virtualenvwrapper.plugin.zsh b/plugins/virtualenvwrapper/virtualenvwrapper.plugin.zsh
2index 88217a7f5bcc74a7bc8c7573b0db829cca850bd2..c30216f51b326b6c2c8a22ded568d02fb8db53c5 100644
3--- a/plugins/virtualenvwrapper/virtualenvwrapper.plugin.zsh
4+++ b/plugins/virtualenvwrapper/virtualenvwrapper.plugin.zsh
5@@ -35,27 +35,19 @@ if [[ ! $DISABLE_VENV_CD -eq 1 ]]; then
6 function workon_cwd {
7 if [[ -z "$WORKON_CWD" ]]; then
8 local WORKON_CWD=1
9- # Check if this is a Git repo
10- local GIT_REPO_ROOT=""
11- local GIT_TOPLEVEL="$(git rev-parse --show-toplevel 2> /dev/null)"
12- if [[ $? == 0 ]]; then
13- GIT_REPO_ROOT="$GIT_TOPLEVEL"
14- fi
15 # Get absolute path, resolving symlinks
16 local PROJECT_ROOT="${PWD:A}"
17 while [[ "$PROJECT_ROOT" != "/" && ! -e "$PROJECT_ROOT/.venv" \
18- && ! -d "$PROJECT_ROOT/.git" && "$PROJECT_ROOT" != "$GIT_REPO_ROOT" ]]; do
19+ && ! -d "$PROJECT_ROOT/.git" ]]; do
20 PROJECT_ROOT="${PROJECT_ROOT:h}"
21 done
22- if [[ "$PROJECT_ROOT" == "/" ]]; then
23- PROJECT_ROOT="."
24- fi
25+
26 # Check for virtualenv name override
27 if [[ -f "$PROJECT_ROOT/.venv" ]]; then
28 ENV_NAME="$(cat "$PROJECT_ROOT/.venv")"
29 elif [[ -f "$PROJECT_ROOT/.venv/bin/activate" ]];then
30 ENV_NAME="$PROJECT_ROOT/.venv"
31- elif [[ "$PROJECT_ROOT" != "." ]]; then
32+ elif [[ "$PROJECT_ROOT" != "/" ]]; then
33 ENV_NAME="${PROJECT_ROOT:t}"
34 else
35 ENV_NAME=""
36@@ -68,14 +60,21 @@ if [[ ! $DISABLE_VENV_CD -eq 1 ]]; then
37 fi
38 if [[ "$ENV_NAME" != "" ]]; then
39 # Activate the environment only if it is not already active
40- if [[ "$VIRTUAL_ENV" != "$WORKON_HOME/$ENV_NAME" ]]; then
41+ if [[ ! "$VIRTUAL_ENV" -ef "$WORKON_HOME/$ENV_NAME" ]]; then
42 if [[ -e "$WORKON_HOME/$ENV_NAME/bin/activate" ]]; then
43 workon "$ENV_NAME" && export CD_VIRTUAL_ENV="$ENV_NAME"
44 elif [[ -e "$ENV_NAME/bin/activate" ]]; then
45 source $ENV_NAME/bin/activate && export CD_VIRTUAL_ENV="$ENV_NAME"
46+ else
47+ ENV_NAME=""
48 fi
49 fi
50 fi
51+ if [[ "$ENV_NAME" == "" && -n $CD_VIRTUAL_ENV && -n $VIRTUAL_ENV ]]; then
52+ # We've just left the repo, deactivate the environment
53+ # Note: this only happens if the virtualenv was activated automatically
54+ deactivate && unset CD_VIRTUAL_ENV
55+ fi
56 fi
57 }
58