shell函数如何知道它是否在virtualenv中运行?

kjo*_*kjo 25 python bash shell virtualenv

一个bash函数应该如何测试它是否在Python virtualenv中运行?

想到的两种方法是:

[[ "$(type -t deactivate)" != function ]]; INVENV=$?
Run Code Online (Sandbox Code Playgroud)

要么

[[ "x$(which python)" != "x$VIRTUAL_ENV/bin/python" ]]; INVENV=$?
Run Code Online (Sandbox Code Playgroud)

(注意:$INVENV如果我们在virtualenv中,想要为1,否则为0,这是迫使上面的向后看测试的原因.)

有什么不那么hacky?

rob*_*lep 32

if [[ "$VIRTUAL_ENV" != "" ]]
then
  INVENV=1
else
  INVENV=0
fi
// or shorter if you like:
[[ "$VIRTUAL_ENV" == "" ]]; INVENV=$?
Run Code Online (Sandbox Code Playgroud)

编辑:正如@ThiefMaster在评论中提到的,在某些情况下(例如,当启动一个新的shell - 可能在- tmux或screen- 来自一个活跃的virtualenv)时,这个检查可能会失败(但是,从virtualenv中启动新的shell可能会导致其他问题,我不推荐它).

  • 这是不可靠的。例如,在 virtualenv 中启动的 tmux 会话中,venv 不活动但 $VIRTUAL_ENV 仍然设置。 (3认同)

kjo*_*kjo 15

实际上,我刚刚发现了一个类似的问题,从中可以很容易地得出这个问题的答案:

Python:确定是否在virtualenv中运行

例如,shell脚本可以使用类似的东西

python -c 'import sys; print (sys.real_prefix)' 2>/dev/null && INVENV=1 || INVENV=0
Run Code Online (Sandbox Code Playgroud)

(感谢Christian Long展示了如何使这个解决方案也适用于Python 3.)

编辑:这是一个更直接(更清晰,更清晰)的解决方案(从JuanPablo的评论中得到启示):

INVENV=$(python -c 'import sys; print ("1" if hasattr(sys, "real_prefix") else "0")')
Run Code Online (Sandbox Code Playgroud)

  • 检查的可选命令:`python -c'import sys; 打印 hasattr(sys, "real_prefix")' ` (3认同)
  • 我的 python env (`python3 -m venv venv`) 没有 `sys.real_prefix` 属性。作为替代方案可以吗?`INVENV=$( python -c 'import sys ; print( 0 if sys.prefix == sys.base_prefix else 1 )' )` (3认同)
  • 添加括号以支持Python 3`python -c'import sys; print(sys.real_prefix)'2>/dev/null && INVENV = 1 || INVENV = 0` (2认同)