使用Python时有什么好的处理案例虚拟环境 但是你想通过你的发行版的包管理器安装一些包?
假设您需要 lxml 但是因为你不能得到pip install lxml
在 Ubuntu 上工作。而且您真的不想在这上面浪费时间,所以您只需执行 apt-get install python-lxml
.
现在,您可以使用 --system-site-packages
创建一个 virtaulenv。并可以访问系统范围内安装的预编译 lxml 现在。但是您还将拖入您不需要的所有其他系统范围的软件包!是的,会有很多软件包安装在 virtualenv 之外,或者通过 sudo pip ...
或 sudo apt-get python-...
,所以没有 “只需保持系统清洁并在 virtualenvs 中安装所有可以安装的东西,这样 --system-site-packages
就不会拖拽太多的包” 不是我在这里的解决方案。
所以,有没有办法只安装一些特定的系统站 pip 包?
最佳答案
我总是用pip install --user packagename
– 它不需要 sudo。
如果您没有 pip
然而,或者任何一个操作系统的pip
或操作系统的 easy_install
不能正常使用,先安装setuptools
在用户的主目录中,然后使用它的easy_install
对于 pip
.
$ wget https://bootstrap.pypa.io/ez_setup.py -O - | python3 - --user
$ easy_install-3.4 --user pip
另一方面,如果您决定使用
pip
在 virtualenv 中,不要使用 --user
出于明显的原因选择。按照你描述的方式做
比如我要导入模块
curl
这存在于操作系统中。$ pip3 install --user virtualenv
$ python3 -m virtualenv myvenv
$ cd myvenv
$ source bin/activate
(myvenv)$ python3
>>> import curl
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ImportError: No module named curl
virtualenv 中没有这样的模块。只是为了确保我查看了
sys.path
中的内容.>>> import sys
>>> sys.path
['',
'/home/username/myvenv/lib/python27.zip',
'/home/username/myvenv/lib/python2.7',
'/home/username/myvenv/lib/python2.7/lib-dynload',
'/usr/lib/python2.7', '/usr/lib/python2.7/plat-linux2',
'/home/username/myvenv/lib/python2.7/site-packages']
注意没有
/usr/lib/python3.4/site-packages
,正如你所愿,但是 /usr/lib/python3.4
存在。如果这不适合您,请使用 --always-copy
创建 virtualenv 时的选项。在接下来的步骤中,我创建了指向
curl
的符号链接(symbolic link)。模块及其依赖项。>>> ^D # Press Control-D
(myvenv)$ ln -s /usr/lib/python3.4/site-packages/curl lib/python3.4/site-packages/
请注意,第二个参数(符号链接(symbolic link)指向的文件或目录)中没有斜杠,但第三个参数(应创建符号链接(symbolic link)的位置)中有一个斜杠。那是因为我创建了一个符号链接(symbolic link) 里面 目录
lib/python3.4/site-packages
.如果没有尾部斜杠,它将尝试替换目录。让我们检查一下是否有效。
(myvenv)$ python3
>>> import curl
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/home/username/myvenv/lib/python3.4/site-packages/curl/__init__.py", line 9, in <module>
import sys, pycurl
ImportError: No module named 'pycurl'
没有。
curl
取决于 pycurl
.我们需要更深入。>>> ^D
(myvenv)$ ls -1 /usr/lib/python3.4/site-packages/pycurl*
/usr/lib/python3.4/site-packages/pycurl-7.19.3.1-py3.4.egg-info
/usr/lib/python3.4/site-packages/pycurl.cpython-34m.so
(myvenv)$ ln -s /usr/lib/python3.4/site-packages/pycurl-7.19.3.1-py3.4.egg-info lib/python3.4/site-packages/
(myvenv)$ ln -s /usr/lib/python3.4/site-packages/pycurl.cpython-34m.so lib/python3.4/site-packages/
(myvenv)$ python3
>>> import curl
>>> curl
<module 'curl' from '/home/username/myvenv/lib/python3.4/site-packages/curl/__init__.py'>
最后。
这是你需要的吗?
就个人而言,我强烈反对你这样做,因为首先,这是一种变态。
此外,我怀疑这种方法适用于一切。依赖的深度可能令人恐惧。
其次,我认为没有理由避免
--system-site-packages
在我得到认可的所有情况下,这就像一种魅力。pip
安装的软件包用户主目录中的软件包优先级高于系统范围的软件包,因此在执行 import
时优先使用它们.在 virtualenv 中,只有在使用
--system-site-packages
创建 virtualenv 时才会导入它们。选项。pip
安装的软件包在 virtualenv 内部有更高的优先级。老实说,我写这个答案只是为了问,为什么你想搞砸这一切而不是得到
pip
去工作。我还不能对 SO 写评论,所以我写了一个完整的答案。 :)But you'll also drag in all the other system wide packages that you don't need!
不,你不会。只有在执行
import
时才将模块加载到内存中。 .如果您的意思是该软件包将出现在 virtualenv 中——再一次,它不会出现。如果您查看了 myvenv/lib/python3.4/site-packages/
的内部你会看到里面只有两个包 - pip
和 setuptools
(虽然后者被分成几个目录)。 virtualenv 中的 Python 解释器只是像普通解释器一样加载系统范围的模块。附言上面的代码也适用于 Python 2.7。只需更换
pip3
与 pip2
, python3
与 python2
, 3.4
与 2.7
, ETC。附言除了符号链接(symbolic link),您可以将模块及其依赖项复制到 virtualenv 到相应的目录中。这在使用
--always-copy
时有意义。 ,以便您的 virtualenv 变得可移植。P.P.P.S.如果您决定将 virtualenv 与
--system-site-packages
一起使用和 pip
, 假设你想要 requests
比 /usr/lib
中已安装的软件包更新的软件包, 使用 pip install -I
,如 here 所述.
关于python - 将 Python virtualenv 包与发行包混合?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30094624/