点下载而不执行setup.py [英] pip download without executing setup.py

查看:67
本文介绍了点下载而不执行setup.py的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何下​​载分发文件(可能是sdist),而又不执行 setup.py 文件(可能包含恶意代码)?

How to download a distribution, possibly sdist, without potentially executing a setup.py file (that may contain malicious code)?

我不想递归获取依赖项,仅下载一个文件用于指定的发行版.尝试不起作用:

I don't want to recursively get the dependencies, only download one file for the specified distribution. Attempt that doesn't work:

pip download --no-deps mydist

这是一个可重现的示例,展示了在上述情况下 setup.py 仍被执行:

Here is a reproducible example that demonstrates the setup.py is still executed in the above case:

$ docker run --rm -it python:3.8-alpine sh
/ # pip --version
pip 20.0.2 from /usr/local/lib/python3.8/site-packages/pip (python 3.8)
/ # pip download --no-deps suds
Collecting suds
  Downloading suds-0.4.tar.gz (104 kB)
     |████████████████████████████████| 104 kB 13.4 MB/s 
    ERROR: Command errored out with exit status 1:
     command: /usr/local/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/pip-download-yqfdz35d/suds/setup.py'"'"'; __file__='"'"'/tmp/pip-download-yqfdz35d/suds/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-download-yqfdz35d/suds/pip-egg-info
         cwd: /tmp/pip-download-yqfdz35d/suds/
    Complete output (7 lines):
    Traceback (most recent call last):
      File "<string>", line 1, in <module>
      File "/tmp/pip-download-yqfdz35d/suds/setup.py", line 20, in <module>
        import suds
      File "/tmp/pip-download-yqfdz35d/suds/suds/__init__.py", line 154, in <module>
        import client
    ModuleNotFoundError: No module named 'client'
    ----------------------------------------
ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.

我不能使用-no-binary 选项,因为我不想排除源代码发行版.我只想避免执行其源代码.

I cannot use --no-binary option, because I don't want to exclude source distributions. I just want to avoid executing their source code.

推荐答案

我一直在研究 pip ,可悲的是,那里的代码非常复杂.似乎目前尚无办法,根据@doctaphred提供的链接,目前尚无计划在那个方向上取得进展.

I've been digging into pip, and sadly the code there is pretty convoluted. It seems that currently there is no way to do that, and according to the link provided by @doctaphred there are no plans to make progress in that direction.

下一步取决于您的情况;例如,如果您需要此软件包下载器"进行生产,建议您编写自己的pypi客户端.编写起来非常简单,并且可以根据需要对其进行优化,从而使其比 pip 更快,更简单.为此,您可以尝试使用 pip 中的一些现有代码,但是我认为这很困难(在看到该代码之后).

The next step depends on your situation; If, for example, you need this "package downloader" for production, I'd suggest you write your own pypi client. It would be very simple to write and you could make it much faster and simpler than pip by optimizing it for your needs. To do that you could try to use some of the existing code in pip, but I think it will probably be pretty hard (after seeing that code).

否则,我会考虑采用更快,更骇人的方法来完成工作.我想到的第一个解决方案是,只要尝试运行 egg_info 命令,便停止 pip .为此,您可以使用各种方法在运行时修补 pip 的代码.我最喜欢的是使用 usercutomize 文件.

Otherwise, I'd consider quicker, hackier methods to get the job done. The first solution that comes to mind is just stopping pip whenever it tries to run the egg_info command. To do that you can patch pip's code at runtime using various methods. My favorite is using a usercutomize file.

例如,创建具有以下内容的补丁文件并将其放置在您选择的目录中:

For example, create a patch file with the following content and place it in a directory of your choosing:

/pypatches/pip_pure_download/usercustomize.py :

from pip._internal.req.req_install import InstallRequirement

print('Applying pure download patch!')

def override_run_egg_info(*args, **kwargs):
    raise KeyboardInterrupt # Joke's on you, evil hackers! :P

InstallRequirement.run_egg_info = override_run_egg_info

现在要将补丁应用于python执行,只需将补丁的目录添加到 PYTHONPATH ,例如:

Now to apply the patch to a python execution, just add the patch's directory to the PYTHONPATH, for example:

PYTHONPATH=/pypatches/pip_pure_download:$PYTHONPATH pip download --no-deps suds

这篇关于点下载而不执行setup.py的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆