Python 为什么Pip会忽略具有嵌套依赖项的已配置存储库? 问题

Python 为什么Pip会忽略具有嵌套依赖项的已配置存储库? 问题,python,pip,artifactory,rpy2,python-cffi,Python,Pip,Artifactory,Rpy2,Python Cffi,假设我在Linux机器上有一个完全空的Python+Pip+R(Pip 19.3.1)环境,我想用Pip安装包rpy2。因为我在公司防火墙后面,所以我将pip配置为使用私有存储库 [global] index-url = http://private.com/artifactory/api/pypi/PyPI/simple trusted-host = private.com 现在我执行pip install rpy2,将返回以下错误: Couldn't find index page for

假设我在Linux机器上有一个完全空的Python+Pip+R(Pip 19.3.1)环境,我想用Pip安装包
rpy2
。因为我在公司防火墙后面,所以我将pip配置为使用私有存储库

[global]
index-url = http://private.com/artifactory/api/pypi/PyPI/simple
trusted-host = private.com
现在我执行
pip install rpy2
,将返回以下错误:

Couldn't find index page for 'cffi'
 Download error on https://pypi.python.org/simple/
因此,pip试图通过从官方PyPi存储库中查找和安装
cffi
来解决嵌套依赖关系。它完全忽略了我配置的回购协议

当我一个接一个地运行
pip-install-cffi&&pip-install-rpy2时,一切正常

以下是完整的错误输出:

ERROR: Command errored out with exit status 1:
 command: /usr/bin/python3 -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/pip-install-8vuadu93/rpy2/setup.py'"'"'; __file__='"'"'/tmp/pip-install-8vuadu93/rpy2/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' egg_info --egg-base /tmp/pip-install-8vuadu93/rpy2/pip-egg-info
     cwd: /tmp/pip-install-8vuadu93/rpy2/
Complete output (25 lines):
Download error on https://pypi.python.org/simple/cffi/: [Errno -2] Name or service not known -- Some packages may not be found!
Couldn't find index page for 'cffi' (maybe misspelled?)
Download error on https://pypi.python.org/simple/: [Errno -2] Name or service not known -- Some packages may not be found!
No local packages or working download links found for cffi>=1.13.1
Traceback (most recent call last):
  File "<string>", line 1, in <module>
  File "/tmp/pip-install-8vuadu93/rpy2/setup.py", line 183, in <module>
    'rinterface_lib/R_API_eventloop.h']}
  File "/usr/lib/python3/dist-packages/setuptools/__init__.py", line 128, in setup
    _install_setup_requires(attrs)
  File "/usr/lib/python3/dist-packages/setuptools/__init__.py", line 123, in _install_setup_requires
    dist.fetch_build_eggs(dist.setup_requires)
  File "/usr/lib/python3/dist-packages/setuptools/dist.py", line 513, in fetch_build_eggs
    replace_conflicting=True,
  File "/usr/lib/python3/dist-packages/pkg_resources/__init__.py", line 774, in resolve
    replace_conflicting=replace_conflicting
  File "/usr/lib/python3/dist-packages/pkg_resources/__init__.py", line 1057, in best_match
    return self.obtain(req, installer)
  File "/usr/lib/python3/dist-packages/pkg_resources/__init__.py", line 1069, in obtain
    return installer(requirement)
  File "/usr/lib/python3/dist-packages/setuptools/dist.py", line 580, in fetch_build_egg
    return cmd.easy_install(req)
  File "/usr/lib/python3/dist-packages/setuptools/command/easy_install.py", line 692, in easy_install
    raise DistutilsError(msg)
distutils.errors.DistutilsError: Could not find suitable distribution for Requirement.parse('cffi>=1.13.1')
----------------------------------------
ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.

我使用了
-vvv
,问题似乎发生在
setuptools

解决方案 软件包
rpy2
使用
setuptools
,它再次使用
easy\u install.py
。它还与
index\u url
变量一起使用。但是它不是从
pip.config
获取值,而是从
distutils.cfg
获取值

我识别了所有安装了
find/-name“distutils”
的Python版本。然后,我将a
distutils.cfg
和以下内容添加到每个目录中:

[easy_install]
index_url = blablabla

现在它工作了,我执行了
pip安装rpy2
,所有缺失的需求都一次性安装了我相信这可能是因为
cffi
在rpy2的
setup.py
中被列为
setup\u requires
。很可能是因为在安装项目之前,需要先构建项目本身。这种构建依赖关系不是由pip直接处理的,因此其
索引url
选项没有任何效果

解决方案是在

参考资料:


如果将配置设置指定为命令行参数,会发生什么情况?有什么区别吗?如果您还指定了
--无索引
,会发生什么情况?您是否尝试过在需求中指定私有索引?是的,我两次都试过了,但都没有积极的结果。我在我的帖子中添加了完整的Python stacktrace,但没有深入研究,但这可能是因为
cffi
被列为
setup\u requires
(当然也在
install\u requires
中列出)。如果这个依赖项是在pip控制之外下载的,我不会感到惊讶。也许这会有帮助:是的,就是这样!谢谢@sinoroc。你能补充一个答案吗?这样我就可以把这个问题标记为你的答案了?
[easy_install]
index_url = blablabla
[easy_install]
index_url = https://my.index-mirror.com