python / python/cpython

More easily support creating reproducible archives with `shutil`

未关闭
#120,036 3 条评论 0 个 reaction 已指派 0 人 在 GitHub 查看

还没有人认领这个 Issue。

stdlib type-feature
主要语言
Python
星标
77.2k
派生
35.9k
PR 合并指标
PR 指标待抓取

描述

Proposal:

It would be handy if the shutil module provided a convenient way to opt in to the build artifact reproducibility features described in https://reproducible-builds.org/docs/archives/

Such an addition would likely make more sense as a new shutil.make_reproducible_archive function, rather than trying to shoehorn the new functionality into the existing shutil.make_archive API.

The specific problem that prompted this feature idea was encountering this traceback trying to set owner=0 and group=0 in shutil.make_archive:

Traceback (most recent call last):
[snip application details]
  File "/home/acoghlan/...[snip]...", line 97, in create_archive
    archive_with_extension = shutil.make_archive(
                             ^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib64/python3.12/shutil.py", line 1188, in make_archive
    filename = func(base_name, base_dir, **kwargs)
               ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
  File "/usr/lib64/python3.12/shutil.py", line 992, in _make_tarball
    uid = _get_uid(owner)
          ^^^^^^^^^^^^^^^
  File "/usr/lib64/python3.12/shutil.py", line 941, in _get_uid
    result = getpwnam(name)
             ^^^^^^^^^^^^^^
TypeError: getpwnam() argument must be str, not int

tarfile itself does support setting numeric owner and group IDs (via addfile and the filter option on add),but the high level shutil wrapper assumes the owner and group will always be given via names that can be looked up on the current system, it doesn't allow them to be specified numerically.

While supporting numeric uids and gids in the high level API would be mildly helpful, it isn't necessarily the most useful way to address the limitation since the only value anyone would ever likely pass numerically is 0 (which can be worked around on many systems by passing "root" as a symbolic name), and their actual goal would be to indicate that the archive is intended to be a reproducible build artifact, so they actively don't want to include environmental details that are specific to that particular invocation.

As things are now, it isn't a massive burden to copy-and-paste the _make_tarball code from shutil.py and adapt it for build artifact creation purposes, but I also think there genuinely are two very different use cases for archive creation (backups where you want to reproduce the original environment as faithfully as possible, and build artifacts that you want to make as portable and build system independent as possible), so there's potentially merit in offering a separate high level API for the case that isn't as well served by the existing high level API.

Has this already been discussed elsewhere?

No response given

Links to previous discussion of this feature:

No response

贡献指南

打开贡献指南

从这里开始

  1. 先读完整个 Issue,再读项目的贡献指南。
  2. 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
  3. Fork 仓库,在一个分支上完成修改。
  4. 提交 Pull Request,并在描述里引用这个 Issue 编号。

调研方向

先阅读 shutil.py,尤其是 make_archive 和 _make_tarball,然后将它们的行为与 tarfile 的 addfile 和 filter 支持进行比较。查看链接的 reproducible-builds 存档指南,并确定单独的高层 API 的范围。当所提出的可复现存档工作流已定义并得到支持,且不依赖于特定调用的环境细节时,即视为完成。

由索引模型根据 Issue 内容生成。

评估

技术栈
python
领域
tooling
Issue 类型
功能
难度
5/5
预计耗时
一周以上
活跃度
停滞
描述清晰度
基本清楚
新手友好度
35/100

把新 issue 发到你的邮箱

精选适合新手参与的 GitHub issue 摘要。