python 虚拟环境已通过 WSL 成功激活但无法正常工作
python virtual env succesfully activated via WSL but not working
在我的 windows 系统上,我已经使用 windows 命令提示符
成功安装了虚拟环境(python 版本是 3.9)
python -m venv C:\my_path\my_venv
总是使用 windows 命令提示符,我可以通过
激活创建的 venv
C:\my_path\my_venv\Scripts\activate.bat
我确定 venv 已正确激活,因为:
- 在 windows 终端上,我看到命令行前面有
(my_venv)
- 如果我从终端 (
python
) 激活 python 和 运行 以下命令: import sys
; sys.path
我可以在路径列表中看到所需的路径 [..., 'C:\my_path\my_venv\lib\site-packages\win32\lib', ...]
- 如果我在激活的 venv 中做一些事情(比如安装包)一切正常并且在 venv 中完成
总而言之,到目前为止一切都很好。
我也有 WSL2 (Ubuntu),我想使用 Ubuntu 终端激活相同的 venv。
如果我从 Ubuntu 终端激活 venv
source /mnt/c/my_path/my_venv/Scripts/activate
它似乎可以工作,因为命令行前面有 (my_venv)
,但是当我 运行 python(python3
命令)然后 运行 import sys
; sys.path
我看到系统针对基础 Ubuntu python 安装(3.8 版)而不是 venv 安装:
['', '/usr/lib/python38.zip', '/usr/lib/python3.8', '/usr/lib/python3.8/lib-dynload', '/usr/local/lib/python3.8/dist-packages', '/usr/lib/python3/dist-packages']
venv 并未真正激活。有什么解决问题的建议吗?
如果有帮助,我补充一些信息。
如果我尝试直接使用 Ubuntu 终端创建一个 venv
python3 -m venv /mnt/c/my_path/my_venv_unix
并通过 Ubuntu 终端激活它 (source /mnt/c/my_path/my_venv_unix/bin/activate
) 一切正常,但这不是我想要的:我想使用 WSL 激活使用 [= 创建的虚拟环境80=] 命令提示符,因为在我的机器上我有很多用 windows 创建的 venvs,我不想复制它们。
按照脚本 C:\my_path\my_venv\Scripts\activate(/mnt/c/my_path/my_venv/Scripts/activate 使用 wsl 文件夹命名)(我必须将 EOL 从 windows 更改为 Ubuntu,否则命令 source /mnt/c/my_path/my_venv/Scripts/activate
不会起作用)
# This file must be used with "source bin/activate" *from bash*
# you cannot run it directly
deactivate () {
# reset old environment variables
if [ -n "${_OLD_VIRTUAL_PATH:-}" ] ; then
PATH="${_OLD_VIRTUAL_PATH:-}"
export PATH
unset _OLD_VIRTUAL_PATH
fi
if [ -n "${_OLD_VIRTUAL_PYTHONHOME:-}" ] ; then
PYTHONHOME="${_OLD_VIRTUAL_PYTHONHOME:-}"
export PYTHONHOME
unset _OLD_VIRTUAL_PYTHONHOME
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r 2> /dev/null
fi
if [ -n "${_OLD_VIRTUAL_PS1:-}" ] ; then
PS1="${_OLD_VIRTUAL_PS1:-}"
export PS1
unset _OLD_VIRTUAL_PS1
fi
unset VIRTUAL_ENV
if [ ! "${1:-}" = "nondestructive" ] ; then
# Self destruct!
unset -f deactivate
fi
}
# unset irrelevant variables
deactivate nondestructive
VIRTUAL_ENV="C:\my_path\my_venv"
export VIRTUAL_ENV
_OLD_VIRTUAL_PATH="$PATH"
PATH="$VIRTUAL_ENV/Scripts:$PATH"
export PATH
# unset PYTHONHOME if set
# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)
# could use `if (set -u; : $PYTHONHOME) ;` in bash
if [ -n "${PYTHONHOME:-}" ] ; then
_OLD_VIRTUAL_PYTHONHOME="${PYTHONHOME:-}"
unset PYTHONHOME
fi
if [ -z "${VIRTUAL_ENV_DISABLE_PROMPT:-}" ] ; then
_OLD_VIRTUAL_PS1="${PS1:-}"
PS1="(.venv_ml_dl_gen_purpose) ${PS1:-}"
export PS1
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r 2> /dev/null
fi
最后,这里还有脚本/mnt/c/my_path/my_venv_unix/bin/activate
# This file must be used with "source bin/activate" *from bash*
# you cannot run it directly
deactivate () {
# reset old environment variables
if [ -n "${_OLD_VIRTUAL_PATH:-}" ] ; then
PATH="${_OLD_VIRTUAL_PATH:-}"
export PATH
unset _OLD_VIRTUAL_PATH
fi
if [ -n "${_OLD_VIRTUAL_PYTHONHOME:-}" ] ; then
PYTHONHOME="${_OLD_VIRTUAL_PYTHONHOME:-}"
export PYTHONHOME
unset _OLD_VIRTUAL_PYTHONHOME
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r
fi
if [ -n "${_OLD_VIRTUAL_PS1:-}" ] ; then
PS1="${_OLD_VIRTUAL_PS1:-}"
export PS1
unset _OLD_VIRTUAL_PS1
fi
unset VIRTUAL_ENV
if [ ! "${1:-}" = "nondestructive" ] ; then
# Self destruct!
unset -f deactivate
fi
}
# unset irrelevant variables
deactivate nondestructive
VIRTUAL_ENV="/mnt/c/my_path/my_venv_unix"
export VIRTUAL_ENV
_OLD_VIRTUAL_PATH="$PATH"
PATH="$VIRTUAL_ENV/bin:$PATH"
export PATH
# unset PYTHONHOME if set
# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)
# could use `if (set -u; : $PYTHONHOME) ;` in bash
if [ -n "${PYTHONHOME:-}" ] ; then
_OLD_VIRTUAL_PYTHONHOME="${PYTHONHOME:-}"
unset PYTHONHOME
fi
if [ -z "${VIRTUAL_ENV_DISABLE_PROMPT:-}" ] ; then
_OLD_VIRTUAL_PS1="${PS1:-}"
if [ "x(venv_unix) " != x ] ; then
PS1="(venv_unix) ${PS1:-}"
else
if [ "`basename \"$VIRTUAL_ENV\"`" = "__" ] ; then
# special case for Aspen magic directories
# see https://aspen.io/
PS1="[`basename \`dirname \"$VIRTUAL_ENV\"\``] $PS1"
else
PS1="(`basename \"$VIRTUAL_ENV\"`)$PS1"
fi
fi
export PS1
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r
fi
感谢所有愿意回答的人!
简短回答:强烈建议在 WSL 中使用 Python 的 Linux 版本和工具。您会在 Stack Overflow 上找到许多与此相关的帖子,但您的问题非常不同(关于 venv),值得单独回答。
更多详情:
同样值得一读。在那种情况下,问题是关于双引导系统以及是否可以在 Windows 和 Linux 之间共享相同的 venv。
我知道 似乎 WSL 上的东西可能会更好,在那里你可以 运行 Windows .exe
cutables 在 Linux,但它确实不适用于这种特殊情况。
您已经解决了第一个问题,即行尾的差异,但您面临的下一个问题是目录格式的差异。采购 activate
后,执行 echo $PATH
,您会看到 Windows 样式 C:\path\to\the\venv
路径已添加到您的 PATH
。对于 WSL,需要 /mnt/c/path/to/the/venv
.
那是行不通的。
一旦你解决了这个问题(同样,通过编辑 activate
),你仍然在尝试 运行 python3
。 venv 可执行文件实际上是 python.exe
。在 WSL 下,您必须指定扩展名。
所以如果你:
- 将行尾从 CRLF 更改为 LF
- 将
activate
中的路径样式从 Windows 更改为 WSL2 格式
- 使用
python.exe
可执行文件
那么你至少可以启动 Windows Python 版本。您的 import sys; sys.path
将显示 Windows 路径。
就是说,您几乎肯定会 运行 遇到其他不值得这样做的问题。例如,如果脚本假定 python
或 python3
,甚至 pip
;那么那些将失败,因为它需要调用,例如 pip.exe
.
行尾和本机代码也会成为问题。
出于这些原因(可能更多),强烈建议在 WSL 中使用 Python 的 Linux 版本。
在我的 windows 系统上,我已经使用 windows 命令提示符
成功安装了虚拟环境(python 版本是 3.9) python -m venv C:\my_path\my_venv
总是使用 windows 命令提示符,我可以通过
激活创建的 venvC:\my_path\my_venv\Scripts\activate.bat
我确定 venv 已正确激活,因为:
- 在 windows 终端上,我看到命令行前面有
(my_venv)
- 如果我从终端 (
python
) 激活 python 和 运行 以下命令:import sys
;sys.path
我可以在路径列表中看到所需的路径[..., 'C:\my_path\my_venv\lib\site-packages\win32\lib', ...]
- 如果我在激活的 venv 中做一些事情(比如安装包)一切正常并且在 venv 中完成
总而言之,到目前为止一切都很好。
我也有 WSL2 (Ubuntu),我想使用 Ubuntu 终端激活相同的 venv。 如果我从 Ubuntu 终端激活 venv
source /mnt/c/my_path/my_venv/Scripts/activate
它似乎可以工作,因为命令行前面有 (my_venv)
,但是当我 运行 python(python3
命令)然后 运行 import sys
; sys.path
我看到系统针对基础 Ubuntu python 安装(3.8 版)而不是 venv 安装:
['', '/usr/lib/python38.zip', '/usr/lib/python3.8', '/usr/lib/python3.8/lib-dynload', '/usr/local/lib/python3.8/dist-packages', '/usr/lib/python3/dist-packages']
venv 并未真正激活。有什么解决问题的建议吗?
如果有帮助,我补充一些信息。
如果我尝试直接使用 Ubuntu 终端创建一个 venv
python3 -m venv /mnt/c/my_path/my_venv_unix
并通过 Ubuntu 终端激活它 (source /mnt/c/my_path/my_venv_unix/bin/activate
) 一切正常,但这不是我想要的:我想使用 WSL 激活使用 [= 创建的虚拟环境80=] 命令提示符,因为在我的机器上我有很多用 windows 创建的 venvs,我不想复制它们。
按照脚本 C:\my_path\my_venv\Scripts\activate(/mnt/c/my_path/my_venv/Scripts/activate 使用 wsl 文件夹命名)(我必须将 EOL 从 windows 更改为 Ubuntu,否则命令 source /mnt/c/my_path/my_venv/Scripts/activate
不会起作用)
# This file must be used with "source bin/activate" *from bash*
# you cannot run it directly
deactivate () {
# reset old environment variables
if [ -n "${_OLD_VIRTUAL_PATH:-}" ] ; then
PATH="${_OLD_VIRTUAL_PATH:-}"
export PATH
unset _OLD_VIRTUAL_PATH
fi
if [ -n "${_OLD_VIRTUAL_PYTHONHOME:-}" ] ; then
PYTHONHOME="${_OLD_VIRTUAL_PYTHONHOME:-}"
export PYTHONHOME
unset _OLD_VIRTUAL_PYTHONHOME
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r 2> /dev/null
fi
if [ -n "${_OLD_VIRTUAL_PS1:-}" ] ; then
PS1="${_OLD_VIRTUAL_PS1:-}"
export PS1
unset _OLD_VIRTUAL_PS1
fi
unset VIRTUAL_ENV
if [ ! "${1:-}" = "nondestructive" ] ; then
# Self destruct!
unset -f deactivate
fi
}
# unset irrelevant variables
deactivate nondestructive
VIRTUAL_ENV="C:\my_path\my_venv"
export VIRTUAL_ENV
_OLD_VIRTUAL_PATH="$PATH"
PATH="$VIRTUAL_ENV/Scripts:$PATH"
export PATH
# unset PYTHONHOME if set
# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)
# could use `if (set -u; : $PYTHONHOME) ;` in bash
if [ -n "${PYTHONHOME:-}" ] ; then
_OLD_VIRTUAL_PYTHONHOME="${PYTHONHOME:-}"
unset PYTHONHOME
fi
if [ -z "${VIRTUAL_ENV_DISABLE_PROMPT:-}" ] ; then
_OLD_VIRTUAL_PS1="${PS1:-}"
PS1="(.venv_ml_dl_gen_purpose) ${PS1:-}"
export PS1
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r 2> /dev/null
fi
最后,这里还有脚本/mnt/c/my_path/my_venv_unix/bin/activate
# This file must be used with "source bin/activate" *from bash*
# you cannot run it directly
deactivate () {
# reset old environment variables
if [ -n "${_OLD_VIRTUAL_PATH:-}" ] ; then
PATH="${_OLD_VIRTUAL_PATH:-}"
export PATH
unset _OLD_VIRTUAL_PATH
fi
if [ -n "${_OLD_VIRTUAL_PYTHONHOME:-}" ] ; then
PYTHONHOME="${_OLD_VIRTUAL_PYTHONHOME:-}"
export PYTHONHOME
unset _OLD_VIRTUAL_PYTHONHOME
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r
fi
if [ -n "${_OLD_VIRTUAL_PS1:-}" ] ; then
PS1="${_OLD_VIRTUAL_PS1:-}"
export PS1
unset _OLD_VIRTUAL_PS1
fi
unset VIRTUAL_ENV
if [ ! "${1:-}" = "nondestructive" ] ; then
# Self destruct!
unset -f deactivate
fi
}
# unset irrelevant variables
deactivate nondestructive
VIRTUAL_ENV="/mnt/c/my_path/my_venv_unix"
export VIRTUAL_ENV
_OLD_VIRTUAL_PATH="$PATH"
PATH="$VIRTUAL_ENV/bin:$PATH"
export PATH
# unset PYTHONHOME if set
# this will fail if PYTHONHOME is set to the empty string (which is bad anyway)
# could use `if (set -u; : $PYTHONHOME) ;` in bash
if [ -n "${PYTHONHOME:-}" ] ; then
_OLD_VIRTUAL_PYTHONHOME="${PYTHONHOME:-}"
unset PYTHONHOME
fi
if [ -z "${VIRTUAL_ENV_DISABLE_PROMPT:-}" ] ; then
_OLD_VIRTUAL_PS1="${PS1:-}"
if [ "x(venv_unix) " != x ] ; then
PS1="(venv_unix) ${PS1:-}"
else
if [ "`basename \"$VIRTUAL_ENV\"`" = "__" ] ; then
# special case for Aspen magic directories
# see https://aspen.io/
PS1="[`basename \`dirname \"$VIRTUAL_ENV\"\``] $PS1"
else
PS1="(`basename \"$VIRTUAL_ENV\"`)$PS1"
fi
fi
export PS1
fi
# This should detect bash and zsh, which have a hash command that must
# be called to get it to forget past commands. Without forgetting
# past commands the $PATH changes we made may not be respected
if [ -n "${BASH:-}" -o -n "${ZSH_VERSION:-}" ] ; then
hash -r
fi
感谢所有愿意回答的人!
简短回答:强烈建议在 WSL 中使用 Python 的 Linux 版本和工具。您会在 Stack Overflow 上找到许多与此相关的帖子,但您的问题非常不同(关于 venv),值得单独回答。
更多详情:
同样值得一读
我知道 似乎 WSL 上的东西可能会更好,在那里你可以 运行 Windows .exe
cutables 在 Linux,但它确实不适用于这种特殊情况。
您已经解决了第一个问题,即行尾的差异,但您面临的下一个问题是目录格式的差异。采购 activate
后,执行 echo $PATH
,您会看到 Windows 样式 C:\path\to\the\venv
路径已添加到您的 PATH
。对于 WSL,需要 /mnt/c/path/to/the/venv
.
那是行不通的。
一旦你解决了这个问题(同样,通过编辑 activate
),你仍然在尝试 运行 python3
。 venv 可执行文件实际上是 python.exe
。在 WSL 下,您必须指定扩展名。
所以如果你:
- 将行尾从 CRLF 更改为 LF
- 将
activate
中的路径样式从 Windows 更改为 WSL2 格式 - 使用
python.exe
可执行文件
那么你至少可以启动 Windows Python 版本。您的 import sys; sys.path
将显示 Windows 路径。
就是说,您几乎肯定会 运行 遇到其他不值得这样做的问题。例如,如果脚本假定 python
或 python3
,甚至 pip
;那么那些将失败,因为它需要调用,例如 pip.exe
.
行尾和本机代码也会成为问题。
出于这些原因(可能更多),强烈建议在 WSL 中使用 Python 的 Linux 版本。